--- /dev/null
+/* MikMod sound library\r
+ (c) 1998, 1999, 2000 Miodrag Vallat and others - see file AUTHORS for\r
+ complete list.\r
+\r
+ This library is free software; you can redistribute it and/or modify\r
+ it under the terms of the GNU Library General Public License as\r
+ published by the Free Software Foundation; either version 2 of\r
+ the License, or (at your option) any later version.\r
+\r
+ This program is distributed in the hope that it will be useful,\r
+ but WITHOUT ANY WARRANTY; without even the implied warranty of\r
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\r
+ GNU Library General Public License for more details.\r
+\r
+ You should have received a copy of the GNU Library General Public\r
+ License along with this library; if not, write to the Free Software\r
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA\r
+ 02111-1307, USA.\r
+*/\r
+\r
+/*==============================================================================\r
+\r
+ $Id: mikmod_internals.h,v 1.4 2004/02/18 13:29:17 raph Exp $\r
+\r
+ MikMod sound library internal definitions\r
+\r
+==============================================================================*/\r
+\r
+#ifndef _MIKMOD_INTERNALS_H\r
+#define _MIKMOD_INTERNALS_H\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+#ifdef HAVE_MALLOC_H\r
+#include <malloc.h>\r
+#endif\r
+#include <stdarg.h>\r
+#if defined(__OS2__)||defined(__EMX__)||defined(WIN32)\r
+#define strcasecmp(s,t) stricmp(s,t)\r
+#endif\r
+\r
+\r
+#include "plugin.h"\r
+extern struct plugin_api *rb;\r
+\r
+#include <mikmod_build.h>\r
+\r
+#ifdef WIN32\r
+#pragma warning(disable:4761)\r
+#endif\r
+\r
+/*========== More type definitions */\r
+\r
+/* SLONGLONG: 64bit, signed */\r
+typedef long long SLONGLONG;\r
+\r
+/*========== Error handling */\r
+\r
+#define _mm_errno MikMod_errno\r
+#define _mm_critical MikMod_critical\r
+extern MikMod_handler_t _mm_errorhandler;\r
+\r
+/*========== Memory allocation */\r
+\r
+extern void* _mm_malloc(size_t);\r
+extern void* _mm_calloc(size_t,size_t);\r
+#define _mm_free(p) do { if (p) free(p); p = NULL; } while(0)\r
+\r
+/*========== MT stuff */\r
+\r
+#ifdef HAVE_PTHREAD\r
+#include <pthread.h>\r
+#define DECLARE_MUTEX(name) \\r
+ extern pthread_mutex_t _mm_mutex_##name\r
+#define MUTEX_LOCK(name) \\r
+ pthread_mutex_lock(&_mm_mutex_##name)\r
+#define MUTEX_UNLOCK(name) \\r
+ pthread_mutex_unlock(&_mm_mutex_##name)\r
+#elif defined(__OS2__)||defined(__EMX__)\r
+#define DECLARE_MUTEX(name) \\r
+ extern HMTX _mm_mutex_##name\r
+#define MUTEX_LOCK(name) \\r
+ if(_mm_mutex_##name) \\r
+ DosRequestMutexSem(_mm_mutex_##name,SEM_INDEFINITE_WAIT)\r
+#define MUTEX_UNLOCK(name) \\r
+ if(_mm_mutex_##name) \\r
+ DosReleaseMutexSem(_mm_mutex_##name)\r
+#elif defined(WIN32)\r
+#include <windows.h>\r
+#define DECLARE_MUTEX(name) \\r
+ extern HANDLE _mm_mutex_##name\r
+#define MUTEX_LOCK(name) \\r
+ if(_mm_mutex_##name) \\r
+ WaitForSingleObject(_mm_mutex_##name,INFINITE)\r
+#define MUTEX_UNLOCK(name) \\r
+ if(_mm_mutex_##name) \\r
+ ReleaseMutex(_mm_mutex_##name)\r
+#else\r
+#define DECLARE_MUTEX(name) \\r
+ extern void *_mm_mutex_##name\r
+#define MUTEX_LOCK(name)\r
+#define MUTEX_UNLOCK(name)\r
+#endif\r
+\r
+DECLARE_MUTEX(lists);\r
+DECLARE_MUTEX(vars);\r
+\r
+/*========== Portable file I/O */\r
+\r
+extern MREADER* _mm_new_file_reader(int fp);\r
+extern void _mm_delete_file_reader(MREADER*);\r
+\r
+extern MWRITER* _mm_new_file_writer(int fp);\r
+extern void _mm_delete_file_writer(MWRITER*);\r
+\r
+extern BOOL _mm_FileExists(CHAR *fname);\r
+\r
+#define _mm_write_SBYTE(x,y) y->Put(y,(int)x)\r
+#define _mm_write_UBYTE(x,y) y->Put(y,(int)x)\r
+\r
+#define _mm_read_SBYTE(x) (SBYTE)x->Get(x)\r
+#define _mm_read_UBYTE(x) (UBYTE)x->Get(x)\r
+\r
+#define _mm_write_SBYTES(x,y,z) z->Write(z,(void *)x,y)\r
+#define _mm_write_UBYTES(x,y,z) z->Write(z,(void *)x,y)\r
+#define _mm_read_SBYTES(x,y,z) z->Read(z,(void *)x,y)\r
+#define _mm_read_UBYTES(x,y,z) z->Read(z,(void *)x,y)\r
+\r
+#define _mm_fseek(x,y,z) x->Seek(x,y,z)\r
+#define _mm_ftell(x) x->Tell(x)\r
+#define _mm_rewind(x) _mm_fseek(x,0,SEEK_SET)\r
+\r
+#define _mm_eof(x) x->Eof(x)\r
+\r
+extern void _mm_iobase_setcur(MREADER*);\r
+extern void _mm_iobase_revert(void);\r
+extern int _mm_fopen(CHAR*,int);\r
+extern int _mm_fclose(int);\r
+extern void _mm_write_string(CHAR*,MWRITER*);\r
+extern int _mm_read_string (CHAR*,int,MREADER*);\r
+\r
+extern SWORD _mm_read_M_SWORD(MREADER*);\r
+extern SWORD _mm_read_I_SWORD(MREADER*);\r
+extern UWORD _mm_read_M_UWORD(MREADER*);\r
+extern UWORD _mm_read_I_UWORD(MREADER*);\r
+\r
+extern SLONG _mm_read_M_SLONG(MREADER*);\r
+extern SLONG _mm_read_I_SLONG(MREADER*);\r
+extern ULONG _mm_read_M_ULONG(MREADER*);\r
+extern ULONG _mm_read_I_ULONG(MREADER*);\r
+\r
+extern int _mm_read_M_SWORDS(SWORD*,int,MREADER*);\r
+extern int _mm_read_I_SWORDS(SWORD*,int,MREADER*);\r
+extern int _mm_read_M_UWORDS(UWORD*,int,MREADER*);\r
+extern int _mm_read_I_UWORDS(UWORD*,int,MREADER*);\r
+\r
+extern int _mm_read_M_SLONGS(SLONG*,int,MREADER*);\r
+extern int _mm_read_I_SLONGS(SLONG*,int,MREADER*);\r
+extern int _mm_read_M_ULONGS(ULONG*,int,MREADER*);\r
+extern int _mm_read_I_ULONGS(ULONG*,int,MREADER*);\r
+\r
+extern void _mm_write_M_SWORD(SWORD,MWRITER*);\r
+extern void _mm_write_I_SWORD(SWORD,MWRITER*);\r
+extern void _mm_write_M_UWORD(UWORD,MWRITER*);\r
+extern void _mm_write_I_UWORD(UWORD,MWRITER*);\r
+\r
+extern void _mm_write_M_SLONG(SLONG,MWRITER*);\r
+extern void _mm_write_I_SLONG(SLONG,MWRITER*);\r
+extern void _mm_write_M_ULONG(ULONG,MWRITER*);\r
+extern void _mm_write_I_ULONG(ULONG,MWRITER*);\r
+\r
+extern void _mm_write_M_SWORDS(SWORD*,int,MWRITER*);\r
+extern void _mm_write_I_SWORDS(SWORD*,int,MWRITER*);\r
+extern void _mm_write_M_UWORDS(UWORD*,int,MWRITER*);\r
+extern void _mm_write_I_UWORDS(UWORD*,int,MWRITER*);\r
+\r
+extern void _mm_write_M_SLONGS(SLONG*,int,MWRITER*);\r
+extern void _mm_write_I_SLONGS(SLONG*,int,MWRITER*);\r
+extern void _mm_write_M_ULONGS(ULONG*,int,MWRITER*);\r
+extern void _mm_write_I_ULONGS(ULONG*,int,MWRITER*);\r
+\r
+/*========== Samples */\r
+\r
+/* This is a handle of sorts attached to any sample registered with\r
+ SL_RegisterSample. Generally, this only need be used or changed by the\r
+ loaders and drivers of mikmod. */\r
+typedef struct SAMPLOAD {\r
+ struct SAMPLOAD *next;\r
+\r
+ ULONG length; /* length of sample (in samples!) */\r
+ ULONG loopstart; /* repeat position (relative to start, in samples) */\r
+ ULONG loopend; /* repeat end */\r
+ UWORD infmt,outfmt;\r
+ int scalefactor;\r
+ SAMPLE* sample;\r
+ MREADER* reader;\r
+} SAMPLOAD;\r
+\r
+/*========== Sample and waves loading interface */\r
+\r
+extern void SL_HalveSample(SAMPLOAD*,int);\r
+extern void SL_Sample8to16(SAMPLOAD*);\r
+extern void SL_Sample16to8(SAMPLOAD*);\r
+extern void SL_SampleSigned(SAMPLOAD*);\r
+extern void SL_SampleUnsigned(SAMPLOAD*);\r
+extern BOOL SL_LoadSamples(void);\r
+extern SAMPLOAD* SL_RegisterSample(SAMPLE*,int,MREADER*);\r
+extern BOOL SL_Load(void*,SAMPLOAD*,ULONG);\r
+extern BOOL SL_Init(SAMPLOAD*);\r
+extern void SL_Exit(SAMPLOAD*);\r
+\r
+/*========== Internal module representation (UniMod) interface */\r
+\r
+/* number of notes in an octave */\r
+#define OCTAVE 12\r
+\r
+extern void UniSetRow(UBYTE*);\r
+extern UBYTE UniGetByte(void);\r
+extern UWORD UniGetWord(void);\r
+extern UBYTE* UniFindRow(UBYTE*,UWORD);\r
+extern void UniSkipOpcode(void);\r
+extern void UniReset(void);\r
+extern void UniWriteByte(UBYTE);\r
+extern void UniWriteWord(UWORD);\r
+extern void UniNewline(void);\r
+extern UBYTE* UniDup(void);\r
+extern BOOL UniInit(void);\r
+extern void UniCleanup(void);\r
+extern void UniEffect(UWORD,UWORD);\r
+#define UniInstrument(x) UniEffect(UNI_INSTRUMENT,x)\r
+#define UniNote(x) UniEffect(UNI_NOTE,x)\r
+extern void UniPTEffect(UBYTE,UBYTE);\r
+extern void UniVolEffect(UWORD,UBYTE);\r
+\r
+/*========== Module Commands */\r
+\r
+enum {\r
+ /* Simple note */\r
+ UNI_NOTE = 1,\r
+ /* Instrument change */\r
+ UNI_INSTRUMENT,\r
+ /* Protracker effects */\r
+ UNI_PTEFFECT0, /* arpeggio */\r
+ UNI_PTEFFECT1, /* porta up */\r
+ UNI_PTEFFECT2, /* porta down */\r
+ UNI_PTEFFECT3, /* porta to note */\r
+ UNI_PTEFFECT4, /* vibrato */\r
+ UNI_PTEFFECT5, /* dual effect 3+A */\r
+ UNI_PTEFFECT6, /* dual effect 4+A */\r
+ UNI_PTEFFECT7, /* tremolo */\r
+ UNI_PTEFFECT8, /* pan */\r
+ UNI_PTEFFECT9, /* sample offset */\r
+ UNI_PTEFFECTA, /* volume slide */\r
+ UNI_PTEFFECTB, /* pattern jump */\r
+ UNI_PTEFFECTC, /* set volume */\r
+ UNI_PTEFFECTD, /* pattern break */\r
+ UNI_PTEFFECTE, /* extended effects */\r
+ UNI_PTEFFECTF, /* set speed */\r
+ /* Scream Tracker effects */\r
+ UNI_S3MEFFECTA, /* set speed */\r
+ UNI_S3MEFFECTD, /* volume slide */\r
+ UNI_S3MEFFECTE, /* porta down */\r
+ UNI_S3MEFFECTF, /* porta up */\r
+ UNI_S3MEFFECTI, /* tremor */\r
+ UNI_S3MEFFECTQ, /* retrig */\r
+ UNI_S3MEFFECTR, /* tremolo */\r
+ UNI_S3MEFFECTT, /* set tempo */\r
+ UNI_S3MEFFECTU, /* fine vibrato */\r
+ UNI_KEYOFF, /* note off */\r
+ /* Fast Tracker effects */\r
+ UNI_KEYFADE, /* note fade */\r
+ UNI_VOLEFFECTS, /* volume column effects */\r
+ UNI_XMEFFECT4, /* vibrato */\r
+ UNI_XMEFFECT6, /* dual effect 4+A */\r
+ UNI_XMEFFECTA, /* volume slide */\r
+ UNI_XMEFFECTE1, /* fine porta up */\r
+ UNI_XMEFFECTE2, /* fine porta down */\r
+ UNI_XMEFFECTEA, /* fine volume slide up */\r
+ UNI_XMEFFECTEB, /* fine volume slide down */\r
+ UNI_XMEFFECTG, /* set global volume */\r
+ UNI_XMEFFECTH, /* global volume slide */\r
+ UNI_XMEFFECTL, /* set envelope position */\r
+ UNI_XMEFFECTP, /* pan slide */\r
+ UNI_XMEFFECTX1, /* extra fine porta up */\r
+ UNI_XMEFFECTX2, /* extra fine porta down */\r
+ /* Impulse Tracker effects */\r
+ UNI_ITEFFECTG, /* porta to note */\r
+ UNI_ITEFFECTH, /* vibrato */\r
+ UNI_ITEFFECTI, /* tremor (xy not incremented) */\r
+ UNI_ITEFFECTM, /* set channel volume */\r
+ UNI_ITEFFECTN, /* slide / fineslide channel volume */\r
+ UNI_ITEFFECTP, /* slide / fineslide channel panning */\r
+ UNI_ITEFFECTT, /* slide tempo */\r
+ UNI_ITEFFECTU, /* fine vibrato */\r
+ UNI_ITEFFECTW, /* slide / fineslide global volume */\r
+ UNI_ITEFFECTY, /* panbrello */\r
+ UNI_ITEFFECTZ, /* resonant filters */\r
+ UNI_ITEFFECTS0,\r
+ /* UltraTracker effects */\r
+ UNI_ULTEFFECT9, /* Sample fine offset */\r
+ /* OctaMED effects */\r
+ UNI_MEDSPEED,\r
+ UNI_MEDEFFECTF1, /* play note twice */\r
+ UNI_MEDEFFECTF2, /* delay note */\r
+ UNI_MEDEFFECTF3, /* play note three times */\r
+ /* Oktalyzer effects */\r
+ UNI_OKTARP, /* arpeggio */\r
+\r
+ UNI_LAST\r
+};\r
+\r
+extern UWORD unioperands[UNI_LAST];\r
+\r
+/* IT / S3M Extended SS effects: */\r
+enum {\r
+ SS_GLISSANDO = 1,\r
+ SS_FINETUNE,\r
+ SS_VIBWAVE,\r
+ SS_TREMWAVE,\r
+ SS_PANWAVE,\r
+ SS_FRAMEDELAY,\r
+ SS_S7EFFECTS,\r
+ SS_PANNING,\r
+ SS_SURROUND,\r
+ SS_HIOFFSET,\r
+ SS_PATLOOP,\r
+ SS_NOTECUT,\r
+ SS_NOTEDELAY,\r
+ SS_PATDELAY\r
+};\r
+\r
+/* IT Volume column effects */\r
+enum {\r
+ VOL_VOLUME = 1,\r
+ VOL_PANNING,\r
+ VOL_VOLSLIDE,\r
+ VOL_PITCHSLIDEDN,\r
+ VOL_PITCHSLIDEUP,\r
+ VOL_PORTAMENTO,\r
+ VOL_VIBRATO\r
+};\r
+\r
+/* IT resonant filter information */\r
+\r
+#define UF_MAXMACRO 0x10\r
+#define UF_MAXFILTER 0x100\r
+\r
+#define FILT_CUT 0x80\r
+#define FILT_RESONANT 0x81\r
+\r
+typedef struct FILTER {\r
+ UBYTE filter,inf;\r
+} FILTER;\r
+\r
+/*========== Instruments */\r
+\r
+/* Instrument format flags */\r
+#define IF_OWNPAN 1\r
+#define IF_PITCHPAN 2\r
+\r
+/* Envelope flags: */\r
+#define EF_ON 1\r
+#define EF_SUSTAIN 2\r
+#define EF_LOOP 4\r
+#define EF_VOLENV 8\r
+\r
+/* New Note Action Flags */\r
+#define NNA_CUT 0\r
+#define NNA_CONTINUE 1\r
+#define NNA_OFF 2\r
+#define NNA_FADE 3\r
+\r
+#define NNA_MASK 3\r
+\r
+#define DCT_OFF 0\r
+#define DCT_NOTE 1\r
+#define DCT_SAMPLE 2\r
+#define DCT_INST 3\r
+\r
+#define DCA_CUT 0\r
+#define DCA_OFF 1\r
+#define DCA_FADE 2\r
+\r
+#define KEY_KICK 0\r
+#define KEY_OFF 1\r
+#define KEY_FADE 2\r
+#define KEY_KILL (KEY_OFF|KEY_FADE)\r
+\r
+#define KICK_ABSENT 0\r
+#define KICK_NOTE 1\r
+#define KICK_KEYOFF 2\r
+#define KICK_ENV 4\r
+\r
+#define AV_IT 1 /* IT vs. XM vibrato info */\r
+\r
+/*========== Playing */\r
+\r
+#define POS_NONE (-2) /* no loop position defined */\r
+\r
+#define LAST_PATTERN (UWORD)(-1) /* special ``end of song'' pattern */\r
+\r
+typedef struct ENVPR {\r
+ UBYTE flg; /* envelope flag */\r
+ UBYTE pts; /* number of envelope points */\r
+ UBYTE susbeg; /* envelope sustain index begin */\r
+ UBYTE susend; /* envelope sustain index end */\r
+ UBYTE beg; /* envelope loop begin */\r
+ UBYTE end; /* envelope loop end */\r
+ SWORD p; /* current envelope counter */\r
+ UWORD a; /* envelope index a */\r
+ UWORD b; /* envelope index b */\r
+ ENVPT* env; /* envelope points */\r
+} ENVPR;\r
+\r
+typedef struct MP_CHANNEL {\r
+ INSTRUMENT* i;\r
+ SAMPLE* s;\r
+ UBYTE sample; /* which sample number */\r
+ UBYTE note; /* the audible note as heard, direct rep of period */\r
+ SWORD outvolume; /* output volume (vol + sampcol + instvol) */\r
+ SBYTE chanvol; /* channel's "global" volume */\r
+ UWORD fadevol; /* fading volume rate */\r
+ SWORD panning; /* panning position */\r
+ UBYTE kick; /* if true = sample has to be restarted */\r
+ UBYTE kick_flag; /* kick has been true */\r
+ UWORD period; /* period to play the sample at */\r
+ UBYTE nna; /* New note action type + master/slave flags */\r
+\r
+ UBYTE volflg; /* volume envelope settings */\r
+ UBYTE panflg; /* panning envelope settings */\r
+ UBYTE pitflg; /* pitch envelope settings */\r
+\r
+ UBYTE keyoff; /* if true = fade out and stuff */\r
+ SWORD handle; /* which sample-handle */\r
+ UBYTE notedelay; /* (used for note delay) */\r
+ SLONG start; /* The starting byte index in the sample */\r
+} MP_CHANNEL;\r
+\r
+typedef struct MP_CONTROL {\r
+ struct MP_CHANNEL main;\r
+\r
+ struct MP_VOICE *slave; /* Audio Slave of current effects control channel */\r
+\r
+ UBYTE slavechn; /* Audio Slave of current effects control channel */\r
+ UBYTE muted; /* if set, channel not played */\r
+ UWORD ultoffset; /* fine sample offset memory */\r
+ UBYTE anote; /* the note that indexes the audible */\r
+ UBYTE oldnote;\r
+ SWORD ownper;\r
+ SWORD ownvol;\r
+ UBYTE dca; /* duplicate check action */\r
+ UBYTE dct; /* duplicate check type */\r
+ UBYTE* row; /* row currently playing on this channel */\r
+ SBYTE retrig; /* retrig value (0 means don't retrig) */\r
+ ULONG speed; /* what finetune to use */\r
+ SWORD volume; /* amiga volume (0 t/m 64) to play the sample at */\r
+\r
+ SWORD tmpvolume; /* tmp volume */\r
+ UWORD tmpperiod; /* tmp period */\r
+ UWORD wantedperiod; /* period to slide to (with effect 3 or 5) */\r
+\r
+ UBYTE arpmem; /* arpeggio command memory */\r
+ UBYTE pansspd; /* panslide speed */\r
+ UWORD slidespeed;\r
+ UWORD portspeed; /* noteslide speed (toneportamento) */\r
+\r
+ UBYTE s3mtremor; /* s3m tremor (effect I) counter */\r
+ UBYTE s3mtronof; /* s3m tremor ontime/offtime */\r
+ UBYTE s3mvolslide; /* last used volslide */\r
+ SBYTE sliding;\r
+ UBYTE s3mrtgspeed; /* last used retrig speed */\r
+ UBYTE s3mrtgslide; /* last used retrig slide */\r
+\r
+ UBYTE glissando; /* glissando (0 means off) */\r
+ UBYTE wavecontrol;\r
+\r
+ SBYTE vibpos; /* current vibrato position */\r
+ UBYTE vibspd; /* "" speed */\r
+ UBYTE vibdepth; /* "" depth */\r
+\r
+ SBYTE trmpos; /* current tremolo position */\r
+ UBYTE trmspd; /* "" speed */\r
+ UBYTE trmdepth; /* "" depth */\r
+\r
+ UBYTE fslideupspd;\r
+ UBYTE fslidednspd;\r
+ UBYTE fportupspd; /* fx E1 (extra fine portamento up) data */\r
+ UBYTE fportdnspd; /* fx E2 (extra fine portamento dn) data */\r
+ UBYTE ffportupspd; /* fx X1 (extra fine portamento up) data */\r
+ UBYTE ffportdnspd; /* fx X2 (extra fine portamento dn) data */\r
+\r
+ ULONG hioffset; /* last used high order of sample offset */\r
+ UWORD soffset; /* last used low order of sample-offset (effect 9) */\r
+\r
+ UBYTE sseffect; /* last used Sxx effect */\r
+ UBYTE ssdata; /* last used Sxx data info */\r
+ UBYTE chanvolslide; /* last used channel volume slide */\r
+\r
+ UBYTE panbwave; /* current panbrello waveform */\r
+ UBYTE panbpos; /* current panbrello position */\r
+ SBYTE panbspd; /* "" speed */\r
+ UBYTE panbdepth; /* "" depth */\r
+\r
+ UWORD newsamp; /* set to 1 upon a sample / inst change */\r
+ UBYTE voleffect; /* Volume Column Effect Memory as used by IT */\r
+ UBYTE voldata; /* Volume Column Data Memory */\r
+\r
+ SWORD pat_reppos; /* patternloop position */\r
+ UWORD pat_repcnt; /* times to loop */\r
+} MP_CONTROL;\r
+\r
+/* Used by NNA only player (audio control. AUDTMP is used for full effects\r
+ control). */\r
+typedef struct MP_VOICE {\r
+ struct MP_CHANNEL main;\r
+\r
+ ENVPR venv;\r
+ ENVPR penv;\r
+ ENVPR cenv;\r
+\r
+ UWORD avibpos; /* autovibrato pos */\r
+ UWORD aswppos; /* autovibrato sweep pos */\r
+\r
+ ULONG totalvol; /* total volume of channel (before global mixings) */\r
+\r
+ BOOL mflag;\r
+ SWORD masterchn;\r
+ UWORD masterperiod;\r
+\r
+ MP_CONTROL* master; /* index of "master" effects channel */\r
+} MP_VOICE;\r
+\r
+/*========== Loaders */\r
+\r
+typedef struct MLOADER {\r
+struct MLOADER* next;\r
+ CHAR* type;\r
+ CHAR* version;\r
+ BOOL (*Init)(void);\r
+ BOOL (*Test)(void);\r
+ BOOL (*Load)(BOOL);\r
+ void (*Cleanup)(void);\r
+ CHAR* (*LoadTitle)(void);\r
+} MLOADER;\r
+\r
+/* internal loader variables */\r
+extern MREADER* modreader;\r
+extern UWORD finetune[16];\r
+extern MODULE of; /* static unimod loading space */\r
+extern UWORD npertab[7*OCTAVE]; /* used by the original MOD loaders */\r
+\r
+extern SBYTE remap[UF_MAXCHAN]; /* for removing empty channels */\r
+extern UBYTE* poslookup; /* lookup table for pattern jumps after\r
+ blank pattern removal */\r
+extern UBYTE poslookupcnt;\r
+extern UWORD* origpositions;\r
+\r
+extern BOOL filters; /* resonant filters in use */\r
+extern UBYTE activemacro; /* active midi macro number for Sxx */\r
+extern UBYTE filtermacros[UF_MAXMACRO]; /* midi macro settings */\r
+extern FILTER filtersettings[UF_MAXFILTER]; /* computed filter settings */\r
+\r
+extern int* noteindex;\r
+\r
+/*========== Internal loader interface */\r
+\r
+extern BOOL ReadComment(UWORD);\r
+extern BOOL ReadLinedComment(UWORD,UWORD);\r
+extern BOOL AllocPositions(int);\r
+extern BOOL AllocPatterns(void);\r
+extern BOOL AllocTracks(void);\r
+extern BOOL AllocInstruments(void);\r
+extern BOOL AllocSamples(void);\r
+extern CHAR* DupStr(CHAR*,UWORD,BOOL);\r
+\r
+/* loader utility functions */\r
+extern int* AllocLinear(void);\r
+extern void FreeLinear(void);\r
+extern int speed_to_finetune(ULONG,int);\r
+extern void S3MIT_ProcessCmd(UBYTE,UBYTE,unsigned int);\r
+extern void S3MIT_CreateOrders(BOOL);\r
+\r
+/* flags for S3MIT_ProcessCmd */\r
+#define S3MIT_OLDSTYLE 1 /* behave as old scream tracker */\r
+#define S3MIT_IT 2 /* behave as impulse tracker */\r
+#define S3MIT_SCREAM 4 /* enforce scream tracker specific limits */\r
+\r
+/* used to convert c4spd to linear XM periods (IT and IMF loaders). */\r
+extern UWORD getlinearperiod(UWORD,ULONG);\r
+extern ULONG getfrequency(UWORD,ULONG);\r
+\r
+/* loader shared data */\r
+#define STM_NTRACKERS 3\r
+extern CHAR *STM_Signatures[STM_NTRACKERS];\r
+\r
+/*========== Player interface */\r
+\r
+extern BOOL Player_Init(MODULE*);\r
+extern void Player_Exit(MODULE*);\r
+extern void Player_HandleTick(void);\r
+\r
+/*========== Drivers */\r
+\r
+/* max. number of handles a driver has to provide. (not strict) */\r
+#define MAXSAMPLEHANDLES 384\r
+\r
+/* These variables can be changed at ANY time and results will be immediate */\r
+extern UWORD md_bpm; /* current song / hardware BPM rate */\r
+\r
+/* Variables below can be changed via MD_SetNumVoices at any time. However, a\r
+ call to MD_SetNumVoicess while the driver is active will cause the sound to\r
+ skip slightly. */\r
+extern UBYTE md_numchn; /* number of song + sound effects voices */\r
+extern UBYTE md_sngchn; /* number of song voices */\r
+extern UBYTE md_sfxchn; /* number of sound effects voices */\r
+extern UBYTE md_hardchn; /* number of hardware mixed voices */\r
+extern UBYTE md_softchn; /* number of software mixed voices */\r
+\r
+/* This is for use by the hardware drivers only. It points to the registered\r
+ tickhandler function. */\r
+extern void (*md_player)(void);\r
+\r
+extern SWORD MD_SampleLoad(SAMPLOAD*,int);\r
+extern void MD_SampleUnload(SWORD);\r
+extern ULONG MD_SampleSpace(int);\r
+extern ULONG MD_SampleLength(int,SAMPLE*);\r
+\r
+/* uLaw conversion */\r
+extern void unsignedtoulaw(char *,int);\r
+\r
+/* Parameter extraction helper */\r
+extern CHAR *MD_GetAtom(CHAR*,CHAR*,BOOL);\r
+\r
+/* Internal software mixer stuff */\r
+extern void VC_SetupPointers(void);\r
+extern BOOL VC1_Init(void);\r
+extern BOOL VC2_Init(void);\r
+\r
+#if defined(unix) || defined(__APPLE__) && defined(__MACH__)\r
+/* POSIX helper functions */\r
+extern BOOL MD_Access(CHAR *);\r
+extern BOOL MD_DropPrivileges(void);\r
+#endif\r
+\r
+/* Macro to define a missing driver, yet allowing binaries to dynamically link\r
+ with the library without missing symbol errors */\r
+#define MISSING(a) MDRIVER a = { NULL, NULL, NULL, 0, 0 }\r
+\r
+/*========== Prototypes for non-MT safe versions of some public functions */\r
+\r
+extern void _mm_registerdriver(struct MDRIVER*);\r
+extern void _mm_registerloader(struct MLOADER*);\r
+extern BOOL MikMod_Active_internal(void);\r
+extern void MikMod_DisableOutput_internal(void);\r
+extern BOOL MikMod_EnableOutput_internal(void);\r
+extern void MikMod_Exit_internal(void);\r
+extern BOOL MikMod_SetNumVoices_internal(int,int);\r
+extern void Player_Exit_internal(MODULE*);\r
+extern void Player_Stop_internal(void);\r
+extern BOOL Player_Paused_internal(void);\r
+extern void Sample_Free_internal(SAMPLE*);\r
+extern void Voice_Play_internal(SBYTE,SAMPLE*,ULONG);\r
+extern void Voice_SetFrequency_internal(SBYTE,ULONG);\r
+extern void Voice_SetPanning_internal(SBYTE,ULONG);\r
+extern void Voice_SetVolume_internal(SBYTE,UWORD);\r
+extern void Voice_Stop_internal(SBYTE);\r
+extern BOOL Voice_Stopped_internal(SBYTE);\r
+\r
+\r
+/*\r
+ * Static memory management + rockboxed function calls\r
+ */\r
+void* mikmod_malloc(size_t size);\r
+void* mikmod_calloc(size_t nmemb, size_t size);\r
+void* mikmod_realloc(void* ptr, size_t size);\r
+void mikmod_free(void* ptr);\r
+int mikmod_abs(int num);\r
+char* mikmod_strdup(const char *srcbuf);\r
+char* mikmod_strncat(char *dest, const char *src, size_t count);\r
+char* mikmod_strstr(char *str, char *search);\r
+int mikmod_toupper(int character);\r
+int mikmod_isalnum(int character);\r
+int mikmod_isdigit(char c);\r
+\r
+//#define malloc(a) mikmod_malloc(a)\r
+//#define calloc(a,b) mikmod_calloc(a,b)\r
+#define free(a) mikmod_free(a)\r
+#define realloc(a,b) mikmod_realloc(a,b)\r
+//#define abs(a) mikmod_abs(a)\r
+#define strdup(a) mikmod_strdup(a)\r
+#define strncat(a, b, c) mikmod_strncat(a, b, c)\r
+#define strstr(a, b) mikmod_strstr(a, b)\r
+#define toupper(a) mikmod_toupper(a)\r
+#define isalnum(a) mikmod_isalnum(a)\r
+#define isdigit(a) mikmod_isdigit(a)\r
+\r
+\r
+#define strcpy(a, b) rb->strcpy(a, b)\r
+#define strncpy(a, b, c) rb->strncpy(a, b, c)\r
+#define strlen(a) rb->strlen(a)\r
+#define strrchr(a, b) rb->strrchr(a, b)\r
+#define strcmp(a, b) rb->strcmp(a, b)\r
+#define strncmp(a, b, c) rb->strncmp(a, b, c)\r
+#define strcasecmp(a, b) rb->strcasecmp(a, b)\r
+#define strncasecmp(a, b, c) rb->strncasecmp(a, b, c)\r
+#define memset(a, b, c) rb->memset(a, b, c)\r
+#define memcpy(a, b, c) rb->memcpy(a, b, c)\r
+#define memmove(a, b, c) rb->memmove(a, b, c)\r
+\r
+#define rand() rb->rand()\r
+#define atoi(a) rb->atoi(a)\r
+#define strchr(a, b) rb->strchr(a, b)\r
+#define strcat(a, b) rb->strcat(a, b)\r
+#define memchr(a, b, c) rb->memchr(a, b, c)\r
+#define memcmp(a, b, c) rb->memcmp(a, b, c)\r
+#define strcasestr(a, b) rb->strcasestr(a, b)\r
+#define strtok_r(a, b, c) rb->strtok_r(a, b, c)\r
+#define snprintf(a, b, c, args...) rb->snprintf(a, b, c, args)\r
+\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif\r
+\r
+/* ex:set ts=4: */\r