Commit 75014c3b authored by Monty's avatar Monty
Browse files

Continuing to flesh out the programmatic API in libvorbis.
Incremental update.

Monty

svn path=/trunk/vorbis/; revision=135
parent 117b96ee
# vorbis makefile configured for use with gcc on any platform
# $Id: Makefile.in,v 1.8 1999/08/09 21:11:38 xiphmont Exp $
# $Id: Makefile.in,v 1.9 1999/10/02 21:21:18 xiphmont Exp $
###############################################################################
# #
......@@ -28,7 +28,7 @@ RANLIB=@RANLIB@
LIBS=@LIBS@ -lm
OFILES = framing.o mdct.o smallft.o block.o envelope.o window.o\
lsp.o lpc.o analysis.o synthesis.o psy.o
lsp.o lpc.o analysis.o synthesis.o psy.o info.o bitwise.o
TARGETFILES = libvorbis.a
all:
......
......@@ -14,7 +14,7 @@
function: single-block PCM analysis
author: Monty <xiphmont@mit.edu>
modifications by: Monty
last modification date: Aug 22 1999
last modification date: Oct 2 1999
********************************************************************/
......@@ -30,7 +30,7 @@
extern void compute_balance(double *A, double *B, double *phi,int n);
int vorbis_analysis(vorbis_block *vb){
int vorbis_analysis(vorbis_block *vb,ogg_packet *op){
int i;
double *window=vb->vd->window[vb->W][vb->lW][vb->nW];
lpc_lookup *vl=&vb->vd->vl[vb->W];
......@@ -231,20 +231,3 @@ int vorbis_analysis(vorbis_block *vb){
return(0);
}
int vorbis_analysis_packetout(vorbis_block *vb, ogg_packet *op){
/* find block's envelope vector and apply it */
/* the real analysis begins; forward MDCT with window */
/* Noise floor, resolution floor */
/* encode the floor into LSP; get the actual floor back for quant */
/* use noise floor, res floor for culling, actual floor for quant */
/* encode residue */
}
......@@ -14,7 +14,7 @@
function: PCM data vector blocking, windowing and dis/reassembly
author: Monty <xiphmont@mit.edu>
modifications by: Monty
last modification date: Aug 05 1999
last modification date: Oct 2 1999
Handle windowing, overlap-add, etc of the PCM vectors. This is made
more amusing by Vorbis' current two allowed block sizes.
......@@ -70,6 +70,59 @@
|beginW
*/
/* block abstraction setup *********************************************/
int vorbis_block_init(vorbis_dsp_state *v, vorbis_block *vb){
int i;
memset(vb,0,sizeof(vorbis_block));
vb->vd=v;
vb->pcm_storage=v->block_size[1];
vb->pcm_channels=v->pcm_channels;
vb->mult_storage=v->block_size[1]/v->samples_per_envelope_step;
vb->mult_channels=v->envelope_channels;
vb->floor_channels=v->vi.floorch;
vb->floor_storage=v->vi.floororder;
vb->pcm=malloc(vb->pcm_channels*sizeof(double *));
for(i=0;i<vb->pcm_channels;i++)
vb->pcm[i]=malloc(vb->pcm_storage*sizeof(double));
vb->mult=malloc(vb->mult_channels*sizeof(double *));
for(i=0;i<vb->mult_channels;i++)
vb->mult[i]=malloc(vb->mult_storage*sizeof(double));
vb->lsp=malloc(vb->floor_channels*sizeof(double *));
vb->lpc=malloc(vb->floor_channels*sizeof(double *));
vb->amp=malloc(vb->floor_channels*sizeof(double));
for(i=0;i<vb->floor_channels;i++){
vb->lsp[i]=malloc(vb->floor_storage*sizeof(double));
vb->lpc[i]=malloc(vb->floor_storage*sizeof(double));
}
return(0);
}
int vorbis_block_clear(vorbis_block *vb){
int i;
if(vb->pcm){
for(i=0;i<vb->pcm_channels;i++)
free(vb->pcm[i]);
free(vb->pcm);
}
if(vb->mult){
for(i=0;i<vb->mult_channels;i++)
free(vb->mult[i]);
free(vb->mult);
}
memset(vb,0,sizeof(vorbis_block));
return(0);
}
/* Analysis side code, but directly related to blocking. Thus it's
here and not in analysis.c (which is for analysis transforms only).
The init is here because some of it is shared */
static int _vds_shared_init(vorbis_dsp_state *v,vorbis_info *vi){
memset(v,0,sizeof(vorbis_dsp_state));
......@@ -233,51 +286,6 @@ int vorbis_analysis_wrote(vorbis_dsp_state *v, int vals){
return(0);
}
int vorbis_block_init(vorbis_dsp_state *v, vorbis_block *vb){
int i;
memset(vb,0,sizeof(vorbis_block));
vb->pcm_storage=v->block_size[1];
vb->pcm_channels=v->pcm_channels;
vb->mult_storage=v->block_size[1]/v->samples_per_envelope_step;
vb->mult_channels=v->envelope_channels;
vb->floor_channels=v->vi.floorch;
vb->floor_storage=v->vi.floororder;
vb->pcm=malloc(vb->pcm_channels*sizeof(double *));
for(i=0;i<vb->pcm_channels;i++)
vb->pcm[i]=malloc(vb->pcm_storage*sizeof(double));
vb->mult=malloc(vb->mult_channels*sizeof(double *));
for(i=0;i<vb->mult_channels;i++)
vb->mult[i]=malloc(vb->mult_storage*sizeof(double));
vb->lsp=malloc(vb->floor_channels*sizeof(double *));
vb->lpc=malloc(vb->floor_channels*sizeof(double *));
vb->amp=malloc(vb->floor_channels*sizeof(double));
for(i=0;i<vb->floor_channels;i++){
vb->lsp[i]=malloc(vb->floor_storage*sizeof(double));
vb->lpc[i]=malloc(vb->floor_storage*sizeof(double));
}
return(0);
}
int vorbis_block_clear(vorbis_block *vb){
int i;
if(vb->pcm){
for(i=0;i<vb->pcm_channels;i++)
free(vb->pcm[i]);
free(vb->pcm);
}
if(vb->mult){
for(i=0;i<vb->mult_channels;i++)
free(vb->mult[i]);
free(vb->mult);
}
memset(vb,0,sizeof(vorbis_block));
return(0);
}
/* do the deltas, envelope shaping, pre-echo and determine the size of
the next block on which to continue analysis */
int vorbis_analysis_blockout(vorbis_dsp_state *v,vorbis_block *vb){
......
......@@ -14,13 +14,15 @@
function: codec headers
author: Monty <xiphmont@mit.edu>
modifications by: Monty
last modification date: Aug 21 1999
last modification date: Oct 2 1999
********************************************************************/
#ifndef _vorbis_codec_h_
#define _vorbis_codec_h_
/* lookup structures for various simple transforms *****************/
typedef struct {
int n;
int log2n;
......@@ -56,6 +58,7 @@ typedef struct lpclook{
} lpc_lookup;
/* structures for various internal data abstractions ********************/
typedef struct {
long endbyte;
......@@ -67,25 +70,28 @@ typedef struct {
} oggpack_buffer;
/* vobis_info contains all the setup information specific to the specific
compression/decompression mode in progress (eg, psychoacoustic settings,
channel setup, options, codebook etc) *********************************/
typedef struct vorbis_info{
int channels;
int rate;
int version;
int mode;
char **user_comments;
int max_comment;
char *vendor;
int smallblock;
int largeblock;
int envelopesa;
int envelopech;
int *envelopemap; /* which envelope applies to what pcm channel */
int **Echannelmap; /* which encoding channels produce what pcm (decode) */
int **channelmap; /* which pcm channels produce what floors (encode) */
int floororder;
int flooroctaves;
int floorch;
int *floormap;
/* no mapping, copuling, balance yet. */
int balanceorder;
int balanceoctaves;
......@@ -94,6 +100,8 @@ typedef struct vorbis_info{
double preecho_clamp;
} vorbis_info;
/* ogg_page is used to encapsulate the data in one Ogg bitstream page *****/
typedef struct {
unsigned char *header;
long header_len;
......@@ -101,6 +109,9 @@ typedef struct {
long body_len;
} ogg_page;
/* ogg_stream_state contains the current encode/decode state of a logical
Ogg bitstream **********************************************************/
typedef struct {
unsigned char *body_data; /* bytes from packet bodies */
long body_storage; /* storage elements allocated */
......@@ -130,6 +141,9 @@ typedef struct {
} ogg_stream_state;
/* ogg_packet is used to encapsulate the data and metadata belonging
to a single raw Ogg/Vorbis packet *************************************/
typedef struct {
unsigned char *packet;
long bytes;
......@@ -151,6 +165,10 @@ typedef struct {
int bodybytes;
} ogg_sync_state;
/* vorbis_dsp_state buffers the current vorbis audio
analysis/synthesis state. The DSP state belongs to a specific
logical bitstream ****************************************************/
typedef struct vorbis_dsp_state{
int samples_per_envelope_step;
int block_size[2];
......@@ -187,6 +205,11 @@ typedef struct vorbis_dsp_state{
} vorbis_dsp_state;
/* vorbis_block is a single block of data to be processed as part of
the analysis/synthesis stream; it belongs to a specific logical
bitstream, but is independant from other vorbis_blocks belonging to
that logical bitstream. *************************************************/
typedef struct vorbis_block{
double **pcm;
double **mult;
......@@ -194,8 +217,8 @@ typedef struct vorbis_block{
double **lsp;
double *amp;
int pcm_channels; /* allocated, not used */
int pcm_storage; /* allocated, not used */
int pcm_channels; /* allocated, not used */
int pcm_storage; /* allocated, not used */
int mult_channels; /* allocated, not used */
int mult_storage; /* allocated, not used */
int floor_channels;
......@@ -258,33 +281,35 @@ extern size64 ogg_page_frameno(ogg_page *og);
extern int ogg_page_serialno(ogg_page *og);
extern int ogg_page_pageno(ogg_page *og);
/* Vorbis PRIMITIVES: general ***************************************/
extern int vorbis_info_clear(vorbis_info *vi);
extern int vorbis_info_modeset(vorbis_info *vi, int mode);
extern int vorbis_info_addcomment(vorbis_info *vi, char *comment);
extern int vorbis_info_headerin(vorbis_info *vi,ogg_packet *op);
extern int vorbis_info_headerout(vorbis_info *vi,ogg_packet *op);
extern int vorbis_block_init(vorbis_dsp_state *v, vorbis_block *vb);
extern int vorbis_block_clear(vorbis_block *vb);
/* Vorbis PRIMITIVES: analysis/DSP layer ****************************/
extern int vorbis_analysis_init(vorbis_dsp_state *v,vorbis_info *vi);
extern void vorbis_analysis_clear(vorbis_dsp_state *v);
extern int vorbis_analysis_init(vorbis_dsp_state *vd,vorbis_info *vi);
extern int vorbis_analysis_reset(vorbis_dsp_state *vd);
extern void vorbis_analysis_free(vorbis_dsp_state *vd);
extern double **vorbis_analysis_buffer(vorbis_dsp_state *vd,int vals);
extern int vorbis_analysis_wrote(vorbis_dsp_state *vd,int vals);
extern int vorbis_analysis_blockout(vorbis_dsp_state *vd,
vorbis_block *vb);
extern int vorbis_analysis(vorbis_block *vb);
extern int vorbis_analysis_packetout(vorbis_block *vb,
ogg_packet *op);
extern double **vorbis_analysis_buffer(vorbis_dsp_state *v,int vals);
extern int vorbis_analysis_wrote(vorbis_dsp_state *v,int vals);
extern int vorbis_analysis_blockout(vorbis_dsp_state *v,vorbis_block *vb);
extern int vorbis_analysis(vorbis_block *vb,ogg_packet *op);
/* Vorbis PRIMITIVES: synthesis layer *******************************/
extern int vorbis_synthesis_clear(vorbis_dsp_state *v);
extern int vorbis_synthesis_init(vorbis_dsp_state *v,vorbis_info *vi);
extern void vorbis_synthesis_free(vorbis_dsp_state *vd);
extern int vorbis_synthesis_init(vorbis_dsp_state *vd,vorbis_info *vi);
extern int vorbis_synthesis(vorbis_block *vb);
extern int vorbis_synthesis(vorbis_block *vb,ogg_packet *op);
extern int vorbis_synthesis_blockin(vorbis_dsp_state *v,vorbis_block *vb);
extern int vorbis_synthesis_pcmout(vorbis_dsp_state *v,double ***pcm);
extern int vorbis_synthesis_read(vorbis_dsp_state *v,int bytes);
extern int vorbis_block_init(vorbis_dsp_state *v, vorbis_block *vb);
#define min(x,y) ((x)>(y)?(y):(x))
#define max(x,y) ((x)<(y)?(y):(x))
#define todB(x) (x==0?-9.e40:log(fabs(x))*8.6858896) /* 20log10(x) */
......
......@@ -72,6 +72,7 @@ int main(){
/* analysis */
vorbis_analysis(&vb);
vorbis_analysis_packetout(&vb,&op);
/* synthesis */
......
......@@ -14,7 +14,7 @@
function: PCM data envelope analysis and manipulation
author: Monty <xiphmont@mit.edu>
modifications by: Monty
last modification date: Aug 07 1999
last modification date: Oct 02 1999
Vorbis manipulates the dynamic range of the incoming PCM data
envelope to minimise time-domain energy leakage from percussive and
......@@ -139,7 +139,8 @@ void _ve_envelope_multipliers(vorbis_dsp_state *v){
for(pch=0;pch<vi->channels;pch++){
/* does this channel contribute to the envelope analysis */
if(vi->envelopemap[pch]==ech){
/*if(vi->envelopemap[pch]==ech){ not mapping yet */
if(pch==ech){
/* we need a 1/4 envelope window overlap front and back */
double *pcm=v->pcm[pch]+dcurr*step-step/2;
......@@ -233,7 +234,8 @@ void _ve_envelope_apply(vorbis_block *vb,int multp){
for(j=0;j<vi->channels;j++){
/* check to see if the generated envelope applies to this channel */
if(vi->envelopemap[j]==i){
/*if(vi->envelopemap[j]==i){ not mapping yet */
if(j==i){
if(multp)
for(k=0;k<vb->multend*vi->envelopesa;k++)
......
/********************************************************************
* *
* THIS FILE IS PART OF THE Ogg Vorbis SOFTWARE CODEC SOURCE CODE. *
* USE, DISTRIBUTION AND REPRODUCTION OF THIS SOURCE IS GOVERNED BY *
* THE GNU PUBLIC LICENSE 2, WHICH IS INCLUDED WITH THIS SOURCE. *
* PLEASE READ THESE TERMS DISTRIBUTING. *
* *
* THE OggSQUISH SOURCE CODE IS (C) COPYRIGHT 1994-1999 *
* by 1999 Monty <monty@xiph.org> and The XIPHOPHORUS Company *
* http://www.xiph.org/ *
* *
********************************************************************
function: maintain the info structure, info <-> header packets
author: Monty <xiphmont@mit.edu>
modifications by: Monty
last modification date: Oct 02 1999
********************************************************************/
/* This fills in a vorbis_info structure with settings from a few
pre-defined encoding modes. Also handles choosing/blowing in the
codebook */
#include <stdlib.h>
#include <string.h>
#include "modes.h"
/* one test mode for now; temporary of course */
int vorbis_info_modeset(vorbis_info *vi, int mode){
if(mode<0 || mode>predef_mode_max)return(-1);
/* handle the flat settings first */
memcpy(vi,&(predef_modes[mode]),sizeof(vorbis_info));
vi->user_comments=calloc(1,sizeof(char *));
return(0);
}
/* convenience function */
int vorbis_info_add_comment(vorbis_info *vi,char *comment){
vi->user_comments=realloc(vi->user_comments,
(vi->max_comment+2)*sizeof(char *));
vi->user_comments[vi->max_comment]=strdup(comment);
vi->max_comment++;
vi->user_comments[vi->max_comment]=NULL;
return(0);
}
/* The Vorbis header is in three packets; the initial small packet in
the first page that identifies basic parameters, a second
[optional] packet with bitstream comments and a third packet that
holds the codebook. */
int vorbis_info_headerin(vorbis_info *vi,ogg_packet *op){
}
int vorbis_info_headerout(vorbis_info *vi,ogg_packet *op){
}
int vorbis_info_clear(vorbis_info *vi){
/* clear the non-flat storage before zeroing */
/* comments */
if(vi->user_comments){
char **ptr=vi->user_comments;
while(*ptr){
free(*(ptr++));
}
free(vi->user_comments);
}
/* vendor string */
if(vi->vendor)free(vi->vendor);
memset(vi,0,sizeof(vorbis_info));
}
/********************************************************************
* *
* THIS FILE IS PART OF THE Ogg Vorbis SOFTWARE CODEC SOURCE CODE. *
* USE, DISTRIBUTION AND REPRODUCTION OF THIS SOURCE IS GOVERNED BY *
* THE GNU PUBLIC LICENSE 2, WHICH IS INCLUDED WITH THIS SOURCE. *
* PLEASE READ THESE TERMS DISTRIBUTING. *
* *
* THE OggSQUISH SOURCE CODE IS (C) COPYRIGHT 1994-1999 *
* by 1999 Monty <monty@xiph.org> and The XIPHOPHORUS Company *
* http://www.xiph.org/ *
* *
********************************************************************
function: predefined encoding modes
author: Monty <xiphmont@mit.edu>
modifications by: Monty
last modification date: Oct 2 1999
********************************************************************/
#ifndef _V_MODES_H_
#define _V_MODES_H_
#include <stdio.h>
#include "codec.h"
vorbis_info predef_modes[]={
/* CD quality stereo, no channel coupling */
{ 2, 44100, 0, NULL, 0, NULL, 512, 2048, 64, 2, 30, 5, 2, 0, 0, 10, .5 },
};
#define predef_mode_max 0
#endif
......@@ -24,7 +24,7 @@
#include "lpc.h"
#include "lsp.h"
int vorbis_synthesis(vorbis_block *vb){
int vorbis_synthesis(vorbis_block *vb,ogg_packet *op){
int i;
vorbis_info *vi=&vb->vd->vi;
double *window=vb->vd->window[vb->W][vb->lW][vb->nW];
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment