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

📄 munitrk.c

📁 wince下著名的视频播放器源码
💻 C
字号:
/*	MikMod sound library	(c) 1998, 1999, 2000, 2001 Miodrag Vallat and others - see file AUTHORS	for complete list.	This library is free software; you can redistribute it and/or modify	it under the terms of the GNU Library General Public License as	published by the Free Software Foundation; either version 2 of	the License, or (at your option) any later version. 	This program is distributed in the hope that it will be useful,	but WITHOUT ANY WARRANTY; without even the implied warranty of	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the	GNU Library General Public License for more details. 	You should have received a copy of the GNU Library General Public	License along with this library; if not, write to the Free Software	Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA	02111-1307, USA.*//*==============================================================================  $Id: munitrk.c,v 1.1.1.1 2004/01/21 01:36:35 raph Exp $  All routines dealing with the manipulation of UNITRK streams==============================================================================*/#ifdef HAVE_CONFIG_H#include "config.h"#endif#include "mikmod_internals.h"#include <string.h>/* Unibuffer chunk size */#define BUFPAGE  128UWORD unioperands[UNI_LAST]={	0, /* not used */	1, /* UNI_NOTE */	1, /* UNI_INSTRUMENT */	1, /* UNI_PTEFFECT0 */	1, /* UNI_PTEFFECT1 */	1, /* UNI_PTEFFECT2 */	1, /* UNI_PTEFFECT3 */	1, /* UNI_PTEFFECT4 */	1, /* UNI_PTEFFECT5 */	1, /* UNI_PTEFFECT6 */	1, /* UNI_PTEFFECT7 */	1, /* UNI_PTEFFECT8 */	1, /* UNI_PTEFFECT9 */	1, /* UNI_PTEFFECTA */	1, /* UNI_PTEFFECTB */	1, /* UNI_PTEFFECTC */	1, /* UNI_PTEFFECTD */	1, /* UNI_PTEFFECTE */	1, /* UNI_PTEFFECTF */	1, /* UNI_S3MEFFECTA */	1, /* UNI_S3MEFFECTD */	1, /* UNI_S3MEFFECTE */	1, /* UNI_S3MEFFECTF */	1, /* UNI_S3MEFFECTI */	1, /* UNI_S3MEFFECTQ */	1, /* UNI_S3MEFFECTR */	1, /* UNI_S3MEFFECTT */	1, /* UNI_S3MEFFECTU */	0, /* UNI_KEYOFF */	1, /* UNI_KEYFADE */	2, /* UNI_VOLEFFECTS */	1, /* UNI_XMEFFECT4 */	1, /* UNI_XMEFFECT6 */	1, /* UNI_XMEFFECTA */	1, /* UNI_XMEFFECTE1 */	1, /* UNI_XMEFFECTE2 */	1, /* UNI_XMEFFECTEA */	1, /* UNI_XMEFFECTEB */	1, /* UNI_XMEFFECTG */	1, /* UNI_XMEFFECTH */	1, /* UNI_XMEFFECTL */	1, /* UNI_XMEFFECTP */	1, /* UNI_XMEFFECTX1 */	1, /* UNI_XMEFFECTX2 */	1, /* UNI_ITEFFECTG */	1, /* UNI_ITEFFECTH */	1, /* UNI_ITEFFECTI */	1, /* UNI_ITEFFECTM */	1, /* UNI_ITEFFECTN */	1, /* UNI_ITEFFECTP */	1, /* UNI_ITEFFECTT */	1, /* UNI_ITEFFECTU */	1, /* UNI_ITEFFECTW */	1, /* UNI_ITEFFECTY */	2, /* UNI_ITEFFECTZ */	1, /* UNI_ITEFFECTS0 */	2, /* UNI_ULTEFFECT9 */	2, /* UNI_MEDSPEED */	0, /* UNI_MEDEFFECTF1 */	0, /* UNI_MEDEFFECTF2 */	0, /* UNI_MEDEFFECTF3 */	2, /* UNI_OKTARP */};/* Sparse description of the internal module format   ------------------------------------------------  A UNITRK stream is an array of bytes representing a single track of a pattern.It's made up of 'repeat/length' bytes, opcodes and operands (sort of a assemblylanguage):rrrlllll[REP/LEN][OPCODE][OPERAND][OPCODE][OPERAND] [REP/LEN][OPCODE][OPERAND]..^                                         ^ ^|-------ROWS 0 - 0+REP of a track---------| |-------ROWS xx - xx+REP of a track...  The rep/len byte contains the number of bytes in the current row, _including_the length byte itself (So the LENGTH byte of row 0 in the previous examplewould have a value of 5). This makes it easy to search through a stream for aparticular row. A track is concluded by a 0-value length byte.  The upper 3 bits of the rep/len byte contain the number of times -1 this rowis repeated for this track. (so a value of 7 means this row is repeated 8 times)  Opcodes can range from 1 to 255 but currently only opcodes 1 to 62 are beingused. Each opcode can have a different number of operands. You can find thenumber of operands to a particular opcode by using the opcode as an index intothe 'unioperands' table.*//*========== Reading routines */static	UBYTE *rowstart; /* startadress of a row */static	UBYTE *rowend;   /* endaddress of a row (exclusive) */static	UBYTE *rowpc;    /* current unimod(tm) programcounter */static	UBYTE lastbyte;  /* for UniSkipOpcode() */void UniSetRow(UBYTE* t){	rowstart = t;	rowpc    = rowstart;	rowend   = t?rowstart+(*(rowpc++)&0x1f):t;}UBYTE UniGetByte(void){	return lastbyte = (rowpc<rowend)?*(rowpc++):0;}UWORD UniGetWord(void){	return ((UWORD)UniGetByte()<<8)|UniGetByte();}void UniSkipOpcode(void){	if (lastbyte < UNI_LAST) {		UWORD t = unioperands[lastbyte];		while (t--)			UniGetByte();	}}/* Finds the address of row number 'row' in the UniMod(tm) stream 't' returns   NULL if the row can't be found. */UBYTE *UniFindRow(UBYTE* t,UWORD row){	UBYTE c,l;	if(t)		while(1) {			c = *t;             /* get rep/len byte */			if(!c) return NULL; /* zero ? -> end of track.. */			l = (c>>5)+1;       /* extract repeat value */			if(l>row) break;    /* reached wanted row? -> return pointer */			row -= l;           /* haven't reached row yet.. update row */			t += c&0x1f;        /* point t to the next row */		}	return t;}/*========== Writing routines */static	UBYTE *unibuf; /* pointer to the temporary unitrk buffer */static	UWORD unimax;  /* buffer size */static	UWORD unipc;   /* buffer cursor */static	UWORD unitt;   /* current row index */static	UWORD lastp;   /* previous row index *//* Resets index-pointers to create a new track. */void UniReset(void){	unitt     = 0;   /* reset index to rep/len byte */	unipc     = 1;   /* first opcode will be written to index 1 */	lastp     = 0;   /* no previous row yet */	unibuf[0] = 0;   /* clear rep/len byte */}/* Expands the buffer */static BOOL UniExpand(int wanted){	if ((unipc+wanted)>=unimax) {		UBYTE *newbuf;		/* Expand the buffer by BUFPAGE bytes */		newbuf=(UBYTE*)realloc(unibuf,(unimax+BUFPAGE)*sizeof(UBYTE));		/* Check if realloc succeeded */		if(newbuf) {			unibuf = newbuf;			unimax+=BUFPAGE;			return 1;		} else 			return 0;	}	return 1;}/* Appends one byte of data to the current row of a track. */void UniWriteByte(UBYTE data){	if (UniExpand(1))		/* write byte to current position and update */		unibuf[unipc++]=data;}void UniWriteWord(UWORD data){	if (UniExpand(2)) {		unibuf[unipc++]=data>>8;		unibuf[unipc++]=data&0xff;	}}static BOOL MyCmp(UBYTE* a,UBYTE* b,UWORD l){	UWORD t;	for(t=0;t<l;t++)		if(*(a++)!=*(b++)) return 0;	return 1;}/* Closes the current row of a unitrk stream (updates the rep/len byte) and sets   pointers to start a new row. */void UniNewline(void){	UWORD n,l,len;	n = (unibuf[lastp]>>5)+1;     /* repeat of previous row */	l = (unibuf[lastp]&0x1f);     /* length of previous row */	len = unipc-unitt;            /* length of current row */	/* Now, check if the previous and the current row are identical.. when they	   are, just increase the repeat field of the previous row */	if(n<8 && len==l && MyCmp(&unibuf[lastp+1],&unibuf[unitt+1],len-1)) {		unibuf[lastp]+=0x20;		unipc = unitt+1;	} else {		if (UniExpand(unitt-unipc)) {			/* current and previous row aren't equal... update the pointers */			unibuf[unitt] = len;			lastp = unitt;			unitt = unipc++;		}	}}/* Terminates the current unitrk stream and returns a pointer to a copy of the   stream. */UBYTE* UniDup(void){	UBYTE *d;	if (!UniExpand(unitt-unipc)) return NULL;	unibuf[unitt] = 0;	if(!(d=(UBYTE *)_mm_malloc(unipc))) return NULL;	memcpy(d,unibuf,unipc);	return d;}BOOL UniInit(void){	unimax = BUFPAGE;	if(!(unibuf=(UBYTE*)_mm_malloc(unimax*sizeof(UBYTE)))) return 0;	return 1;}void UniCleanup(void){	if(unibuf) free(unibuf);	unibuf = NULL;}/* ex:set ts=4: */

⌨️ 快捷键说明

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