home *** CD-ROM | disk | FTP | other *** search
/ Geek 6 / Geek-006.iso / linux / video / xmovie-1.5.3.tar.gz / xmovie-1.5.3.tar / xmovie-1.5.3 / quicktime / plugin.c < prev    next >
C/C++ Source or Header  |  2000-11-29  |  9KB  |  368 lines

  1. #include <stdio.h>
  2. #include <dirent.h>
  3. #include <dlfcn.h>
  4. #include "quicktime.h"
  5.  
  6.  
  7. static int total_vcodecs = 0;
  8. static int total_acodecs = 0;
  9. static quicktime_extern_video_t *vcodecs = NULL; 
  10. static quicktime_extern_audio_t *acodecs = NULL; 
  11.  
  12.  
  13. #define CODEC_PREFIX "quicktime_codec_"
  14.  
  15.  
  16.  
  17. static int decode_audio_external(quicktime_t *file, 
  18.                 QUICKTIME_INT16 *output_i, 
  19.                 float *output_f, 
  20.                 long samples, 
  21.                 int track,
  22.                 int channel)
  23. {
  24.     return -1;
  25. }
  26.  
  27. static int encode_audio_external(quicktime_t *file, 
  28.                 QUICKTIME_INT16 **input_i, 
  29.                 float **input_f, 
  30.                 int track, 
  31.                 long samples)
  32. {
  33.     return -1;
  34. }
  35.  
  36. static int decode_video_external(quicktime_t *file, 
  37.                 unsigned char **row_pointers, 
  38.                 int track)
  39. {
  40.     unsigned char *input;
  41.     unsigned char *output = row_pointers[0]; 
  42.     int    index = 0;
  43.     int error = -1;
  44.     quicktime_video_map_t *vtrack = &(file->vtracks[track]);
  45.     unsigned int bytes;
  46.     char *compressor;
  47.  
  48.     compressor = quicktime_video_compressor(file, track);
  49.     index = quicktime_find_vcodec(compressor);
  50.  
  51.     if(index >= 0)
  52.     {
  53.         quicktime_set_video_position(file, vtrack->current_position, track);
  54.         bytes = quicktime_frame_size(file, vtrack->current_position, track);
  55.  
  56.         if(bytes <= 0) 
  57.         {
  58.             fprintf(stderr, "decode_video_external: frame size equal %d\n", bytes);
  59.             return -1;
  60.         }
  61.  
  62.         input = (unsigned char*)malloc(bytes);
  63.         if(input) 
  64.         {
  65.             if(quicktime_read_data(file, input, bytes)) 
  66.                 error = vcodecs[index].decode(file, track, bytes, input, output); 
  67.               else 
  68.                 fprintf(stderr, "decode_video_external: can't read data from file\n");
  69.  
  70.         } 
  71.         else 
  72.             fprintf(stderr, "decode_video_external: Can't allocate decoding buffer");
  73.  
  74.         free(input);
  75.     }
  76.     else 
  77.     {
  78.         fprintf(stderr, 
  79.             "decode_video_external: Can't find the corresponding codec: ",
  80.             quicktime_video_compressor(file, track));
  81.     }
  82.     return error;
  83. }
  84.  
  85.  
  86.  
  87.  
  88. static int encode_video_external(quicktime_t *file, 
  89.                  unsigned char **row_pointers, 
  90.                  int track)
  91. {
  92.     unsigned char *input = row_pointers[0];
  93.     unsigned char *output; 
  94.     int index = 0;
  95.     int error = -1;
  96.     quicktime_video_map_t *vtrack = &(file->vtracks[track]);
  97.     unsigned int bytes;
  98.     long offset = quicktime_position(file);
  99.     char *compressor;
  100.     short width, height, depth;
  101.  
  102.     compressor = quicktime_video_compressor(file, track);
  103.     index = quicktime_find_vcodec(compressor);
  104.     if(index >= 0)
  105.     {
  106. /* Initializing some local variables */
  107.         width  = vtrack->track->tkhd.track_width;
  108.         height = vtrack->track->tkhd.track_height;
  109.         depth  = file->vtracks[track].track->mdia.minf.stbl.stsd.table[0].depth;
  110.         bytes  = width * height * depth / 8;
  111.  
  112.         output = (unsigned char*)malloc(bytes);
  113.         if(output) 
  114.         {
  115.             bytes = vcodecs[index].encode(file, track, input, output); 
  116.  
  117.             if(bytes > 0)
  118.             {
  119.                 printf("Writing %d bytes\n", bytes);
  120.  
  121.                 error = !quicktime_write_data(file, output, bytes);
  122.  
  123.                 quicktime_update_tables(file,
  124.                     file->vtracks[track].track,
  125.                     offset,
  126.                     file->vtracks[track].current_chunk,
  127.                     file->vtracks[track].current_position,
  128.                     1,
  129.                     bytes);
  130.  
  131.                 file->vtracks[track].current_chunk++;
  132.               } 
  133.             else 
  134.                 fprintf(stderr, "encode_video_external: Error in external encoding function\n");
  135.  
  136.               free(output);
  137.         } 
  138.         else 
  139.             fprintf(stderr, "encode_video_external: Can't allocate encoding buffer");
  140.       } 
  141.     else 
  142.         fprintf(stderr, 
  143.             "encode_video_external: Can't find the corresponding codec: ",
  144.             quicktime_video_compressor(file, track) );
  145.   
  146.     return error;    
  147. }
  148.  
  149.  
  150.  
  151. int quicktime_vcodec_size()
  152. {
  153.     return total_vcodecs;
  154. }
  155.  
  156. int quicktime_acodec_size()
  157. {
  158.     return total_acodecs;
  159. }
  160.  
  161.  
  162. int quicktime_find_vcodec(char *fourcc)
  163. {
  164.       int i;
  165.  
  166.       for(i = 0; i < total_vcodecs; i++)
  167.       {
  168.         if(quicktime_match_32(fourcc, vcodecs[i].fourcc))
  169.               return i;
  170.       }
  171.       return -1;
  172. }
  173.  
  174.  
  175. int quicktime_find_acodec(char *fourcc)
  176. {
  177.     int i;
  178.  
  179.     for(i = 0; i < total_acodecs; i++)
  180.     {
  181.         if(quicktime_match_32(fourcc, acodecs[i].fourcc))
  182.             return i;
  183.     }
  184.     return -1;
  185. }
  186.  
  187.  
  188.  
  189.  
  190.  
  191. int quicktime_register_vcodec(char *fourcc, 
  192.     void (*init_vcodec)(quicktime_video_map_t *))
  193. {
  194.     int index = quicktime_find_vcodec(fourcc);
  195.  
  196.     if(index == -1)
  197.     {
  198.         total_vcodecs++;
  199.         vcodecs = (quicktime_extern_video_t *)realloc(vcodecs,
  200.             total_vcodecs * sizeof(quicktime_extern_video_t));
  201.  
  202.         vcodecs[total_vcodecs - 1].init = init_vcodec;
  203.         quicktime_copy_char32(vcodecs[total_vcodecs - 1].fourcc, fourcc);
  204.         return total_vcodecs - 1;
  205.     }
  206.     return index;
  207. }
  208.  
  209. int quicktime_register_acodec(char *fourcc, 
  210.     void (*init_acodec)(quicktime_audio_map_t *))
  211. {
  212.     int index = quicktime_find_acodec(fourcc);
  213.  
  214.     if(index == -1)
  215.     {
  216.         total_acodecs++;
  217.         acodecs = (quicktime_extern_audio_t *)realloc(acodecs,
  218.             total_acodecs * sizeof(quicktime_extern_audio_t));
  219.         acodecs[total_acodecs - 1].init = init_acodec;
  220.         quicktime_copy_char32(acodecs[total_acodecs - 1].fourcc, fourcc);
  221.         return total_acodecs - 1;
  222.     }
  223.     return index;
  224. }
  225.  
  226. static int select_codec(const struct dirent *ptr)
  227. {
  228.     if(strncmp(ptr->d_name, CODEC_PREFIX, 15) == 0)
  229.         return 1;
  230.     else 
  231.         return 0;
  232. }
  233.  
  234. void quicktime_register_internal_acodec()
  235. {
  236.     quicktime_register_acodec(QUICKTIME_TWOS, quicktime_init_codec_twos);
  237.     quicktime_register_acodec(QUICKTIME_RAW,  quicktime_init_codec_rawaudio);
  238.     quicktime_register_acodec(QUICKTIME_IMA4, quicktime_init_codec_ima4); 
  239.     quicktime_register_acodec(QUICKTIME_ULAW, quicktime_init_codec_ulaw); 
  240. }
  241.  
  242. void quicktime_register_internal_vcodec()
  243. {
  244.     quicktime_register_vcodec(QUICKTIME_RAW, quicktime_init_codec_raw);
  245.     quicktime_register_vcodec(QUICKTIME_DV, quicktime_init_codec_dv); 
  246.     quicktime_register_vcodec(QUICKTIME_JPEG, quicktime_init_codec_jpeg); 
  247.     quicktime_register_vcodec(QUICKTIME_MJPA, quicktime_init_codec_jpeg); 
  248.     quicktime_register_vcodec(QUICKTIME_PNG, quicktime_init_codec_png); 
  249.     quicktime_register_vcodec(QUICKTIME_YUV422, quicktime_init_codec_yuv2); 
  250.     quicktime_register_vcodec(QUICKTIME_YUV4, quicktime_init_codec_yuv4); 
  251.     quicktime_register_vcodec(QUICKTIME_YUV420, quicktime_init_codec_yuv4); 
  252. }
  253.  
  254.  
  255. int quicktime_register_external_vcodec(const char *codec_name)
  256. {
  257.     void *handle;
  258.     int (*quicktime_codec_register)(quicktime_extern_video_t*);
  259.     char path[1024];
  260.     char *error;
  261.  
  262.     sprintf(path, "%s%s.so", CODEC_PREFIX, codec_name);
  263.     fprintf(stderr, "Trying to load external codec %s\n", path);
  264.  
  265.     handle = dlopen(path, RTLD_NOW);
  266.     if(!handle)
  267.     {
  268.         fprintf(stderr, "Can't load the codec\n");
  269.         fprintf(stderr, "%s\n", dlerror());
  270.         return -1;
  271.     }
  272.     fprintf(stderr, "External codec %s loaded\n", path);
  273.  
  274.     quicktime_codec_register = dlsym(handle, "quicktime_codec_register");
  275.     if((error = dlerror()) != NULL)  
  276.     {
  277.         fprintf(stderr, "%s\n",error);
  278.         return -1;
  279.     }
  280.  
  281.     total_vcodecs++;
  282.     vcodecs = (quicktime_extern_video_t *)realloc(vcodecs,
  283.         total_vcodecs*sizeof(quicktime_extern_video_t));
  284.  
  285.     if((*quicktime_codec_register)(&(vcodecs[total_vcodecs - 1]))) 
  286.     {
  287.         printf("adding intermediate functions\n");
  288.  
  289.         vcodecs[total_vcodecs - 1].codec.delete_vcodec = vcodecs[total_vcodecs - 1].delete_codec;
  290.         vcodecs[total_vcodecs - 1].codec.decode_video = decode_video_external;
  291.         vcodecs[total_vcodecs - 1].codec.encode_video = encode_video_external;
  292.  
  293.         return total_vcodecs - 1;
  294.     } 
  295.     else
  296.         return -1;
  297. }
  298.  
  299.  
  300.  
  301. int quicktime_register_external_acodec(const char *codec_name)
  302. {
  303.     void *handle;
  304.     int (*quicktime_codec_register)(quicktime_extern_audio_t*);
  305.     char path[1024];
  306.     char *error;
  307.  
  308.     sprintf(path, "%s%s.so", CODEC_PREFIX, codec_name);
  309.     fprintf(stderr, "Trying to load external codec %s\n", path);
  310.     handle = dlopen(path, RTLD_NOW);
  311.     if(!handle)
  312.     {
  313.         fprintf(stderr, "Can't load the codec\n");
  314.         fprintf(stderr, "%s\n", dlerror());
  315.         return -1;
  316.     }
  317.     fprintf(stderr, "External codec %s loaded\n", path);
  318.  
  319.     quicktime_codec_register = dlsym(handle, "quicktime_codec_register");
  320.     if((error = dlerror()) != NULL)  
  321.     {
  322.         fprintf(stderr, "%s\n",error);
  323.         return -1;
  324.     }
  325.  
  326.     total_acodecs++;
  327.     acodecs = (quicktime_extern_audio_t *)realloc(acodecs,
  328.         total_acodecs*sizeof(quicktime_extern_audio_t));
  329.  
  330.     if((*quicktime_codec_register)(&(acodecs[total_acodecs-1])))
  331.     {
  332.         printf("adding intermediate functions\n");
  333.  
  334.         acodecs[total_acodecs - 1].codec.delete_acodec = acodecs[total_acodecs - 1].delete_codec;
  335.         acodecs[total_acodecs - 1].codec.decode_audio = decode_audio_external;
  336.         acodecs[total_acodecs - 1].codec.encode_audio = encode_audio_external;
  337.  
  338.         return total_vcodecs - 1;
  339.     } 
  340.     else
  341.         return -1;
  342. }
  343.  
  344.  
  345. int quicktime_init_vcodec_core(int index, quicktime_video_map_t *vtrack)
  346. {
  347.     ((quicktime_codec_t*)vtrack->codec)->delete_vcodec = vcodecs[total_vcodecs - 1].codec.delete_vcodec;
  348.     ((quicktime_codec_t*)vtrack->codec)->decode_video = vcodecs[total_vcodecs - 1].codec.decode_video;
  349.     ((quicktime_codec_t*)vtrack->codec)->encode_video = vcodecs[total_vcodecs - 1].codec.encode_video;
  350.  
  351.     vcodecs[index].init(vtrack);
  352.     return 0;
  353. }
  354.  
  355. int quicktime_init_acodec_core(int index, quicktime_audio_map_t *atrack)
  356. {
  357.     ((quicktime_codec_t*)atrack->codec)->delete_acodec = acodecs[total_acodecs - 1].codec.delete_acodec;
  358.     ((quicktime_codec_t*)atrack->codec)->decode_audio = acodecs[total_acodecs - 1].codec.decode_audio;
  359.     ((quicktime_codec_t*)atrack->codec)->encode_audio = acodecs[total_acodecs - 1].codec.encode_audio;
  360.  
  361.     acodecs[index].init(atrack);
  362.     return 0;
  363. }
  364.  
  365.  
  366.  
  367.  
  368.