Beispiel #1
0
void
encoder_progress( lame_global_flags const* gf )
{
    if (global_ui_config.silent <= 0) {
        int const frames = lame_get_frameNum(gf);
        int const frames_diff = frames - global_encoder_progress.last_frame_num;
        if (global_ui_config.update_interval <= 0) {     /*  most likely --disptime x not used */
            if (frames_diff < 100 && frames_diff != 0) {  /*  true, most of the time */
                return;
            }
            global_encoder_progress.last_frame_num = (frames/100)*100;
        }
        else {
            if (frames != 0 && frames != 9) {
                double const act = GetRealTime();
                double const dif = act - global_encoder_progress.last_time;
                if (dif >= 0 && dif < global_ui_config.update_interval) {
                    return;
                }
            }
            global_encoder_progress.last_time = GetRealTime(); /* from now! disp_time seconds */
        }
        if (global_ui_config.brhist) {
            brhist_jump_back();
        }
        timestatus(gf);
        if (global_ui_config.brhist) {
            brhist_disp(gf);
        }
        console_flush();
    }
}
Beispiel #2
0
int lame_encode_finish(lame_global_flags *gfp,char *mp3buffer, int mp3buffer_size)
{
  int imp3,mp3count,mp3buffer_size_remaining;
  short int buffer[2][1152];
  memset((char *)buffer,0,sizeof(buffer));
  mp3count = 0;

  while (mf_samples_to_encode > 0) {

    mp3buffer_size_remaining = mp3buffer_size - mp3count;
    /* if user specifed buffer size = 0, dont check size */
    if (mp3buffer_size == 0) mp3buffer_size_remaining=0;  
    imp3=lame_encode(gfp,buffer,mp3buffer,mp3buffer_size_remaining);

    if (imp3 == -1) {
      /* fatel error: mp3buffer too small */
      desalloc_buffer(&bs);    /* Deallocate all buffers */
      return -1;
    }
    mp3buffer += imp3;
    mp3count += imp3;
    mf_samples_to_encode -= gfp->framesize;
  }


  gfp->frameNum--;
  if (!gfp->gtkflag && !gfp->silent) {
      timestatus(gfp->out_samplerate,gfp->frameNum,gfp->totalframes,gfp->framesize);
#ifdef BRHIST
      if (disp_brhist)
	{
	  brhist_add_count();
	  brhist_disp();
	  brhist_disp_total(gfp);
	}
#endif
      fprintf(stderr,"\n");
      fflush(stderr);
  }


  III_FlushBitstream();
  mp3buffer_size_remaining = mp3buffer_size - mp3count;
  /* if user specifed buffer size = 0, dont check size */
  if (mp3buffer_size == 0) mp3buffer_size_remaining=0;  

  imp3= copy_buffer(mp3buffer,mp3buffer_size_remaining,&bs);
  if (imp3 == -1) {
    /* fatel error: mp3buffer too small */
    desalloc_buffer(&bs);    /* Deallocate all buffers */
    return -1;
  }

  mp3count += imp3;
  desalloc_buffer(&bs);    /* Deallocate all buffers */
  return mp3count;
}
Beispiel #3
0
void
encoder_progress_end( lame_global_flags const* gf )
{
    if (global_ui_config.silent <= 0) {
        if (global_ui_config.brhist) {
            brhist_jump_back();
        }
        timestatus(gf);
        if (global_ui_config.brhist) {
            brhist_disp(gf);
        }
        timestatus_finish();
    }
}
Beispiel #4
0
void timestatus_klemm ( const lame_global_flags* const gfp )
{
    static double  last_time = 0.;

    if ( silent <= 0 )
        if ( lame_get_frameNum(gfp) == 0  ||  
  	     lame_get_frameNum(gfp) == 9  ||
  	     GetRealTime () - last_time >= update_interval  ||
	     GetRealTime () - last_time <  0 ) {
#ifdef BRHIST
            brhist_jump_back();
#endif
            timestatus ( lame_get_out_samplerate( gfp ),
                         lame_get_frameNum(gfp),
                         lame_get_totalframes(gfp),
                         lame_get_framesize(gfp) );
#ifdef BRHIST
            if ( brhist ) {
	        brhist_disp ( gfp );
	    }
#endif
            last_time = GetRealTime ();  /* from now! disp_time seconds */
        }
}
Beispiel #5
0
int
lame_encoder(lame_global_flags * gf, FILE * outf, int nogap, char *inPath,
             char *outPath)
{
    unsigned char mp3buffer[LAME_MAXMP3BUFFER];
    int     Buffer[2][1152];
    int     iread, imp3;
    static const char *mode_names[2][4] = {
        {"stereo", "j-stereo", "dual-ch", "single-ch"},
        {"stereo", "force-ms", "dual-ch", "single-ch"}
    };
    int     frames;

    if (silent < 10) {
        lame_print_config(gf); /* print useful information about options being used */

        fprintf(stderr, "Encoding %s%s to %s\n",
                strcmp(inPath, "-") ? inPath : "<stdin>",
                strlen(inPath) + strlen(outPath) < 66 ? "" : "\n     ",
                strcmp(outPath, "-") ? outPath : "<stdout>");

        fprintf(stderr,
                "Encoding as %g kHz ", 1.e-3 * lame_get_out_samplerate(gf));

	{
            const char *appendix = "";

            switch (lame_get_VBR(gf)) {
            case vbr_mt:
            case vbr_rh:
            case vbr_mtrh:
                appendix = "ca. ";
                fprintf(stderr, "VBR(q=%i)", lame_get_VBR_q(gf));
                break;
            case vbr_abr:
                fprintf(stderr, "average %d kbps",
                        lame_get_VBR_mean_bitrate_kbps(gf));
                break;
            default:
                fprintf(stderr, "%3d kbps", lame_get_brate(gf));
                break;
            }
            fprintf(stderr, " %s MPEG-%u%s Layer III (%s%gx) qval=%i\n",
                    mode_names[lame_get_force_ms(gf)][lame_get_mode(gf)],
                    2 - lame_get_version(gf),
                    lame_get_out_samplerate(gf) < 16000 ? ".5" : "",
                    appendix,
                    0.1 * (int) (10. * lame_get_compression_ratio(gf) + 0.5),
                    lame_get_quality(gf));
        }

        if (silent <= -10)
            lame_print_internals(gf);

        fflush(stderr);
    }


    /* encode until we hit eof */
    do {
        /* read in 'iread' samples */
        iread = get_audio(gf, Buffer);
        frames = lame_get_frameNum(gf);


 /********************** status display  *****************************/
        if (silent <= 0) {
            if (update_interval > 0) {
                timestatus_klemm(gf);
            }
            else {
                if (0 == frames % 50) {
#ifdef BRHIST
                    brhist_jump_back();
#endif
                    timestatus(lame_get_out_samplerate(gf),
                               frames,
                               lame_get_totalframes(gf),
                               lame_get_framesize(gf));
#ifdef BRHIST
                    if (brhist)
                        brhist_disp(gf);
#endif
                }
            }
        }

        /* encode */
        imp3 = lame_encode_buffer_int(gf, Buffer[0], Buffer[1], iread,
                                      mp3buffer, sizeof(mp3buffer));

        /* was our output buffer big enough? */
        if (imp3 < 0) {
            if (imp3 == -1)
                fprintf(stderr, "mp3 buffer is not big enough... \n");
            else
                fprintf(stderr, "mp3 internal error:  error code=%i\n", imp3);
            return 1;
        }

        if (fwrite(mp3buffer, 1, imp3, outf) != imp3) {
            fprintf(stderr, "Error writing mp3 output \n");
            return 1;
        }

    } while (iread);

    if (nogap) 
        imp3 = lame_encode_flush_nogap(gf, mp3buffer, sizeof(mp3buffer)); /* may return one more mp3 frame */
    else
        imp3 = lame_encode_flush(gf, mp3buffer, sizeof(mp3buffer)); /* may return one more mp3 frame */

    if (imp3 < 0) {
        if (imp3 == -1)
            fprintf(stderr, "mp3 buffer is not big enough... \n");
        else
            fprintf(stderr, "mp3 internal error:  error code=%i\n", imp3);
        return 1;

    }

    if (silent <= 0) {
#ifdef BRHIST
        brhist_jump_back();
#endif
        frames = lame_get_frameNum(gf);
        timestatus(lame_get_out_samplerate(gf),
                   frames, lame_get_totalframes(gf), lame_get_framesize(gf));
#ifdef BRHIST
        if (brhist) {
            brhist_disp(gf);
        }
        brhist_disp_total(gf);
#endif
        timestatus_finish();
    }

    fwrite(mp3buffer, 1, imp3, outf);

    return 0;
}
Beispiel #6
0
/************************************************************************
*
* encodeframe()           Layer 3
*
* encode a single frame
*
************************************************************************
lame_encode_frame()


                       gr 0            gr 1
inbuf:           |--------------|---------------|-------------|
MDCT output:  |--------------|---------------|-------------|

FFT's                    <---------1024---------->
                                         <---------1024-------->



    inbuf = buffer of PCM data size=MP3 framesize
    encoder acts on inbuf[ch][0], but output is delayed by MDCTDELAY
    so the MDCT coefficints are from inbuf[ch][-MDCTDELAY]

    psy-model FFT has a 1 granule day, so we feed it data for the next granule.
    FFT is centered over granule:  224+576+224
    So FFT starts at:   576-224-MDCTDELAY

    MPEG2:  FFT ends at:  BLKSIZE+576-224-MDCTDELAY
    MPEG1:  FFT ends at:  BLKSIZE+2*576-224-MDCTDELAY    (1904)

    FFT starts at 576-224-MDCTDELAY (304)  = 576-FFTOFFSET

*/
int lame_encode_frame(lame_global_flags *gfp,
short int inbuf_l[],short int inbuf_r[],
int mf_size,char *mp3buf, int mp3buf_size)
{
  static unsigned long frameBits;
  static unsigned long bitsPerSlot;
  static FLOAT8 frac_SpF;
  static FLOAT8 slot_lag;
  static unsigned long sentBits = 0;
  FLOAT8 xr[2][2][576];
  int l3_enc[2][2][576];
  int mp3count;
  III_psy_ratio masking_ratio[2][2];    /*LR ratios */
  III_psy_ratio masking_MS_ratio[2][2]; /*MS ratios */
  III_psy_ratio (*masking)[2][2];  /*LR ratios and MS ratios*/
  III_scalefac_t scalefac[2][2];
  short int *inbuf[2];

  typedef FLOAT8 pedata[2][2];
  pedata pe,pe_MS;
  pedata *pe_use;

  int ch,gr,mean_bits;
  int bitsPerFrame;

  int check_ms_stereo;
  static FLOAT8 ms_ratio[2]={0,0};
  FLOAT8 ms_ratio_next=0;
  FLOAT8 ms_ratio_prev=0;
  static FLOAT8 ms_ener_ratio[2]={0,0};

  memset((char *) masking_ratio, 0, sizeof(masking_ratio));
  memset((char *) masking_MS_ratio, 0, sizeof(masking_MS_ratio));
  memset((char *) scalefac, 0, sizeof(scalefac));
  inbuf[0]=inbuf_l;
  inbuf[1]=inbuf_r;

  gfp->mode_ext = MPG_MD_LR_LR;

  if (gfp->frameNum==0 )  {
    /* Figure average number of 'slots' per frame. */
    FLOAT8 avg_slots_per_frame;
    FLOAT8 sampfreq =   gfp->out_samplerate/1000.0;
    int bit_rate = gfp->brate;
    sentBits = 0;
    bitsPerSlot = 8;
    avg_slots_per_frame = (bit_rate*gfp->framesize) /
           (sampfreq* bitsPerSlot);
    /* -f fast-math option causes some strange rounding here, be carefull: */
    frac_SpF  = avg_slots_per_frame - floor(avg_slots_per_frame + 1e-9);
    if (fabs(frac_SpF) < 1e-9) frac_SpF = 0;

    slot_lag  = -frac_SpF;
    gfp->padding = 1;
    if (frac_SpF==0) gfp->padding = 0;
    /* check FFT will not use a negative starting offset */
    assert(576>=FFTOFFSET);
    /* check if we have enough data for FFT */
    assert(mf_size>=(BLKSIZE+gfp->framesize-FFTOFFSET));
  }


  /********************** padding *****************************/
  switch (gfp->padding_type) {
  case 0:
    gfp->padding=0;
    break;
  case 1:
    gfp->padding=1;
    break;
  case 2:
  default:
    if (gfp->VBR) {
      gfp->padding=0;
    } else {
      if (gfp->disable_reservoir) {
	gfp->padding = 0;
	/* if the user specified --nores, dont very gfp->padding either */
	/* tiny changes in frac_SpF rounding will cause file differences */
      }else{
	if (frac_SpF != 0) {
	  if (slot_lag > (frac_SpF-1.0) ) {
	    slot_lag -= frac_SpF;
	    gfp->padding = 0;
	  }
	  else {
	    gfp->padding = 1;
	    slot_lag += (1-frac_SpF);
	  }
	}
      }
    }
  }


  /********************** status display  *****************************/
  if (!gfp->gtkflag && !gfp->silent) {
    int mod = gfp->version == 0 ? 200 : 50;
    if (gfp->frameNum%mod==0) {
      timestatus(gfp->out_samplerate,gfp->frameNum,gfp->totalframes,gfp->framesize);
#ifdef BRHIST
      if (disp_brhist)
	{
	  brhist_add_count();
	  brhist_disp();
	}
#endif
    }
  }


  if (gfp->psymodel) {
    /* psychoacoustic model
     * psy model has a 1 granule (576) delay that we must compensate for
     * (mt 6/99).
     */
    short int *bufp[2];  /* address of beginning of left & right granule */
    int blocktype[2];

    ms_ratio_prev=ms_ratio[gfp->mode_gr-1];
    for (gr=0; gr < gfp->mode_gr ; gr++) {

      for ( ch = 0; ch < gfp->stereo; ch++ )
	bufp[ch] = &inbuf[ch][576 + gr*576-FFTOFFSET];

      L3psycho_anal( gfp,bufp, gr, 
		     &ms_ratio[gr],&ms_ratio_next,&ms_ener_ratio[gr],
		     masking_ratio, masking_MS_ratio,
		     pe[gr],pe_MS[gr],blocktype);

      for ( ch = 0; ch < gfp->stereo; ch++ )
	l3_side.gr[gr].ch[ch].tt.block_type=blocktype[ch];

    }
  }else{
    for (gr=0; gr < gfp->mode_gr ; gr++)
      for ( ch = 0; ch < gfp->stereo; ch++ ) {
	l3_side.gr[gr].ch[ch].tt.block_type=NORM_TYPE;
	pe[gr][ch]=700;
      }
  }


  /* block type flags */
  for( gr = 0; gr < gfp->mode_gr; gr++ ) {
    for ( ch = 0; ch < gfp->stereo; ch++ ) {
      gr_info *cod_info = &l3_side.gr[gr].ch[ch].tt;
      cod_info->mixed_block_flag = 0;     /* never used by this model */
      if (cod_info->block_type == NORM_TYPE )
	cod_info->window_switching_flag = 0;
      else
	cod_info->window_switching_flag = 1;
    }
  }

  /* polyphase filtering / mdct */
  mdct_sub48(gfp,inbuf[0], inbuf[1], xr, &l3_side);

  /* use m/s gfp->stereo? */
  check_ms_stereo =  (gfp->mode == MPG_MD_JOINT_STEREO);
  if (check_ms_stereo) {
    /* make sure block type is the same in each channel */
    check_ms_stereo =
      (l3_side.gr[0].ch[0].tt.block_type==l3_side.gr[0].ch[1].tt.block_type) &&
      (l3_side.gr[1].ch[0].tt.block_type==l3_side.gr[1].ch[1].tt.block_type);
  }
  if (check_ms_stereo) {
    /* ms_ratio = is like the ratio of side_energy/total_energy */
    FLOAT8 ms_ratio_ave,ms_ener_ratio_ave;
    /*     ms_ratio_ave = .5*(ms_ratio[0] + ms_ratio[1]);*/
    ms_ratio_ave = .25*(ms_ratio[0] + ms_ratio[1]+
			 ms_ratio_prev + ms_ratio_next);
    ms_ener_ratio_ave = .5*(ms_ener_ratio[0]+ms_ener_ratio[1]);
    if ( ms_ratio_ave <.35 /*&& ms_ener_ratio_ave<.75*/ ) gfp->mode_ext = MPG_MD_MS_LR;
  }
  if (gfp->force_ms) gfp->mode_ext = MPG_MD_MS_LR;


#ifdef HAVEGTK
  if (gfp->gtkflag) {
    int j;
    for ( gr = 0; gr < gfp->mode_gr; gr++ ) {
      for ( ch = 0; ch < gfp->stereo; ch++ ) {
	pinfo->ms_ratio[gr]=ms_ratio[gr];
	pinfo->ms_ener_ratio[gr]=ms_ener_ratio[gr];
	pinfo->blocktype[gr][ch]=
	  l3_side.gr[gr].ch[ch].tt.block_type;
	for ( j = 0; j < 576; j++ ) pinfo->xr[gr][ch][j]=xr[gr][ch][j];
	/* if MS stereo, switch to MS psy data */
	if (gfp->mode_ext==MPG_MD_MS_LR) {
	  pinfo->pe[gr][ch]=pinfo->pe[gr][ch+2];
	  pinfo->ers[gr][ch]=pinfo->ers[gr][ch+2];
	  memcpy(pinfo->energy[gr][ch],pinfo->energy[gr][ch+2],
		 sizeof(pinfo->energy[gr][ch]));
	}
      }
    }
  }
#endif




  /* bit and noise allocation */
  if (MPG_MD_MS_LR == gfp->mode_ext) {
    masking = &masking_MS_ratio;    /* use MS masking */
    pe_use=&pe_MS;
  } else {
    masking = &masking_ratio;    /* use LR masking */
    pe_use=&pe;
  }


  /*
  VBR_iteration_loop_new( gfp,*pe_use, ms_ratio, xr, masking, &l3_side, l3_enc,
  	  &scalefac);
  */


  if (gfp->VBR) {
    VBR_iteration_loop( gfp,*pe_use, ms_ratio, xr, *masking, &l3_side, l3_enc,
			scalefac);
  }else{
    iteration_loop( gfp,*pe_use, ms_ratio, xr, *masking, &l3_side, l3_enc,
		    scalefac);
  }




#ifdef BRHIST
  brhist_temp[gfp->bitrate_index]++;
#endif


  /*  write the frame to the bitstream  */
  getframebits(gfp,&bitsPerFrame,&mean_bits);
  III_format_bitstream( gfp,bitsPerFrame, l3_enc, &l3_side,
			scalefac, &bs);


  frameBits = bs.totbit - sentBits;


  if ( frameBits % bitsPerSlot )   /* a program failure */
    fprintf( stderr, "Sent %ld bits = %ld slots plus %ld\n",
	     frameBits, frameBits/bitsPerSlot,
	     frameBits%bitsPerSlot );
  sentBits += frameBits;

  /* copy mp3 bit buffer into array */
  mp3count = copy_buffer(mp3buf,mp3buf_size,&bs);

  if (gfp->bWriteVbrTag) AddVbrFrame((int)(sentBits/8));

#ifdef HAVEGTK
  if (gfp->gtkflag) {
    int j;
    for ( ch = 0; ch < gfp->stereo; ch++ ) {
      for ( j = 0; j < FFTOFFSET; j++ )
	pinfo->pcmdata[ch][j] = pinfo->pcmdata[ch][j+gfp->framesize];
      for ( j = FFTOFFSET; j < 1600; j++ ) {
	pinfo->pcmdata[ch][j] = inbuf[ch][j-FFTOFFSET];
      }
    }
  }
#endif
  gfp->frameNum++;

  return mp3count;
}