⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 avilib.c

📁 Simple SunPlus SP54 codec converter and a more playable mode MJPG. untar the archive go to the r
💻 C
📖 第 1 页 / 共 3 页
字号:
      if(read(AVI->fdes,data,8)!=8) ERR_EXIT(AVI_ERR_READ)      if( strncasecmp(data,AVI->idx[i],4)==0 && str2ulong(data+4)==len )      {         idx_type = 1; /* Index from start of file */      }      else      {         lseek(AVI->fdes,pos+AVI->movi_start-4,SEEK_SET);         if(read(AVI->fdes,data,8)!=8) ERR_EXIT(AVI_ERR_READ)         if( strncasecmp(data,AVI->idx[i],4)==0 && str2ulong(data+4)==len )         {            idx_type = 2; /* Index from start of movi list */         }      }      /* idx_type remains 0 if neither of the two tests above succeeds */   }   if(idx_type == 0)   {      /* we must search through the file to get the index */      lseek(AVI->fdes, AVI->movi_start, SEEK_SET);      AVI->n_idx = 0;      while(1)      {         if( read(AVI->fdes,data,8) != 8 ) break;         n = str2ulong(data+4);         /* The movi list may contain sub-lists, ignore them */         if(strncasecmp(data,"LIST",4)==0)         {            lseek(AVI->fdes,4,SEEK_CUR);            continue;         }         /* Check if we got a tag ##db, ##dc or ##wb */         if( ( (data[2]=='d' || data[2]=='D') &&               (data[3]=='b' || data[3]=='B' || data[3]=='c' || data[3]=='C') )          || ( (data[2]=='w' || data[2]=='W') &&               (data[3]=='b' || data[3]=='B') ) )         {            avi_add_index_entry(AVI,data,0,lseek(AVI->fdes,0,SEEK_CUR)-8,n);         }         lseek(AVI->fdes,PAD_EVEN(n),SEEK_CUR);      }      idx_type = 1;   }   /* Now generate the video index and audio index arrays */   nvi = 0;   nai = 0;   for(i=0;i<AVI->n_idx;i++)   {      if(strncasecmp(AVI->idx[i],AVI->video_tag,3) == 0) nvi++;      if(strncasecmp(AVI->idx[i],AVI->audio_tag,4) == 0) nai++;   }   AVI->video_frames = nvi;   AVI->audio_chunks = nai;   if(AVI->video_frames==0) ERR_EXIT(AVI_ERR_NO_VIDS)   AVI->video_index = (video_index_entry *) malloc(nvi*sizeof(video_index_entry));   if(AVI->video_index==0) ERR_EXIT(AVI_ERR_NO_MEM)   if(AVI->audio_chunks)   {      AVI->audio_index = (audio_index_entry *) malloc(nai*sizeof(audio_index_entry));      if(AVI->audio_index==0) ERR_EXIT(AVI_ERR_NO_MEM)   }   nvi = 0;   nai = 0;   tot = 0;   ioff = idx_type == 1 ? 8 : AVI->movi_start+4;   for(i=0;i<AVI->n_idx;i++)   {      if(strncasecmp(AVI->idx[i],AVI->video_tag,3) == 0)      {         AVI->video_index[nvi].pos = str2ulong(AVI->idx[i]+ 8)+ioff;         AVI->video_index[nvi].len = str2ulong(AVI->idx[i]+12);         nvi++;      }      if(strncasecmp(AVI->idx[i],AVI->audio_tag,4) == 0)      {         AVI->audio_index[nai].pos = str2ulong(AVI->idx[i]+ 8)+ioff;         AVI->audio_index[nai].len = str2ulong(AVI->idx[i]+12);         AVI->audio_index[nai].tot = tot;         tot += AVI->audio_index[nai].len;         nai++;      }   }   AVI->audio_bytes = tot;   /* Reposition the file */   lseek(AVI->fdes,AVI->movi_start,SEEK_SET);   AVI->video_pos = 0;   return AVI;}long AVI_video_frames(avi_t *AVI){   return AVI->video_frames;}int  AVI_video_width(avi_t *AVI){   return AVI->width;}int  AVI_video_height(avi_t *AVI){   return AVI->height;}double AVI_frame_rate(avi_t *AVI){   return AVI->fps;}char* AVI_video_compressor(avi_t *AVI){   return AVI->compressor;}int AVI_audio_channels(avi_t *AVI){   return AVI->a_chans;}int AVI_audio_bits(avi_t *AVI){   return AVI->a_bits;}int AVI_audio_format(avi_t *AVI){   return AVI->a_fmt;}long AVI_audio_rate(avi_t *AVI){   return AVI->a_rate;}long AVI_audio_bytes(avi_t *AVI){   return AVI->audio_bytes;}long AVI_frame_size(avi_t *AVI, long frame){   if(AVI->mode==AVI_MODE_WRITE) { AVI_errno = AVI_ERR_NOT_PERM; return -1; }   if(!AVI->video_index)         { AVI_errno = AVI_ERR_NO_IDX;   return -1; }   if(frame < 0 || frame >= AVI->video_frames) return 0;   return(AVI->video_index[frame].len);}int AVI_seek_start(avi_t *AVI){   if(AVI->mode==AVI_MODE_WRITE) { AVI_errno = AVI_ERR_NOT_PERM; return -1; }   lseek(AVI->fdes,AVI->movi_start,SEEK_SET);   AVI->video_pos = 0;   return 0;}int AVI_set_video_position(avi_t *AVI, long frame){   if(AVI->mode==AVI_MODE_WRITE) { AVI_errno = AVI_ERR_NOT_PERM; return -1; }   if(!AVI->video_index)         { AVI_errno = AVI_ERR_NO_IDX;   return -1; }   if (frame < 0 ) frame = 0;   AVI->video_pos = frame;   return 0;}      long AVI_read_frame(avi_t *AVI, char *vidbuf){   long n;   if(AVI->mode==AVI_MODE_WRITE) { AVI_errno = AVI_ERR_NOT_PERM; return -1; }   if(!AVI->video_index)         { AVI_errno = AVI_ERR_NO_IDX;   return -1; }   if(AVI->video_pos < 0 || AVI->video_pos >= AVI->video_frames) return 0;   n = AVI->video_index[AVI->video_pos].len;   lseek(AVI->fdes, AVI->video_index[AVI->video_pos].pos, SEEK_SET);   if (read(AVI->fdes,vidbuf,n) != n)   {      AVI_errno = AVI_ERR_READ;      return -1;   }   AVI->video_pos++;   return n;}int AVI_set_audio_position(avi_t *AVI, long byte){   long n0, n1, n;   if(AVI->mode==AVI_MODE_WRITE) { AVI_errno = AVI_ERR_NOT_PERM; return -1; }   if(!AVI->audio_index)         { AVI_errno = AVI_ERR_NO_IDX;   return -1; }   if(byte < 0) byte = 0;   /* Binary search in the audio chunks */   n0 = 0;   n1 = AVI->audio_chunks;   while(n0<n1-1)   {      n = (n0+n1)/2;      if(AVI->audio_index[n].tot>byte)         n1 = n;      else         n0 = n;   }   AVI->audio_posc = n0;   AVI->audio_posb = byte - AVI->audio_index[n0].tot;   return 0;}long AVI_read_audio(avi_t *AVI, char *audbuf, long bytes){   long nr, pos, left, todo;   if(AVI->mode==AVI_MODE_WRITE) { AVI_errno = AVI_ERR_NOT_PERM; return -1; }   if(!AVI->audio_index)         { AVI_errno = AVI_ERR_NO_IDX;   return -1; }   nr = 0; /* total number of bytes read */   while(bytes>0)   {      left = AVI->audio_index[AVI->audio_posc].len - AVI->audio_posb;      if(left==0)      {         if(AVI->audio_posc>=AVI->audio_chunks-1) return nr;         AVI->audio_posc++;         AVI->audio_posb = 0;         continue;      }      if(bytes<left)         todo = bytes;      else         todo = left;      pos = AVI->audio_index[AVI->audio_posc].pos + AVI->audio_posb;      lseek(AVI->fdes, pos, SEEK_SET);      if (read(AVI->fdes,audbuf+nr,todo) != todo)      {         AVI_errno = AVI_ERR_READ;         return -1;      }      bytes -= todo;      nr    += todo;      AVI->audio_posb += todo;   }   return nr;}/* AVI_read_data: Special routine for reading the next audio or video chunk                  without having an index of the file. */int AVI_read_data(avi_t *AVI, char *vidbuf, long max_vidbuf,                              char *audbuf, long max_audbuf,                              long *len){/* * Return codes: * *    1 = video data read *    2 = audio data read *    0 = reached EOF *   -1 = video buffer too small *   -2 = audio buffer too small */   int n;   char data[8];   if(AVI->mode==AVI_MODE_WRITE) return 0;   while(1)   {      /* Read tag and length */      if( read(AVI->fdes,data,8) != 8 ) return 0;      /* if we got a list tag, ignore it */      if(strncasecmp(data,"LIST",4) == 0)      {         lseek(AVI->fdes,4,SEEK_CUR);         continue;      }      n = PAD_EVEN(str2ulong(data+4));      if(strncasecmp(data,AVI->video_tag,3) == 0)      {         *len = n;         AVI->video_pos++;         if(n>max_vidbuf)         {            lseek(AVI->fdes,n,SEEK_CUR);            return -1;         }         if(read(AVI->fdes,vidbuf,n) != n ) return 0;         return 1;      }      else if(strncasecmp(data,AVI->audio_tag,4) == 0)      {         *len = n;         if(n>max_audbuf)         {            lseek(AVI->fdes,n,SEEK_CUR);            return -2;         }         if(read(AVI->fdes,audbuf,n) != n ) return 0;         return 2;         break;      }      else         if(lseek(AVI->fdes,n,SEEK_CUR)<0)  return 0;   }}/* AVI_print_error: Print most recent error (similar to perror) */char *(avi_errors[]) ={  /*  0 */ "avilib - No Error",  /*  1 */ "avilib - AVI file size limit reached",  /*  2 */ "avilib - Error opening AVI file",  /*  3 */ "avilib - Error reading from AVI file",  /*  4 */ "avilib - Error writing to AVI file",  /*  5 */ "avilib - Error writing index (file may still be useable)",  /*  6 */ "avilib - Error closing AVI file",  /*  7 */ "avilib - Operation (read/write) not permitted",  /*  8 */ "avilib - Out of memory (malloc failed)",  /*  9 */ "avilib - Not an AVI file",  /* 10 */ "avilib - AVI file has no header list (corrupted?)",  /* 11 */ "avilib - AVI file has no MOVI list (corrupted?)",  /* 12 */ "avilib - AVI file has no video data",  /* 13 */ "avilib - operation needs an index",  /* 14 */ "avilib - Unkown Error"};static int num_avi_errors = sizeof(avi_errors)/sizeof(char*);static char error_string[4096];void AVI_print_error(char *str){   int aerrno;   aerrno = (AVI_errno>=0 && AVI_errno<num_avi_errors) ? AVI_errno : num_avi_errors-1;   fprintf(stderr,"%s: %s\n",str,avi_errors[aerrno]);   /* for the following errors, perror should report a more detailed reason: */   if(AVI_errno == AVI_ERR_OPEN ||      AVI_errno == AVI_ERR_READ ||      AVI_errno == AVI_ERR_WRITE ||      AVI_errno == AVI_ERR_WRITE_INDEX ||      AVI_errno == AVI_ERR_CLOSE )   {      perror("REASON");   }}char *AVI_strerror(){   int aerrno;   aerrno = (AVI_errno>=0 && AVI_errno<num_avi_errors) ? AVI_errno : num_avi_errors-1;   if(AVI_errno == AVI_ERR_OPEN ||      AVI_errno == AVI_ERR_READ ||      AVI_errno == AVI_ERR_WRITE ||      AVI_errno == AVI_ERR_WRITE_INDEX ||      AVI_errno == AVI_ERR_CLOSE )   {      sprintf(error_string,"%s - %s",avi_errors[aerrno],strerror(errno));      return error_string;   }   else   {      return avi_errors[aerrno];   }}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -