1
0
Fork 0
forked from len0rd/rockbox

MIDI: Optimize the new pitch bending code for a small speedup.

git-svn-id: svn://svn.rockbox.org/rockbox/trunk@15160 a1c6a512-1295-4272-9138-f99709370657
This commit is contained in:
Stepan Moskovchenko 2007-10-17 03:48:24 +00:00
parent 1cc852c346
commit d33645ba13
4 changed files with 28 additions and 99 deletions

View file

@ -25,7 +25,10 @@ int chVol[16] IBSS_ATTR; /* Channel volume */
int chPan[16] IBSS_ATTR; /* Channel panning */ int chPan[16] IBSS_ATTR; /* Channel panning */
int chPat[16] IBSS_ATTR; /* Channel patch */ int chPat[16] IBSS_ATTR; /* Channel patch */
int chPW[16] IBSS_ATTR; /* Channel pitch wheel, MSB only */ int chPW[16] IBSS_ATTR; /* Channel pitch wheel, MSB only */
int chPBDepth[16] IBSS_ATTR; /* Channel pitch wheel, MSB only */ int chPBDepth[16] IBSS_ATTR; /* Channel pitch bend depth */
int chPBNoteOffset[16] IBSS_ATTR; /* Pre-computed whole semitone offset */
int chPBFractBend[16] IBSS_ATTR; /* Fractional bend applied to delta */
struct GPatch * gusload(char *); struct GPatch * gusload(char *);
struct GPatch * patchSet[128]; struct GPatch * patchSet[128];

View file

@ -34,8 +34,7 @@
mainly because they have to use 44100Hz sample rate */ mainly because they have to use 44100Hz sample rate */
#define MAX_VOICES 16 #define MAX_VOICES 16
#else #else
#define MAX_VOICES 24 /* Note: 24 midi channels is the minimum general midi #define MAX_VOICES 24 /* Note: 24 midi channels is the minimum general midi spec implementation */
spec implementation */
#endif /* CPU_PP */ #endif /* CPU_PP */
#else /* Simulator requires 44100Hz, and we can afford to use more voices */ #else /* Simulator requires 44100Hz, and we can afford to use more voices */
@ -98,19 +97,6 @@ struct MIDIfile
int numPatches; int numPatches;
}; };
/*
struct SynthObject
{
struct GWaveform * wf;
unsigned int delta;
unsigned int decay;
unsigned int cp;
unsigned char state, loopState, loopDir;
unsigned char note, vol, ch, isUsed;
int curRate, curOffset, targetOffset;
unsigned int curPoint;
};
*/
struct SynthObject struct SynthObject
{ {
@ -161,6 +147,10 @@ extern int chPan[16]; /* Channel panning */
extern int chPat[16]; /* Channel patch */ extern int chPat[16]; /* Channel patch */
extern int chPW[16]; /* Channel pitch wheel, MSB only */ extern int chPW[16]; /* Channel pitch wheel, MSB only */
extern int chPBDepth[16]; /* Channel pitch bend depth (Controller 6 */ extern int chPBDepth[16]; /* Channel pitch bend depth (Controller 6 */
extern int chPBNoteOffset[16] IBSS_ATTR; /* Pre-computed whole semitone offset */
extern int chPBFractBend[16] IBSS_ATTR; /* Fractional bend applied to delta */
extern struct GPatch * gusload(char *); extern struct GPatch * gusload(char *);
extern struct GPatch * patchSet[128]; extern struct GPatch * patchSet[128];

View file

@ -52,32 +52,19 @@ static inline void setPatch(int ch, int pat)
} }
/*
* Pitch Bend table, Computed by
* for i=0:127, fprintf('%d,', round(2^16*2^((i-64)/384))); end
* (When typed into Matlab)
* 16 bit pitch bend table
*/
/*
long pitchTbl[]=
{
58386,58491,58597,58703,58809,58915,59022,59128,59235,59342,59449,59557,
59664,59772,59880,59988,60097,60205,60314,60423,60532,60642,60751,60861,
60971,61081,61191,61302,61413,61524,61635,61746,61858,61970,62081,62194,
62306,62419,62531,62644,62757,62871,62984,63098,63212,63326,63441,63555,
63670,63785,63901,64016,64132,64248,64364,64480,64596,64713,64830,64947,
65065,65182,65300,65418,65536,65654,65773,65892,66011,66130,66250,66369,
66489,66609,66730,66850,66971,67092,67213,67335,67456,67578,67700,67823,
67945,68068,68191,68314,68438,68561,68685,68809,68933,69058,69183,69308,
69433,69558,69684,69810,69936,70062,70189,70316,70443,70570,70698,70825,
70953,71082,71210,71339,71468,71597,71726,71856,71985,72115,72246,72376,
72507,72638,72769,72901,73032,73164,73297,73429
};
*/
/* 512 entries here */
/* /*
This is the new pitch bend table. There are 512 entries.
The middle entry is exactly 65536 - no bending.
The range of the table is one semitone /in either direction/
Ie, one semitone from the center.
Bends beyond this can be achieved by first offsetting the index
into the GUS frequency table by the appropriate number of semitones,
and then using this table to bend the rest of the way.
Generated using Matlab code:
for i=0:512, fprintf('%d,', round(2^16*2^((i-256)/1536))); end for i=0:512, fprintf('%d,', round(2^16*2^((i-256)/1536))); end
*/ */
@ -125,57 +112,8 @@ const uint32_t pitchTbl[] ICONST_ATTR={
68933,68949,68965,68980,68996,69011,69027,69042,69058,69074,69089,69105, 68933,68949,68965,68980,68996,69011,69027,69042,69058,69074,69089,69105,
69120,69136,69152,69167,69183,69198,69214,69230,69245,69261,69276,69292, 69120,69136,69152,69167,69183,69198,69214,69230,69245,69261,69276,69292,
69308,69323,69339,69355,69370,69386,69402,69417,69433 69308,69323,69339,69355,69370,69386,69402,69417,69433
}; };
/*
58386,58412,58439,58465,58491,58518,58544,58571,58597,58624,58650,58676,
58703,58729,58756,58782,58809,58836,58862,58889,58915,58942,58968,58995,
59022,59048,59075,59102,59128,59155,59182,59208,59235,59262,59289,59315,
59342,59369,59396,59423,59449,59476,59503,59530,59557,59584,59611,59638,
59664,59691,59718,59745,59772,59799,59826,59853,59880,59907,59934,59961,
59988,60015,60043,60070,60097,60124,60151,60178,60205,60233,60260,60287,
60314,60341,60369,60396,60423,60450,60478,60505,60532,60560,60587,60614,
60642,60669,60696,60724,60751,60779,60806,60833,60861,60888,60916,60943,
60971,60998,61026,61054,61081,61109,61136,61164,61191,61219,61247,61274,
61302,61330,61357,61385,61413,61440,61468,61496,61524,61551,61579,61607,
61635,61663,61690,61718,61746,61774,61802,61830,61858,61886,61914,61942,
61970,61997,62025,62053,62081,62109,62138,62166,62194,62222,62250,62278,
62306,62334,62362,62390,62419,62447,62475,62503,62531,62560,62588,62616,
62644,62673,62701,62729,62757,62786,62814,62843,62871,62899,62928,62956,
62984,63013,63041,63070,63098,63127,63155,63184,63212,63241,63269,63298,
63326,63355,63384,63412,63441,63470,63498,63527,63555,63584,63613,63642,
63670,63699,63728,63757,63785,63814,63843,63872,63901,63929,63958,63987,
64016,64045,64074,64103,64132,64161,64190,64219,64248,64277,64306,64335,
64364,64393,64422,64451,64480,64509,64538,64567,64596,64626,64655,64684,
64713,64742,64772,64801,64830,64859,64889,64918,64947,64976,65006,65035,
65065,65094,65123,65153,65182,65211,65241,65270,65300,65329,65359,65388,
65418,65447,65477,65506,65536,65566,65595,65625,65654,65684,65714,65743,
65773,65803,65832,65862,65892,65922,65951,65981,66011,66041,66071,66100,
66130,66160,66190,66220,66250,66280,66309,66339,66369,66399,66429,66459,
66489,66519,66549,66579,66609,66639,66670,66700,66730,66760,66790,66820,
66850,66880,66911,66941,66971,67001,67032,67062,67092,67122,67153,67183,
67213,67244,67274,67304,67335,67365,67395,67426,67456,67487,67517,67548,
67578,67609,67639,67670,67700,67731,67761,67792,67823,67853,67884,67915,
67945,67976,68007,68037,68068,68099,68129,68160,68191,68222,68252,68283,
68314,68345,68376,68407,68438,68468,68499,68530,68561,68592,68623,68654,
68685,68716,68747,68778,68809,68840,68871,68902,68933,68965,68996,69027,
69058,69089,69120,69152,69183,69214,69245,69276,69308,69339,69370,69402,
69433,69464,69496,69527,69558,69590,69621,69653,69684,69716,69747,69778,
69810,69841,69873,69905,69936,69968,69999,70031,70062,70094,70126,70157,
70189,70221,70252,70284,70316,70348,70379,70411,70443,70475,70507,70538,
70570,70602,70634,70666,70698,70730,70762,70793,70825,70857,70889,70921,
70953,70985,71017,71049,71082,71114,71146,71178,71210,71242,71274,71306,
71339,71371,71403,71435,71468,71500,71532,71564,71597,71629,71661,71694,
71726,71758,71791,71823,71856,71888,71920,71953,71985,72018,72050,72083,
72115,72148,72181,72213,72246,72278,72311,72344,72376,72409,72442,72474,
72507,72540,72573,72605,72638,72671,72704,72736,72769,72802,72835,72868,
72901,72934,72967,72999,73032,73065,73098,73131,73164,73197,73230,73264,
73297,73330,73363,73396,73429,73462,73495,73528
};*/
static void findDelta(struct SynthObject * so, int ch, int note) static void findDelta(struct SynthObject * so, int ch, int note)
{ {
@ -183,16 +121,8 @@ static void findDelta(struct SynthObject * so, int ch, int note)
struct GWaveform * wf = patchSet[chPat[ch]]->waveforms[patchSet[chPat[ch]]->noteTable[note]]; struct GWaveform * wf = patchSet[chPat[ch]]->waveforms[patchSet[chPat[ch]]->noteTable[note]];
so->wf=wf; so->wf=wf;
unsigned int delta= 0; unsigned int delta= 0;
delta = (((gustable[note+chPBNoteOffset[ch]]<<FRACTSIZE) / (wf->rootFreq)) * wf->sampRate / (SAMPLE_RATE));
int totalBend = (chPW[ch]-256) * chPBDepth[ch]; delta = (delta * chPBFractBend[ch])>> 16;
int noteOffset = totalBend >> 8;
int pitchOffset = totalBend - (noteOffset<<8);
delta = (((gustable[note+noteOffset]<<FRACTSIZE) / (wf->rootFreq)) * wf->sampRate / (SAMPLE_RATE));
delta = (delta * pitchTbl[pitchOffset+256])>> 16;
so->delta = delta; so->delta = delta;
} }
@ -201,6 +131,10 @@ static inline void setPW(int ch, int msb, int lsb)
{ {
chPW[ch] = msb<<2|lsb>>5; chPW[ch] = msb<<2|lsb>>5;
int totalBend = (chPW[ch]-256) * chPBDepth[ch];
chPBNoteOffset[ch] = totalBend >> 8;
chPBFractBend[ch] = pitchTbl[(totalBend & 0xFF) + 256];
int a=0; int a=0;
for(a = 0; a<MAX_VOICES; a++) for(a = 0; a<MAX_VOICES; a++)
{ {

View file

@ -66,6 +66,8 @@ int initSynth(struct MIDIfile * mf, char * filename, char * drumConfig)
chPat[a]=0; /* Ac Gr Piano */ chPat[a]=0; /* Ac Gr Piano */
chPW[a]=256; /* .. not .. bent ? */ chPW[a]=256; /* .. not .. bent ? */
chPBDepth[a]=2; /* Default bend value is 2 */ chPBDepth[a]=2; /* Default bend value is 2 */
chPBNoteOffset[a]=0; /* No offset */
chPBFractBend[a]=65536; /* Center.. no bend */
} }
for(a=0; a<128; a++) for(a=0; a<128; a++)
{ {