xref: /btstack/3rd-party/hxcmod-player/hxcmod.c (revision 8201da882231bee1019f0a84a70494b65e0d959a)
1a4cd9b30SMilanka Ringwald ///////////////////////////////////////////////////////////////////////////////////
2a4cd9b30SMilanka Ringwald //-------------------------------------------------------------------------------//
3a4cd9b30SMilanka Ringwald //-------------------------------------------------------------------------------//
4a4cd9b30SMilanka Ringwald //-----------H----H--X----X-----CCCCC----22222----0000-----0000------11----------//
5a4cd9b30SMilanka Ringwald //----------H----H----X-X-----C--------------2---0----0---0----0--1--1-----------//
6a4cd9b30SMilanka Ringwald //---------HHHHHH-----X------C----------22222---0----0---0----0-----1------------//
7a4cd9b30SMilanka Ringwald //--------H----H----X--X----C----------2-------0----0---0----0-----1-------------//
8a4cd9b30SMilanka Ringwald //-------H----H---X-----X---CCCCC-----222222----0000-----0000----1111------------//
9a4cd9b30SMilanka Ringwald //-------------------------------------------------------------------------------//
10a4cd9b30SMilanka Ringwald //----------------------------------------------------- http://hxc2001.free.fr --//
11a4cd9b30SMilanka Ringwald ///////////////////////////////////////////////////////////////////////////////////
12a4cd9b30SMilanka Ringwald // File : hxcmod.c
13a4cd9b30SMilanka Ringwald // Contains: a tiny mod player
14a4cd9b30SMilanka Ringwald //
15d38efbbaSMatthias Ringwald // Written by: Jean Francois DEL NERO
16a4cd9b30SMilanka Ringwald //
17a4cd9b30SMilanka Ringwald // You are free to do what you want with this code.
18a4cd9b30SMilanka Ringwald // A credit is always appreciated if you include it into your prod :)
19a4cd9b30SMilanka Ringwald //
20a4cd9b30SMilanka Ringwald // This file include some parts of the Noisetracker/Soundtracker/Protracker
21a4cd9b30SMilanka Ringwald // Module Format documentation written by Andrew Scott (Adrenalin Software)
22a4cd9b30SMilanka Ringwald // (modformat.txt)
23a4cd9b30SMilanka Ringwald //
24a4cd9b30SMilanka Ringwald // The core (hxcmod.c/hxcmod.h) is designed to have the least external dependency.
25a4cd9b30SMilanka Ringwald // So it should be usable on almost all OS and systems.
26a4cd9b30SMilanka Ringwald // Please also note that no dynamic allocation is done into the HxCMOD core.
27a4cd9b30SMilanka Ringwald //
28a4cd9b30SMilanka Ringwald // Change History (most recent first):
29a4cd9b30SMilanka Ringwald ///////////////////////////////////////////////////////////////////////////////////
30a4cd9b30SMilanka Ringwald // HxCMOD Core API:
31a4cd9b30SMilanka Ringwald // -------------------------------------------
32a4cd9b30SMilanka Ringwald // int  hxcmod_init(modcontext * modctx)
33a4cd9b30SMilanka Ringwald //
34a4cd9b30SMilanka Ringwald // - Initialize the modcontext buffer. Must be called before doing anything else.
35a4cd9b30SMilanka Ringwald //   Return 1 if success. 0 in case of error.
36a4cd9b30SMilanka Ringwald // -------------------------------------------
37a4cd9b30SMilanka Ringwald // int  hxcmod_load( modcontext * modctx, void * mod_data, int mod_data_size )
38a4cd9b30SMilanka Ringwald //
39a4cd9b30SMilanka Ringwald // - "Load" a MOD from memory (from "mod_data" with size "mod_data_size").
40a4cd9b30SMilanka Ringwald //   Return 1 if success. 0 in case of error.
41a4cd9b30SMilanka Ringwald // -------------------------------------------
42*8201da88SMatthias Ringwald // void hxcmod_fillbuffer( modcontext * modctx, unsigned short * outbuffer, mssize nbsample, tracker_buffer_state * trkbuf )
43a4cd9b30SMilanka Ringwald //
44a4cd9b30SMilanka Ringwald // - Generate and return the next samples chunk to outbuffer.
45a4cd9b30SMilanka Ringwald //   nbsample specify the number of stereo 16bits samples you want.
46a4cd9b30SMilanka Ringwald //   The output format is signed 44100Hz 16-bit Stereo PCM samples.
47a4cd9b30SMilanka Ringwald //   The output buffer size in byte must be equal to ( nbsample * 2 * 2 ).
48a4cd9b30SMilanka Ringwald //   The optional trkbuf parameter can be used to get detailed status of the player. Put NULL/0 is unused.
49a4cd9b30SMilanka Ringwald // -------------------------------------------
50a4cd9b30SMilanka Ringwald // void hxcmod_unload( modcontext * modctx )
51a4cd9b30SMilanka Ringwald // - "Unload" / clear the player status.
52a4cd9b30SMilanka Ringwald // -------------------------------------------
53a4cd9b30SMilanka Ringwald ///////////////////////////////////////////////////////////////////////////////////
54a4cd9b30SMilanka Ringwald 
55a4cd9b30SMilanka Ringwald #include "hxcmod.h"
56a4cd9b30SMilanka Ringwald 
57*8201da88SMatthias Ringwald // BK4BSTACK_CHANGE START
58*8201da88SMatthias Ringwald 
59*8201da88SMatthias Ringwald // MODs ar either in ROM (MCUs) or in .text segment
60*8201da88SMatthias Ringwald #define HXCMOD_MOD_FILE_IN_ROM
61*8201da88SMatthias Ringwald 
62*8201da88SMatthias Ringwald #ifdef __GNUC__
63*8201da88SMatthias Ringwald #ifndef	__clang__
64*8201da88SMatthias Ringwald #pragma GCC diagnostic push
65*8201da88SMatthias Ringwald // -Wstringop-overflow unknown to Clang 16.0.0
66*8201da88SMatthias Ringwald #pragma GCC diagnostic ignored "-Wstringop-overflow"
67*8201da88SMatthias Ringwald #endif
68*8201da88SMatthias Ringwald #endif
69*8201da88SMatthias Ringwald 
70*8201da88SMatthias Ringwald // BK4BSTACK_CHANGE END
71*8201da88SMatthias Ringwald 
72a4cd9b30SMilanka Ringwald ///////////////////////////////////////////////////////////////////////////////////
73a4cd9b30SMilanka Ringwald 
74a4cd9b30SMilanka Ringwald // Effects list
75a4cd9b30SMilanka Ringwald #define EFFECT_ARPEGGIO              0x0 // Supported
76a4cd9b30SMilanka Ringwald #define EFFECT_PORTAMENTO_UP         0x1 // Supported
77a4cd9b30SMilanka Ringwald #define EFFECT_PORTAMENTO_DOWN       0x2 // Supported
78a4cd9b30SMilanka Ringwald #define EFFECT_TONE_PORTAMENTO       0x3 // Supported
79a4cd9b30SMilanka Ringwald #define EFFECT_VIBRATO               0x4 // Supported
80a4cd9b30SMilanka Ringwald #define EFFECT_VOLSLIDE_TONEPORTA    0x5 // Supported
81a4cd9b30SMilanka Ringwald #define EFFECT_VOLSLIDE_VIBRATO      0x6 // Supported
82a4cd9b30SMilanka Ringwald #define EFFECT_VOLSLIDE_TREMOLO      0x7 // - TO BE DONE -
83a4cd9b30SMilanka Ringwald #define EFFECT_SET_PANNING           0x8 // - TO BE DONE -
84a4cd9b30SMilanka Ringwald #define EFFECT_SET_OFFSET            0x9 // Supported
85a4cd9b30SMilanka Ringwald #define EFFECT_VOLUME_SLIDE          0xA // Supported
86a4cd9b30SMilanka Ringwald #define EFFECT_JUMP_POSITION         0xB // Supported
87a4cd9b30SMilanka Ringwald #define EFFECT_SET_VOLUME            0xC // Supported
88a4cd9b30SMilanka Ringwald #define EFFECT_PATTERN_BREAK         0xD // Supported
89a4cd9b30SMilanka Ringwald 
90a4cd9b30SMilanka Ringwald #define EFFECT_EXTENDED              0xE
91a4cd9b30SMilanka Ringwald #define EFFECT_E_FINE_PORTA_UP       0x1 // Supported
92a4cd9b30SMilanka Ringwald #define EFFECT_E_FINE_PORTA_DOWN     0x2 // Supported
93a4cd9b30SMilanka Ringwald #define EFFECT_E_GLISSANDO_CTRL      0x3 // - TO BE DONE -
94a4cd9b30SMilanka Ringwald #define EFFECT_E_VIBRATO_WAVEFORM    0x4 // - TO BE DONE -
95*8201da88SMatthias Ringwald #define EFFECT_E_SET_FINETUNE        0x5 // Supported
96a4cd9b30SMilanka Ringwald #define EFFECT_E_PATTERN_LOOP        0x6 // Supported
97a4cd9b30SMilanka Ringwald #define EFFECT_E_TREMOLO_WAVEFORM    0x7 // - TO BE DONE -
98a4cd9b30SMilanka Ringwald #define EFFECT_E_SET_PANNING_2       0x8 // - TO BE DONE -
99*8201da88SMatthias Ringwald #define EFFECT_E_RETRIGGER_NOTE      0x9 // Supported
100a4cd9b30SMilanka Ringwald #define EFFECT_E_FINE_VOLSLIDE_UP    0xA // Supported
101a4cd9b30SMilanka Ringwald #define EFFECT_E_FINE_VOLSLIDE_DOWN  0xB // Supported
102a4cd9b30SMilanka Ringwald #define EFFECT_E_NOTE_CUT            0xC // Supported
103*8201da88SMatthias Ringwald #define EFFECT_E_NOTE_DELAY          0xD // Supported
104a4cd9b30SMilanka Ringwald #define EFFECT_E_PATTERN_DELAY       0xE // Supported
105*8201da88SMatthias Ringwald #define EFFECT_E_INVERT_LOOP         0xF // Supported (W.I.P)
106a4cd9b30SMilanka Ringwald #define EFFECT_SET_SPEED             0xF0 // Supported
107a4cd9b30SMilanka Ringwald #define EFFECT_SET_TEMPO             0xF2 // Supported
108a4cd9b30SMilanka Ringwald 
109a4cd9b30SMilanka Ringwald #define PERIOD_TABLE_LENGTH  MAXNOTES
110a4cd9b30SMilanka Ringwald 
111*8201da88SMatthias Ringwald 
112*8201da88SMatthias Ringwald //
113*8201da88SMatthias Ringwald // Finetuning periods -> Amiga period * 2^(-finetune/12/8)
114*8201da88SMatthias Ringwald //
115b0920f25SMilanka Ringwald 
116a4cd9b30SMilanka Ringwald static const short periodtable[]=
117a4cd9b30SMilanka Ringwald {
118*8201da88SMatthias Ringwald 	// Finetune 0 (* 1.000000), Offset 0x0000
119a4cd9b30SMilanka Ringwald 	27392, 25856, 24384, 23040, 21696, 20480, 19328, 18240, 17216, 16256, 15360, 14496,
120a4cd9b30SMilanka Ringwald 	13696, 12928, 12192, 11520, 10848, 10240,  9664,  9120,  8606,  8128,  7680,  7248,
121a4cd9b30SMilanka Ringwald 	 6848,  6464,  6096,  5760,  5424,  5120,  4832,  4560,  4304,  4064,  3840,  3624,
122a4cd9b30SMilanka Ringwald 	 3424,  3232,  3048,  2880,  2712,  2560,  2416,  2280,  2152,  2032,  1920,  1812,
123a4cd9b30SMilanka Ringwald 	 1712,  1616,  1524,  1440,  1356,  1280,  1208,  1140,  1076,  1016,   960,   906,
124a4cd9b30SMilanka Ringwald 	  856,   808,   762,   720,   678,   640,   604,   570,   538,   508,   480,   453,
125a4cd9b30SMilanka Ringwald 	  428,   404,   381,   360,   339,   320,   302,   285,   269,   254,   240,   226,
126a4cd9b30SMilanka Ringwald 	  214,   202,   190,   180,   170,   160,   151,   143,   135,   127,   120,   113,
127a4cd9b30SMilanka Ringwald 	  107,   101,    95,    90,    85,    80,    75,    71,    67,    63,    60,    56,
128a4cd9b30SMilanka Ringwald 	   53,    50,    47,    45,    42,    40,    37,    35,    33,    31,    30,    28,
129a4cd9b30SMilanka Ringwald 	   27,    25,    24,    22,    21,    20,    19,    18,    17,    16,    15,    14,
130*8201da88SMatthias Ringwald 	   13,    13,    12,    11,    11,    10,     9,     9,     8,     8,     7,     7,
131*8201da88SMatthias Ringwald 
132*8201da88SMatthias Ringwald 	// Finetune 1 (* 0.992806), Offset 0x0120
133*8201da88SMatthias Ringwald 	27195, 25670, 24209, 22874, 21540, 20333, 19189, 18109, 17092, 16139, 15249, 14392,
134*8201da88SMatthias Ringwald 	13597, 12835, 12104, 11437, 10770, 10166,  9594,  9054,  8544,  8070,  7625,  7196,
135*8201da88SMatthias Ringwald 	 6799,  6417,  6052,  5719,  5385,  5083,  4797,  4527,  4273,  4035,  3812,  3598,
136*8201da88SMatthias Ringwald 	 3399,  3209,  3026,  2859,  2692,  2542,  2399,  2264,  2137,  2017,  1906,  1799,
137*8201da88SMatthias Ringwald 	 1700,  1604,  1513,  1430,  1346,  1271,  1199,  1132,  1068,  1009,   953,   899,
138*8201da88SMatthias Ringwald 	  850,   802,   757,   715,   673,   635,   600,   566,   534,   504,   477,   450,
139*8201da88SMatthias Ringwald 	  425,   401,   378,   357,   337,   318,   300,   283,   267,   252,   238,   224,
140*8201da88SMatthias Ringwald 	  212,   201,   189,   179,   169,   159,   150,   142,   134,   126,   119,   112,
141*8201da88SMatthias Ringwald 	  106,   100,    94,    89,    84,    79,    74,    70,    67,    63,    60,    56,
142*8201da88SMatthias Ringwald 	   53,    50,    47,    45,    42,    40,    37,    35,    33,    31,    30,    28,
143*8201da88SMatthias Ringwald 	   27,    25,    24,    22,    21,    20,    19,    18,    17,    16,    15,    14,
144*8201da88SMatthias Ringwald 	   13,    13,    12,    11,    11,    10,     9,     9,     8,     8,     7,     7,
145*8201da88SMatthias Ringwald 
146*8201da88SMatthias Ringwald 	// Finetune 2 (* 0.985663), Offset 0x0240
147*8201da88SMatthias Ringwald 	26999, 25485, 24034, 22710, 21385, 20186, 19051, 17978, 16969, 16023, 15140, 14288,
148*8201da88SMatthias Ringwald 	13500, 12743, 12017, 11355, 10692, 10093,  9525,  8989,  8483,  8011,  7570,  7144,
149*8201da88SMatthias Ringwald 	 6750,  6371,  6009,  5677,  5346,  5047,  4763,  4495,  4242,  4006,  3785,  3572,
150*8201da88SMatthias Ringwald 	 3375,  3186,  3004,  2839,  2673,  2523,  2381,  2247,  2121,  2003,  1892,  1786,
151*8201da88SMatthias Ringwald 	 1687,  1593,  1502,  1419,  1337,  1262,  1191,  1124,  1061,  1001,   946,   893,
152*8201da88SMatthias Ringwald 	  844,   796,   751,   710,   668,   631,   595,   562,   530,   501,   473,   447,
153*8201da88SMatthias Ringwald 	  422,   398,   376,   355,   334,   315,   298,   281,   265,   250,   237,   223,
154*8201da88SMatthias Ringwald 	  211,   199,   187,   177,   168,   158,   149,   141,   133,   125,   118,   111,
155*8201da88SMatthias Ringwald 	  105,   100,    94,    89,    84,    79,    74,    70,    66,    62,    59,    55,
156*8201da88SMatthias Ringwald 	   52,    49,    46,    44,    41,    39,    36,    34,    33,    31,    30,    28,
157*8201da88SMatthias Ringwald 	   27,    25,    24,    22,    21,    20,    19,    18,    17,    16,    15,    14,
158*8201da88SMatthias Ringwald 	   13,    13,    12,    11,    11,    10,     9,     9,     8,     8,     7,     7,
159*8201da88SMatthias Ringwald 
160*8201da88SMatthias Ringwald 	// Finetune 3 (* 0.978572), Offset 0x0360
161*8201da88SMatthias Ringwald 	26805, 25302, 23862, 22546, 21231, 20041, 18914, 17849, 16847, 15908, 15031, 14185,
162*8201da88SMatthias Ringwald 	13403, 12651, 11931, 11273, 10616, 10021,  9457,  8925,  8422,  7954,  7515,  7093,
163*8201da88SMatthias Ringwald 	 6701,  6325,  5965,  5637,  5308,  5010,  4728,  4462,  4212,  3977,  3758,  3546,
164*8201da88SMatthias Ringwald 	 3351,  3163,  2983,  2818,  2654,  2505,  2364,  2231,  2106,  1988,  1879,  1773,
165*8201da88SMatthias Ringwald 	 1675,  1581,  1491,  1409,  1327,  1253,  1182,  1116,  1053,   994,   939,   887,
166*8201da88SMatthias Ringwald 	  838,   791,   746,   705,   663,   626,   591,   558,   526,   497,   470,   443,
167*8201da88SMatthias Ringwald 	  419,   395,   373,   352,   332,   313,   296,   279,   263,   249,   235,   221,
168*8201da88SMatthias Ringwald 	  209,   198,   186,   176,   166,   157,   148,   140,   132,   124,   117,   111,
169*8201da88SMatthias Ringwald 	  105,    99,    93,    88,    83,    78,    73,    69,    66,    62,    59,    55,
170*8201da88SMatthias Ringwald 	   52,    49,    46,    44,    41,    39,    36,    34,    32,    30,    29,    27,
171*8201da88SMatthias Ringwald 	   26,    24,    23,    22,    21,    20,    19,    18,    17,    16,    15,    14,
172*8201da88SMatthias Ringwald 	   13,    13,    12,    11,    11,    10,     9,     9,     8,     8,     7,     7,
173*8201da88SMatthias Ringwald 
174*8201da88SMatthias Ringwald 	// Finetune 4 (* 0.971532), Offset 0x0480
175*8201da88SMatthias Ringwald 	26612, 25120, 23690, 22384, 21078, 19897, 18778, 17721, 16726, 15793, 14923, 14083,
176*8201da88SMatthias Ringwald 	13306, 12560, 11845, 11192, 10539,  9948,  9389,  8860,  8361,  7897,  7461,  7042,
177*8201da88SMatthias Ringwald 	 6653,  6280,  5922,  5596,  5270,  4974,  4694,  4430,  4181,  3948,  3731,  3521,
178*8201da88SMatthias Ringwald 	 3327,  3140,  2961,  2798,  2635,  2487,  2347,  2215,  2091,  1974,  1865,  1760,
179*8201da88SMatthias Ringwald 	 1663,  1570,  1481,  1399,  1317,  1244,  1174,  1108,  1045,   987,   933,   880,
180*8201da88SMatthias Ringwald 	  832,   785,   740,   700,   659,   622,   587,   554,   523,   494,   466,   440,
181*8201da88SMatthias Ringwald 	  416,   392,   370,   350,   329,   311,   293,   277,   261,   247,   233,   220,
182*8201da88SMatthias Ringwald 	  208,   196,   185,   175,   165,   155,   147,   139,   131,   123,   117,   110,
183*8201da88SMatthias Ringwald 	  104,    98,    92,    87,    83,    78,    73,    69,    65,    61,    58,    54,
184*8201da88SMatthias Ringwald 	   51,    49,    46,    44,    41,    39,    36,    34,    32,    30,    29,    27,
185*8201da88SMatthias Ringwald 	   26,    24,    23,    21,    20,    19,    18,    17,    17,    16,    15,    14,
186*8201da88SMatthias Ringwald 	   13,    13,    12,    11,    11,    10,     9,     9,     8,     8,     7,     7,
187*8201da88SMatthias Ringwald 
188*8201da88SMatthias Ringwald 	// Finetune 5 (* 0.964542), Offset 0x05a0
189*8201da88SMatthias Ringwald 	26421, 24939, 23519, 22223, 20927, 19754, 18643, 17593, 16606, 15680, 14815, 13982,
190*8201da88SMatthias Ringwald 	13210, 12470, 11760, 11112, 10463,  9877,  9321,  8797,  8301,  7840,  7408,  6991,
191*8201da88SMatthias Ringwald 	 6605,  6235,  5880,  5556,  5232,  4938,  4661,  4398,  4151,  3920,  3704,  3496,
192*8201da88SMatthias Ringwald 	 3303,  3117,  2940,  2778,  2616,  2469,  2330,  2199,  2076,  1960,  1852,  1748,
193*8201da88SMatthias Ringwald 	 1651,  1559,  1470,  1389,  1308,  1235,  1165,  1100,  1038,   980,   926,   874,
194*8201da88SMatthias Ringwald 	  826,   779,   735,   694,   654,   617,   583,   550,   519,   490,   463,   437,
195*8201da88SMatthias Ringwald 	  413,   390,   367,   347,   327,   309,   291,   275,   259,   245,   231,   218,
196*8201da88SMatthias Ringwald 	  206,   195,   183,   174,   164,   154,   146,   138,   130,   122,   116,   109,
197*8201da88SMatthias Ringwald 	  103,    97,    92,    87,    82,    77,    72,    68,    65,    61,    58,    54,
198*8201da88SMatthias Ringwald 	   51,    48,    45,    43,    41,    39,    36,    34,    32,    30,    29,    27,
199*8201da88SMatthias Ringwald 	   26,    24,    23,    21,    20,    19,    18,    17,    16,    15,    14,    14,
200*8201da88SMatthias Ringwald 	   13,    13,    12,    11,    11,    10,     9,     9,     8,     8,     7,     7,
201*8201da88SMatthias Ringwald 
202*8201da88SMatthias Ringwald 	// Finetune 6 (* 0.957603), Offset 0x06c0
203*8201da88SMatthias Ringwald 	26231, 24760, 23350, 22063, 20776, 19612, 18509, 17467, 16486, 15567, 14709, 13881,
204*8201da88SMatthias Ringwald 	13115, 12380, 11675, 11032, 10388,  9806,  9254,  8733,  8241,  7783,  7354,  6941,
205*8201da88SMatthias Ringwald 	 6558,  6190,  5838,  5516,  5194,  4903,  4627,  4367,  4122,  3892,  3677,  3470,
206*8201da88SMatthias Ringwald 	 3279,  3095,  2919,  2758,  2597,  2451,  2314,  2183,  2061,  1946,  1839,  1735,
207*8201da88SMatthias Ringwald 	 1639,  1547,  1459,  1379,  1299,  1226,  1157,  1092,  1030,   973,   919,   868,
208*8201da88SMatthias Ringwald 	  820,   774,   730,   689,   649,   613,   578,   546,   515,   486,   460,   434,
209*8201da88SMatthias Ringwald 	  410,   387,   365,   345,   325,   306,   289,   273,   258,   243,   230,   216,
210*8201da88SMatthias Ringwald 	  205,   193,   182,   172,   163,   153,   145,   137,   129,   122,   115,   108,
211*8201da88SMatthias Ringwald 	  102,    97,    91,    86,    81,    77,    72,    68,    64,    60,    57,    54,
212*8201da88SMatthias Ringwald 	   51,    48,    45,    43,    40,    38,    35,    34,    32,    30,    29,    27,
213*8201da88SMatthias Ringwald 	   26,    24,    23,    21,    20,    19,    18,    17,    16,    15,    14,    13,
214*8201da88SMatthias Ringwald 	   12,    12,    11,    11,    11,    10,     9,     9,     8,     8,     7,     7,
215*8201da88SMatthias Ringwald 
216*8201da88SMatthias Ringwald 	// Finetune 7 (* 0.950714), Offset 0x07e0
217*8201da88SMatthias Ringwald 	26042, 24582, 23182, 21904, 20627, 19471, 18375, 17341, 16367, 15455, 14603, 13782,
218*8201da88SMatthias Ringwald 	13021, 12291, 11591, 10952, 10313,  9735,  9188,  8671,  8182,  7727,  7301,  6891,
219*8201da88SMatthias Ringwald 	 6510,  6145,  5796,  5476,  5157,  4868,  4594,  4335,  4092,  3864,  3651,  3445,
220*8201da88SMatthias Ringwald 	 3255,  3073,  2898,  2738,  2578,  2434,  2297,  2168,  2046,  1932,  1825,  1723,
221*8201da88SMatthias Ringwald 	 1628,  1536,  1449,  1369,  1289,  1217,  1148,  1084,  1023,   966,   913,   861,
222*8201da88SMatthias Ringwald 	  814,   768,   724,   685,   645,   608,   574,   542,   511,   483,   456,   431,
223*8201da88SMatthias Ringwald 	  407,   384,   362,   342,   322,   304,   287,   271,   256,   241,   228,   215,
224*8201da88SMatthias Ringwald 	  203,   192,   181,   171,   162,   152,   144,   136,   128,   121,   114,   107,
225*8201da88SMatthias Ringwald 	  102,    96,    90,    86,    81,    76,    71,    68,    64,    60,    57,    53,
226*8201da88SMatthias Ringwald 	   50,    48,    45,    43,    40,    38,    35,    33,    31,    29,    29,    27,
227*8201da88SMatthias Ringwald 	   26,    24,    23,    21,    20,    19,    18,    17,    16,    15,    14,    13,
228*8201da88SMatthias Ringwald 	   12,    12,    11,    10,    10,    10,     9,     9,     8,     8,     7,     7,
229*8201da88SMatthias Ringwald 
230*8201da88SMatthias Ringwald 	// Finetune -8 (* 1.059463), Offset 0x0900
231*8201da88SMatthias Ringwald 	29021, 27393, 25834, 24410, 22986, 21698, 20477, 19325, 18240, 17223, 16273, 15358,
232*8201da88SMatthias Ringwald 	14510, 13697, 12917, 12205, 11493, 10849, 10239,  9662,  9118,  8611,  8137,  7679,
233*8201da88SMatthias Ringwald 	 7255,  6848,  6458,  6103,  5747,  5424,  5119,  4831,  4560,  4306,  4068,  3839,
234*8201da88SMatthias Ringwald 	 3628,  3424,  3229,  3051,  2873,  2712,  2560,  2416,  2280,  2153,  2034,  1920,
235*8201da88SMatthias Ringwald 	 1814,  1712,  1615,  1526,  1437,  1356,  1280,  1208,  1140,  1076,  1017,   960,
236*8201da88SMatthias Ringwald 	  907,   856,   807,   763,   718,   678,   640,   604,   570,   538,   509,   480,
237*8201da88SMatthias Ringwald 	  453,   428,   404,   381,   359,   339,   320,   302,   285,   269,   254,   239,
238*8201da88SMatthias Ringwald 	  227,   214,   201,   191,   180,   170,   160,   152,   143,   135,   127,   120,
239*8201da88SMatthias Ringwald 	  113,   107,   101,    95,    90,    85,    79,    75,    71,    67,    64,    59,
240*8201da88SMatthias Ringwald 	   56,    53,    50,    48,    44,    42,    39,    37,    35,    33,    32,    30,
241*8201da88SMatthias Ringwald 	   29,    26,    25,    23,    22,    21,    20,    19,    18,    17,    16,    15,
242*8201da88SMatthias Ringwald 	   14,    14,    13,    12,    12,    11,    10,    10,     8,     8,     7,     7,
243*8201da88SMatthias Ringwald 
244*8201da88SMatthias Ringwald 	// Finetune -7 (* 1.051841), Offset 0x0a20
245*8201da88SMatthias Ringwald 	28812, 27196, 25648, 24234, 22821, 21542, 20330, 19186, 18108, 17099, 16156, 15247,
246*8201da88SMatthias Ringwald 	14406, 13598, 12824, 12117, 11410, 10771, 10165,  9593,  9052,  8549,  8078,  7624,
247*8201da88SMatthias Ringwald 	 7203,  6799,  6412,  6059,  5705,  5385,  5082,  4796,  4527,  4275,  4039,  3812,
248*8201da88SMatthias Ringwald 	 3602,  3400,  3206,  3029,  2853,  2693,  2541,  2398,  2264,  2137,  2020,  1906,
249*8201da88SMatthias Ringwald 	 1801,  1700,  1603,  1515,  1426,  1346,  1271,  1199,  1132,  1069,  1010,   953,
250*8201da88SMatthias Ringwald 	  900,   850,   802,   757,   713,   673,   635,   600,   566,   534,   505,   476,
251*8201da88SMatthias Ringwald 	  450,   425,   401,   379,   357,   337,   318,   300,   283,   267,   252,   238,
252*8201da88SMatthias Ringwald 	  225,   212,   200,   189,   179,   168,   159,   150,   142,   134,   126,   119,
253*8201da88SMatthias Ringwald 	  113,   106,   100,    95,    89,    84,    79,    75,    70,    66,    63,    59,
254*8201da88SMatthias Ringwald 	   56,    53,    49,    47,    44,    42,    39,    37,    35,    33,    32,    29,
255*8201da88SMatthias Ringwald 	   28,    26,    25,    23,    22,    21,    20,    19,    18,    17,    16,    15,
256*8201da88SMatthias Ringwald 	   14,    14,    13,    12,    12,    11,     9,     9,     8,     8,     7,     7,
257*8201da88SMatthias Ringwald 
258*8201da88SMatthias Ringwald 	// Finetune -6 (* 1.044274), Offset 0x0b40
259*8201da88SMatthias Ringwald 	28605, 27001, 25464, 24060, 22657, 21387, 20184, 19048, 17978, 16976, 16040, 15138,
260*8201da88SMatthias Ringwald 	14302, 13500, 12732, 12030, 11328, 10693, 10092,  9524,  8987,  8488,  8020,  7569,
261*8201da88SMatthias Ringwald 	 7151,  6750,  6366,  6015,  5664,  5347,  5046,  4762,  4495,  4244,  4010,  3784,
262*8201da88SMatthias Ringwald 	 3576,  3375,  3183,  3008,  2832,  2673,  2523,  2381,  2247,  2122,  2005,  1892,
263*8201da88SMatthias Ringwald 	 1788,  1688,  1591,  1504,  1416,  1337,  1261,  1190,  1124,  1061,  1003,   946,
264*8201da88SMatthias Ringwald 	  894,   844,   796,   752,   708,   668,   631,   595,   562,   530,   501,   473,
265*8201da88SMatthias Ringwald 	  447,   422,   398,   376,   354,   334,   315,   298,   281,   265,   251,   236,
266*8201da88SMatthias Ringwald 	  223,   211,   198,   188,   178,   167,   158,   149,   141,   133,   125,   118,
267*8201da88SMatthias Ringwald 	  112,   105,    99,    94,    89,    84,    78,    74,    70,    66,    63,    58,
268*8201da88SMatthias Ringwald 	   55,    52,    49,    47,    44,    42,    39,    37,    34,    32,    31,    29,
269*8201da88SMatthias Ringwald 	   28,    26,    25,    23,    22,    21,    20,    19,    18,    17,    16,    15,
270*8201da88SMatthias Ringwald 	   14,    14,    13,    11,    11,    10,     9,     9,     8,     8,     7,     7,
271*8201da88SMatthias Ringwald 
272*8201da88SMatthias Ringwald 	// Finetune -5 (* 1.036761), Offset 0x0c60
273*8201da88SMatthias Ringwald 	28399, 26806, 25280, 23887, 22494, 21233, 20039, 18911, 17849, 16854, 15925, 15029,
274*8201da88SMatthias Ringwald 	14199, 13403, 12640, 11943, 11247, 10616, 10019,  9455,  8922,  8427,  7962,  7514,
275*8201da88SMatthias Ringwald 	 7100,  6702,  6320,  5972,  5623,  5308,  5010,  4728,  4462,  4213,  3981,  3757,
276*8201da88SMatthias Ringwald 	 3550,  3351,  3160,  2986,  2812,  2654,  2505,  2364,  2231,  2107,  1991,  1879,
277*8201da88SMatthias Ringwald 	 1775,  1675,  1580,  1493,  1406,  1327,  1252,  1182,  1116,  1053,   995,   939,
278*8201da88SMatthias Ringwald 	  887,   838,   790,   746,   703,   664,   626,   591,   558,   527,   498,   470,
279*8201da88SMatthias Ringwald 	  444,   419,   395,   373,   351,   332,   313,   295,   279,   263,   249,   234,
280*8201da88SMatthias Ringwald 	  222,   209,   197,   187,   176,   166,   157,   148,   140,   132,   124,   117,
281*8201da88SMatthias Ringwald 	  111,   105,    98,    93,    88,    83,    78,    74,    69,    65,    62,    58,
282*8201da88SMatthias Ringwald 	   55,    52,    49,    47,    44,    41,    38,    36,    34,    32,    31,    29,
283*8201da88SMatthias Ringwald 	   28,    26,    25,    23,    22,    21,    20,    19,    18,    17,    16,    15,
284*8201da88SMatthias Ringwald 	   13,    13,    12,    11,    11,    10,     9,     9,     8,     8,     7,     7,
285*8201da88SMatthias Ringwald 
286*8201da88SMatthias Ringwald 	// Finetune -4 (* 1.029302), Offset 0x0d80
287*8201da88SMatthias Ringwald 	28195, 26614, 25099, 23715, 22332, 21080, 19894, 18774, 17720, 16732, 15810, 14921,
288*8201da88SMatthias Ringwald 	14097, 13307, 12549, 11858, 11166, 10540,  9947,  9387,  8858,  8366,  7905,  7460,
289*8201da88SMatthias Ringwald 	 7049,  6653,  6275,  5929,  5583,  5270,  4974,  4694,  4430,  4183,  3953,  3730,
290*8201da88SMatthias Ringwald 	 3524,  3327,  3137,  2964,  2791,  2635,  2487,  2347,  2215,  2092,  1976,  1865,
291*8201da88SMatthias Ringwald 	 1762,  1663,  1569,  1482,  1396,  1318,  1243,  1173,  1108,  1046,   988,   933,
292*8201da88SMatthias Ringwald 	  881,   832,   784,   741,   698,   659,   622,   587,   554,   523,   494,   466,
293*8201da88SMatthias Ringwald 	  441,   416,   392,   371,   349,   329,   311,   293,   277,   261,   247,   233,
294*8201da88SMatthias Ringwald 	  220,   208,   196,   185,   175,   165,   155,   147,   139,   131,   124,   116,
295*8201da88SMatthias Ringwald 	  110,   104,    98,    93,    87,    82,    77,    73,    69,    65,    62,    58,
296*8201da88SMatthias Ringwald 	   55,    51,    48,    46,    43,    41,    38,    36,    34,    32,    31,    29,
297*8201da88SMatthias Ringwald 	   28,    26,    25,    23,    22,    21,    20,    19,    17,    16,    15,    14,
298*8201da88SMatthias Ringwald 	   13,    13,    12,    11,    11,    10,     9,     9,     8,     8,     7,     7,
299*8201da88SMatthias Ringwald 
300*8201da88SMatthias Ringwald 	// Finetune -3 (* 1.021897), Offset 0x0ea0
301*8201da88SMatthias Ringwald 	27992, 26422, 24918, 23545, 22171, 20928, 19751, 18639, 17593, 16612, 15696, 14813,
302*8201da88SMatthias Ringwald 	13996, 13211, 12459, 11772, 11086, 10464,  9876,  9320,  8794,  8306,  7848,  7407,
303*8201da88SMatthias Ringwald 	 6998,  6606,  6229,  5886,  5543,  5232,  4938,  4660,  4398,  4153,  3924,  3703,
304*8201da88SMatthias Ringwald 	 3499,  3303,  3115,  2943,  2771,  2616,  2469,  2330,  2199,  2076,  1962,  1852,
305*8201da88SMatthias Ringwald 	 1749,  1651,  1557,  1472,  1386,  1308,  1234,  1165,  1100,  1038,   981,   926,
306*8201da88SMatthias Ringwald 	  875,   826,   779,   736,   693,   654,   617,   582,   550,   519,   491,   463,
307*8201da88SMatthias Ringwald 	  437,   413,   389,   368,   346,   327,   309,   291,   275,   260,   245,   231,
308*8201da88SMatthias Ringwald 	  219,   206,   194,   184,   174,   164,   154,   146,   138,   130,   123,   115,
309*8201da88SMatthias Ringwald 	  109,   103,    97,    92,    87,    82,    77,    73,    68,    64,    61,    57,
310*8201da88SMatthias Ringwald 	   54,    51,    48,    46,    43,    41,    38,    36,    34,    32,    31,    29,
311*8201da88SMatthias Ringwald 	   28,    26,    25,    22,    21,    20,    19,    18,    17,    16,    15,    14,
312*8201da88SMatthias Ringwald 	   13,    13,    12,    11,    11,    10,     9,     9,     8,     8,     7,     7,
313*8201da88SMatthias Ringwald 
314*8201da88SMatthias Ringwald 	// Finetune -2 (* 1.014545), Offset 0x0fc0
315*8201da88SMatthias Ringwald 	27790, 26232, 24739, 23375, 22012, 20778, 19609, 18505, 17466, 16492, 15583, 14707,
316*8201da88SMatthias Ringwald 	13895, 13116, 12369, 11688, 11006, 10389,  9805,  9253,  8731,  8246,  7792,  7353,
317*8201da88SMatthias Ringwald 	 6948,  6558,  6185,  5844,  5503,  5194,  4902,  4626,  4367,  4123,  3896,  3677,
318*8201da88SMatthias Ringwald 	 3474,  3279,  3092,  2922,  2751,  2597,  2451,  2313,  2183,  2062,  1948,  1838,
319*8201da88SMatthias Ringwald 	 1737,  1640,  1546,  1461,  1376,  1299,  1226,  1157,  1092,  1031,   974,   919,
320*8201da88SMatthias Ringwald 	  868,   820,   773,   730,   688,   649,   613,   578,   546,   515,   487,   460,
321*8201da88SMatthias Ringwald 	  434,   410,   387,   365,   344,   325,   306,   289,   273,   258,   243,   229,
322*8201da88SMatthias Ringwald 	  217,   205,   193,   183,   172,   162,   153,   145,   137,   129,   122,   115,
323*8201da88SMatthias Ringwald 	  109,   102,    96,    91,    86,    81,    76,    72,    68,    64,    61,    57,
324*8201da88SMatthias Ringwald 	   54,    51,    48,    46,    43,    41,    38,    36,    33,    31,    30,    28,
325*8201da88SMatthias Ringwald 	   27,    25,    24,    22,    21,    20,    19,    18,    17,    16,    15,    14,
326*8201da88SMatthias Ringwald 	   13,    13,    12,    11,    11,    10,     9,     9,     8,     8,     7,     7,
327*8201da88SMatthias Ringwald 
328*8201da88SMatthias Ringwald 	// Finetune -1 (* 1.007246), Offset 0x10e0
329*8201da88SMatthias Ringwald 	27590, 26043, 24561, 23207, 21853, 20628, 19468, 18372, 17341, 16374, 15471, 14601,
330*8201da88SMatthias Ringwald 	13795, 13022, 12280, 11603, 10927, 10314,  9734,  9186,  8668,  8187,  7736,  7301,
331*8201da88SMatthias Ringwald 	 6898,  6511,  6140,  5802,  5463,  5157,  4867,  4593,  4335,  4093,  3868,  3650,
332*8201da88SMatthias Ringwald 	 3449,  3255,  3070,  2901,  2732,  2579,  2434,  2297,  2168,  2047,  1934,  1825,
333*8201da88SMatthias Ringwald 	 1724,  1628,  1535,  1450,  1366,  1289,  1217,  1148,  1084,  1023,   967,   913,
334*8201da88SMatthias Ringwald 	  862,   814,   768,   725,   683,   645,   608,   574,   542,   512,   483,   456,
335*8201da88SMatthias Ringwald 	  431,   407,   384,   363,   341,   322,   304,   287,   271,   256,   242,   228,
336*8201da88SMatthias Ringwald 	  216,   203,   191,   181,   171,   161,   152,   144,   136,   128,   121,   114,
337*8201da88SMatthias Ringwald 	  108,   102,    96,    91,    86,    81,    76,    72,    67,    63,    60,    56,
338*8201da88SMatthias Ringwald 	   53,    50,    47,    45,    42,    40,    37,    35,    33,    31,    30,    28,
339*8201da88SMatthias Ringwald 	   27,    25,    24,    22,    21,    20,    19,    18,    17,    16,    15,    14,
340a4cd9b30SMilanka Ringwald 	   13,    13,    12,    11,    11,    10,     9,     9,     8,     8,     7,     7
341a4cd9b30SMilanka Ringwald };
342a4cd9b30SMilanka Ringwald 
343*8201da88SMatthias Ringwald static const short * periodtable_finetune_ptr[]=
344*8201da88SMatthias Ringwald {
345*8201da88SMatthias Ringwald 	&periodtable[0x0000], &periodtable[0x0090], &periodtable[0x0120], &periodtable[0x01B0],
346*8201da88SMatthias Ringwald 	&periodtable[0x0240], &periodtable[0x02D0], &periodtable[0x0360], &periodtable[0x03F0],
347*8201da88SMatthias Ringwald 	&periodtable[0x0480], &periodtable[0x0510], &periodtable[0x05A0], &periodtable[0x0630],
348*8201da88SMatthias Ringwald 	&periodtable[0x06C0], &periodtable[0x0750], &periodtable[0x07E0], &periodtable[0x0870]
349*8201da88SMatthias Ringwald };
350*8201da88SMatthias Ringwald 
351a4cd9b30SMilanka Ringwald static const short sintable[]={
352a4cd9b30SMilanka Ringwald 	  0,  24,  49,  74,  97, 120, 141, 161,
353a4cd9b30SMilanka Ringwald 	180, 197, 212, 224, 235, 244, 250, 253,
354a4cd9b30SMilanka Ringwald 	255, 253, 250, 244, 235, 224, 212, 197,
355a4cd9b30SMilanka Ringwald 	180, 161, 141, 120,  97,  74,  49,  24
356a4cd9b30SMilanka Ringwald };
357a4cd9b30SMilanka Ringwald 
358*8201da88SMatthias Ringwald static const muchar InvertLoopTable[]={
359*8201da88SMatthias Ringwald 	  0,   5,   6,   7,   8,  10,  11, 13,
360*8201da88SMatthias Ringwald 	 16,  19,  22,  26,  32,  43,  64, 128
361*8201da88SMatthias Ringwald };
362*8201da88SMatthias Ringwald 
363a4cd9b30SMilanka Ringwald typedef struct modtype_
364a4cd9b30SMilanka Ringwald {
365a4cd9b30SMilanka Ringwald 	unsigned char signature[5];
366a4cd9b30SMilanka Ringwald 	int numberofchannels;
367a4cd9b30SMilanka Ringwald }modtype;
368a4cd9b30SMilanka Ringwald 
369*8201da88SMatthias Ringwald static modtype modlist[]=
370a4cd9b30SMilanka Ringwald {
371a4cd9b30SMilanka Ringwald 	{ "M!K!",4},
372a4cd9b30SMilanka Ringwald 	{ "M.K.",4},
373*8201da88SMatthias Ringwald 	{ "M&K!",4},
374*8201da88SMatthias Ringwald 	{ "PATT",4},
375*8201da88SMatthias Ringwald 	{ "NSMS",4},
376*8201da88SMatthias Ringwald 	{ "LARD",4},
377*8201da88SMatthias Ringwald 	{ "FEST",4},
378*8201da88SMatthias Ringwald 	{ "FIST",4},
379*8201da88SMatthias Ringwald 	{ "N.T.",4},
380*8201da88SMatthias Ringwald 	{ "OKTA",8},
381*8201da88SMatthias Ringwald 	{ "OCTA",8},
382*8201da88SMatthias Ringwald 	{ "$CHN",-1},
383*8201da88SMatthias Ringwald 	{ "$$CH",-1},
384*8201da88SMatthias Ringwald 	{ "$$CN",-1},
385*8201da88SMatthias Ringwald 	{ "$$$C",-1},
386*8201da88SMatthias Ringwald 	{ "FLT$",-1},
387*8201da88SMatthias Ringwald 	{ "EXO$",-1},
388*8201da88SMatthias Ringwald 	{ "CD$1",-1},
389*8201da88SMatthias Ringwald 	{ "TDZ$",-1},
390*8201da88SMatthias Ringwald 	{ "FA0$",-1},
391a4cd9b30SMilanka Ringwald 	{ "",0}
392a4cd9b30SMilanka Ringwald };
393a4cd9b30SMilanka Ringwald 
394*8201da88SMatthias Ringwald #ifdef HXCMOD_BIGENDIAN_MACHINE
395*8201da88SMatthias Ringwald 
396*8201da88SMatthias Ringwald #define GET_BGI_W( big_endian_word ) ( big_endian_word )
397*8201da88SMatthias Ringwald 
398*8201da88SMatthias Ringwald #else
399*8201da88SMatthias Ringwald 
400*8201da88SMatthias Ringwald #define GET_BGI_W( big_endian_word ) ( (big_endian_word >> 8) | ((big_endian_word&0xFF) << 8) )
401*8201da88SMatthias Ringwald 
402*8201da88SMatthias Ringwald #endif
403*8201da88SMatthias Ringwald 
404*8201da88SMatthias Ringwald 
405a4cd9b30SMilanka Ringwald ///////////////////////////////////////////////////////////////////////////////////
406a4cd9b30SMilanka Ringwald 
407a4cd9b30SMilanka Ringwald static void memcopy( void * dest, void *source, unsigned long size )
408a4cd9b30SMilanka Ringwald {
409a4cd9b30SMilanka Ringwald 	unsigned long i;
410a4cd9b30SMilanka Ringwald 	unsigned char * d,*s;
411a4cd9b30SMilanka Ringwald 
412a4cd9b30SMilanka Ringwald 	d=(unsigned char*)dest;
413a4cd9b30SMilanka Ringwald 	s=(unsigned char*)source;
414a4cd9b30SMilanka Ringwald 	for(i=0;i<size;i++)
415a4cd9b30SMilanka Ringwald 	{
416a4cd9b30SMilanka Ringwald 		d[i]=s[i];
417a4cd9b30SMilanka Ringwald 	}
418a4cd9b30SMilanka Ringwald }
419a4cd9b30SMilanka Ringwald 
420a4cd9b30SMilanka Ringwald static void memclear( void * dest, unsigned char value, unsigned long size )
421a4cd9b30SMilanka Ringwald {
422a4cd9b30SMilanka Ringwald 	unsigned long i;
423a4cd9b30SMilanka Ringwald 	unsigned char * d;
424a4cd9b30SMilanka Ringwald 
425a4cd9b30SMilanka Ringwald 	d = (unsigned char*)dest;
426a4cd9b30SMilanka Ringwald 	for(i=0;i<size;i++)
427a4cd9b30SMilanka Ringwald 	{
428a4cd9b30SMilanka Ringwald 		d[i]=value;
429a4cd9b30SMilanka Ringwald 	}
430a4cd9b30SMilanka Ringwald }
431a4cd9b30SMilanka Ringwald 
432*8201da88SMatthias Ringwald static int getnote( modcontext * mod, unsigned short period )
433a4cd9b30SMilanka Ringwald {
434a4cd9b30SMilanka Ringwald 	int i;
435*8201da88SMatthias Ringwald 	const short * ptr;
436a4cd9b30SMilanka Ringwald 
437*8201da88SMatthias Ringwald 	ptr = periodtable_finetune_ptr[0];
438*8201da88SMatthias Ringwald 
439*8201da88SMatthias Ringwald 	for(i = 0; i < MAXNOTES; i++)
440a4cd9b30SMilanka Ringwald 	{
441*8201da88SMatthias Ringwald 		if(period >= ptr[i])
442a4cd9b30SMilanka Ringwald 		{
443a4cd9b30SMilanka Ringwald 			return i;
444a4cd9b30SMilanka Ringwald 		}
445a4cd9b30SMilanka Ringwald 	}
446a4cd9b30SMilanka Ringwald 
447a4cd9b30SMilanka Ringwald 	return MAXNOTES;
448a4cd9b30SMilanka Ringwald }
449a4cd9b30SMilanka Ringwald 
450*8201da88SMatthias Ringwald static void doFunk(channel * cptr)
451a4cd9b30SMilanka Ringwald {
452*8201da88SMatthias Ringwald 	if(cptr->funkspeed)
453*8201da88SMatthias Ringwald 	{
454*8201da88SMatthias Ringwald 		cptr->funkoffset += InvertLoopTable[cptr->funkspeed];
455*8201da88SMatthias Ringwald 		if( cptr->funkoffset > 128 )
456*8201da88SMatthias Ringwald 		{
457*8201da88SMatthias Ringwald 			cptr->funkoffset = 0;
458*8201da88SMatthias Ringwald 			if( cptr->sampdata && cptr->length && (cptr->replen > 1) )
459*8201da88SMatthias Ringwald 			{
460*8201da88SMatthias Ringwald 				if( ( (cptr->samppos) >> 11 ) >= (unsigned long)(cptr->replen+cptr->reppnt) )
461*8201da88SMatthias Ringwald 				{
462*8201da88SMatthias Ringwald 					cptr->samppos = ((unsigned long)(cptr->reppnt)<<11) + (cptr->samppos % ((unsigned long)(cptr->replen+cptr->reppnt)<<11));
463*8201da88SMatthias Ringwald 				}
464a4cd9b30SMilanka Ringwald 
465*8201da88SMatthias Ringwald #ifndef HXCMOD_MOD_FILE_IN_ROM
466*8201da88SMatthias Ringwald 				// Note : Directly modify the sample in the mod buffer...
467*8201da88SMatthias Ringwald 				// The current Invert Loop effect implementation can't be played from ROM.
468*8201da88SMatthias Ringwald 				cptr->sampdata[cptr->samppos >> 10] = -1 - cptr->sampdata[cptr->samppos >> 10];
469*8201da88SMatthias Ringwald #endif
470*8201da88SMatthias Ringwald 			}
471*8201da88SMatthias Ringwald 		}
472*8201da88SMatthias Ringwald 	}
473*8201da88SMatthias Ringwald }
474*8201da88SMatthias Ringwald 
475*8201da88SMatthias Ringwald static void worknote( note * nptr, channel * cptr,char t,modcontext * mod )
476*8201da88SMatthias Ringwald {
477*8201da88SMatthias Ringwald 	muint sample, period, effect, operiod;
478*8201da88SMatthias Ringwald 	muint curnote, arpnote;
479*8201da88SMatthias Ringwald 	muchar effect_op;
480*8201da88SMatthias Ringwald 	muchar effect_param,effect_param_l,effect_param_h;
481*8201da88SMatthias Ringwald 	muint enable_nxt_smp;
482*8201da88SMatthias Ringwald 	const short * period_table_ptr;
483*8201da88SMatthias Ringwald 
484*8201da88SMatthias Ringwald 	sample = (nptr->sampperiod & 0xF0) | (nptr->sampeffect >> 4);
485a4cd9b30SMilanka Ringwald 	period = ((nptr->sampperiod & 0xF) << 8) | nptr->period;
486a4cd9b30SMilanka Ringwald 	effect = ((nptr->sampeffect & 0xF) << 8) | nptr->effect;
487*8201da88SMatthias Ringwald 	effect_op = nptr->sampeffect & 0xF;
488*8201da88SMatthias Ringwald 	effect_param = nptr->effect;
489*8201da88SMatthias Ringwald 	effect_param_l = effect_param & 0x0F;
490*8201da88SMatthias Ringwald 	effect_param_h = effect_param >> 4;
491*8201da88SMatthias Ringwald 
492*8201da88SMatthias Ringwald 	enable_nxt_smp = 0;
493a4cd9b30SMilanka Ringwald 
494a4cd9b30SMilanka Ringwald 	operiod = cptr->period;
495a4cd9b30SMilanka Ringwald 
496*8201da88SMatthias Ringwald 	if ( period || sample )
497a4cd9b30SMilanka Ringwald 	{
498*8201da88SMatthias Ringwald 		if( sample && ( sample < 32 ) )
499a4cd9b30SMilanka Ringwald 		{
500*8201da88SMatthias Ringwald 			cptr->sampnum = sample - 1;
501a4cd9b30SMilanka Ringwald 		}
502a4cd9b30SMilanka Ringwald 
503*8201da88SMatthias Ringwald 		if( period || sample )
504a4cd9b30SMilanka Ringwald 		{
505*8201da88SMatthias Ringwald 			if( period )
506*8201da88SMatthias Ringwald 			{
507*8201da88SMatthias Ringwald 				if( ( effect_op != EFFECT_TONE_PORTAMENTO ) || ( ( effect_op == EFFECT_TONE_PORTAMENTO ) && !cptr->sampdata ) )
508*8201da88SMatthias Ringwald 				{
509*8201da88SMatthias Ringwald 					// Not a Tone Partamento effect or no sound currently played :
510*8201da88SMatthias Ringwald 					if ( ( effect_op != EFFECT_EXTENDED || effect_param_h != EFFECT_E_NOTE_DELAY ) || ( ( effect_op == EFFECT_EXTENDED && effect_param_h == EFFECT_E_NOTE_DELAY ) && !effect_param_l ) )
511*8201da88SMatthias Ringwald 					{
512*8201da88SMatthias Ringwald 						// Immediately (re)trigger the new note
513afc6fe18SMatthias Ringwald 						cptr->sampdata = mod->sampledata[cptr->sampnum];
514*8201da88SMatthias Ringwald 						cptr->length = GET_BGI_W( mod->song.samples[cptr->sampnum].length );
515*8201da88SMatthias Ringwald 						cptr->reppnt = GET_BGI_W( mod->song.samples[cptr->sampnum].reppnt );
516*8201da88SMatthias Ringwald 						cptr->replen = GET_BGI_W( mod->song.samples[cptr->sampnum].replen );
517*8201da88SMatthias Ringwald 
518*8201da88SMatthias Ringwald 						cptr->lst_sampdata = cptr->sampdata;
519*8201da88SMatthias Ringwald 						cptr->lst_length = cptr->length;
520*8201da88SMatthias Ringwald 						cptr->lst_reppnt = cptr->reppnt;
521*8201da88SMatthias Ringwald 						cptr->lst_replen = cptr->replen;
522*8201da88SMatthias Ringwald 					}
523*8201da88SMatthias Ringwald 					else
524*8201da88SMatthias Ringwald 					{
525*8201da88SMatthias Ringwald 						cptr->dly_sampdata = mod->sampledata[cptr->sampnum];
526*8201da88SMatthias Ringwald 						cptr->dly_length = GET_BGI_W( mod->song.samples[cptr->sampnum].length );
527*8201da88SMatthias Ringwald 						cptr->dly_reppnt = GET_BGI_W( mod->song.samples[cptr->sampnum].reppnt );
528*8201da88SMatthias Ringwald 						cptr->dly_replen = GET_BGI_W( mod->song.samples[cptr->sampnum].replen );
529*8201da88SMatthias Ringwald 						cptr->note_delay = effect_param_l;
530*8201da88SMatthias Ringwald 					}
531*8201da88SMatthias Ringwald 					// Cancel any delayed note...
532*8201da88SMatthias Ringwald 					cptr->update_nxt_repeat = 0;
533*8201da88SMatthias Ringwald 				}
534*8201da88SMatthias Ringwald 				else
535*8201da88SMatthias Ringwald 				{
536*8201da88SMatthias Ringwald 					// Partamento effect - Play the new note after the current sample.
537*8201da88SMatthias Ringwald 					if( effect_op == EFFECT_TONE_PORTAMENTO )
538*8201da88SMatthias Ringwald 						enable_nxt_smp = 1;
539*8201da88SMatthias Ringwald 				}
540*8201da88SMatthias Ringwald 			}
541*8201da88SMatthias Ringwald 			else // Note without period : Trigger it after the current sample.
542*8201da88SMatthias Ringwald 				enable_nxt_smp = 1;
543*8201da88SMatthias Ringwald 
544*8201da88SMatthias Ringwald 			if ( enable_nxt_smp )
545*8201da88SMatthias Ringwald 			{
546*8201da88SMatthias Ringwald 				// Prepare the next sample retrigger after the current one
547*8201da88SMatthias Ringwald 				cptr->nxt_sampdata = mod->sampledata[cptr->sampnum];
548*8201da88SMatthias Ringwald 				cptr->nxt_length = GET_BGI_W( mod->song.samples[cptr->sampnum].length );
549*8201da88SMatthias Ringwald 				cptr->nxt_reppnt = GET_BGI_W( mod->song.samples[cptr->sampnum].reppnt );
550*8201da88SMatthias Ringwald 				cptr->nxt_replen = GET_BGI_W( mod->song.samples[cptr->sampnum].replen );
551*8201da88SMatthias Ringwald 
552*8201da88SMatthias Ringwald 				if(cptr->nxt_replen < 2)   // Protracker : don't play the sample if not looped...
553*8201da88SMatthias Ringwald 					cptr->nxt_sampdata = 0;
554*8201da88SMatthias Ringwald 
555*8201da88SMatthias Ringwald 				cptr->update_nxt_repeat = 1;
556*8201da88SMatthias Ringwald 			}
557a4cd9b30SMilanka Ringwald 
558a4cd9b30SMilanka Ringwald 			cptr->finetune = (mod->song.samples[cptr->sampnum].finetune) & 0xF;
559a4cd9b30SMilanka Ringwald 
560*8201da88SMatthias Ringwald 			if( effect_op != EFFECT_VIBRATO && effect_op != EFFECT_VOLSLIDE_VIBRATO )
561a4cd9b30SMilanka Ringwald 			{
562a4cd9b30SMilanka Ringwald 				cptr->vibraperiod = 0;
563a4cd9b30SMilanka Ringwald 				cptr->vibrapointeur = 0;
564a4cd9b30SMilanka Ringwald 			}
565a4cd9b30SMilanka Ringwald 		}
566a4cd9b30SMilanka Ringwald 
567*8201da88SMatthias Ringwald 		if( (sample != 0) && ( effect_op != EFFECT_VOLSLIDE_TONEPORTA ) )
568a4cd9b30SMilanka Ringwald 		{
569a4cd9b30SMilanka Ringwald 			cptr->volume = mod->song.samples[cptr->sampnum].volume;
570a4cd9b30SMilanka Ringwald 			cptr->volumeslide = 0;
571*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
572*8201da88SMatthias Ringwald 			cptr->volume_table = mod->volume_selection_table[cptr->volume];
573*8201da88SMatthias Ringwald #endif
574a4cd9b30SMilanka Ringwald 		}
575a4cd9b30SMilanka Ringwald 
576*8201da88SMatthias Ringwald 		if( ( effect_op != EFFECT_TONE_PORTAMENTO ) && ( effect_op != EFFECT_VOLSLIDE_TONEPORTA ) )
577a4cd9b30SMilanka Ringwald 		{
578a4cd9b30SMilanka Ringwald 			if ( period != 0 )
579a4cd9b30SMilanka Ringwald 				cptr->samppos = 0;
580a4cd9b30SMilanka Ringwald 		}
581a4cd9b30SMilanka Ringwald 
582a4cd9b30SMilanka Ringwald 		cptr->decalperiod = 0;
583a4cd9b30SMilanka Ringwald 		if( period )
584a4cd9b30SMilanka Ringwald 		{
585a4cd9b30SMilanka Ringwald 			if( cptr->finetune )
586a4cd9b30SMilanka Ringwald 			{
587*8201da88SMatthias Ringwald 				period_table_ptr = periodtable_finetune_ptr[cptr->finetune&0xF];
588*8201da88SMatthias Ringwald 				period = period_table_ptr[getnote(mod,period)];
589a4cd9b30SMilanka Ringwald 			}
590a4cd9b30SMilanka Ringwald 
591a4cd9b30SMilanka Ringwald 			cptr->period = period;
592a4cd9b30SMilanka Ringwald 		}
593a4cd9b30SMilanka Ringwald 	}
594a4cd9b30SMilanka Ringwald 
595a4cd9b30SMilanka Ringwald 	cptr->effect = 0;
596a4cd9b30SMilanka Ringwald 	cptr->parameffect = 0;
597a4cd9b30SMilanka Ringwald 	cptr->effect_code = effect;
598a4cd9b30SMilanka Ringwald 
599*8201da88SMatthias Ringwald #ifdef EFFECTS_USAGE_STATE
600*8201da88SMatthias Ringwald 	if(effect_op || ((effect_op==EFFECT_ARPEGGIO) && effect_param))
601*8201da88SMatthias Ringwald 	{
602*8201da88SMatthias Ringwald 		mod->effects_event_counts[ effect_op ]++;
603*8201da88SMatthias Ringwald 	}
604*8201da88SMatthias Ringwald 
605*8201da88SMatthias Ringwald 	if(effect_op == 0xE)
606*8201da88SMatthias Ringwald 		mod->effects_event_counts[ 0x10 + effect_param_h ]++;
607*8201da88SMatthias Ringwald #endif
608*8201da88SMatthias Ringwald 
609*8201da88SMatthias Ringwald 	switch ( effect_op )
610a4cd9b30SMilanka Ringwald 	{
611a4cd9b30SMilanka Ringwald 		case EFFECT_ARPEGGIO:
612a4cd9b30SMilanka Ringwald 			/*
613a4cd9b30SMilanka Ringwald 			[0]: Arpeggio
614a4cd9b30SMilanka Ringwald 			Where [0][x][y] means "play note, note+x semitones, note+y
615a4cd9b30SMilanka Ringwald 			semitones, then return to original note". The fluctuations are
616a4cd9b30SMilanka Ringwald 			carried out evenly spaced in one pattern division. They are usually
617a4cd9b30SMilanka Ringwald 			used to simulate chords, but this doesn't work too well. They are
618a4cd9b30SMilanka Ringwald 			also used to produce heavy vibrato. A major chord is when x=4, y=7.
619a4cd9b30SMilanka Ringwald 			A minor chord is when x=3, y=7.
620a4cd9b30SMilanka Ringwald 			*/
621a4cd9b30SMilanka Ringwald 
622*8201da88SMatthias Ringwald 			if( effect_param )
623a4cd9b30SMilanka Ringwald 			{
624a4cd9b30SMilanka Ringwald 				cptr->effect = EFFECT_ARPEGGIO;
625*8201da88SMatthias Ringwald 				cptr->parameffect = effect_param;
626a4cd9b30SMilanka Ringwald 
627a4cd9b30SMilanka Ringwald 				cptr->ArpIndex = 0;
628a4cd9b30SMilanka Ringwald 
629*8201da88SMatthias Ringwald 				curnote = getnote(mod,cptr->period);
630a4cd9b30SMilanka Ringwald 
631a4cd9b30SMilanka Ringwald 				cptr->Arpperiods[0] = cptr->period;
632a4cd9b30SMilanka Ringwald 
633*8201da88SMatthias Ringwald 				period_table_ptr = periodtable_finetune_ptr[cptr->finetune&0xF];
634a4cd9b30SMilanka Ringwald 
635*8201da88SMatthias Ringwald 				arpnote = curnote + (((cptr->parameffect>>4)&0xF));
636*8201da88SMatthias Ringwald 				if( arpnote >= MAXNOTES )
637*8201da88SMatthias Ringwald 					arpnote = (MAXNOTES) - 1;
638a4cd9b30SMilanka Ringwald 
639*8201da88SMatthias Ringwald 				cptr->Arpperiods[1] = period_table_ptr[arpnote];
640a4cd9b30SMilanka Ringwald 
641*8201da88SMatthias Ringwald 				arpnote = curnote + (((cptr->parameffect)&0xF));
642*8201da88SMatthias Ringwald 				if( arpnote >= MAXNOTES )
643*8201da88SMatthias Ringwald 					arpnote = (MAXNOTES) - 1;
644*8201da88SMatthias Ringwald 
645*8201da88SMatthias Ringwald 				cptr->Arpperiods[2] = period_table_ptr[arpnote];
646a4cd9b30SMilanka Ringwald 			}
647a4cd9b30SMilanka Ringwald 		break;
648a4cd9b30SMilanka Ringwald 
649a4cd9b30SMilanka Ringwald 		case EFFECT_PORTAMENTO_UP:
650a4cd9b30SMilanka Ringwald 			/*
651a4cd9b30SMilanka Ringwald 			[1]: Slide up
652a4cd9b30SMilanka Ringwald 			Where [1][x][y] means "smoothly decrease the period of current
653a4cd9b30SMilanka Ringwald 			sample by x*16+y after each tick in the division". The
654a4cd9b30SMilanka Ringwald 			ticks/division are set with the 'set speed' effect (see below). If
655a4cd9b30SMilanka Ringwald 			the period of the note being played is z, then the final period
656a4cd9b30SMilanka Ringwald 			will be z - (x*16 + y)*(ticks - 1). As the slide rate depends on
657a4cd9b30SMilanka Ringwald 			the speed, changing the speed will change the slide. You cannot
658a4cd9b30SMilanka Ringwald 			slide beyond the note B3 (period 113).
659a4cd9b30SMilanka Ringwald 			*/
660a4cd9b30SMilanka Ringwald 
661a4cd9b30SMilanka Ringwald 			cptr->effect = EFFECT_PORTAMENTO_UP;
662*8201da88SMatthias Ringwald 			cptr->parameffect = effect_param;
663a4cd9b30SMilanka Ringwald 		break;
664a4cd9b30SMilanka Ringwald 
665a4cd9b30SMilanka Ringwald 		case EFFECT_PORTAMENTO_DOWN:
666a4cd9b30SMilanka Ringwald 			/*
667a4cd9b30SMilanka Ringwald 			[2]: Slide down
668a4cd9b30SMilanka Ringwald 			Where [2][x][y] means "smoothly increase the period of current
669a4cd9b30SMilanka Ringwald 			sample by x*16+y after each tick in the division". Similar to [1],
670a4cd9b30SMilanka Ringwald 			but lowers the pitch. You cannot slide beyond the note C1 (period
671a4cd9b30SMilanka Ringwald 			856).
672a4cd9b30SMilanka Ringwald 			*/
673a4cd9b30SMilanka Ringwald 
674a4cd9b30SMilanka Ringwald 			cptr->effect = EFFECT_PORTAMENTO_DOWN;
675*8201da88SMatthias Ringwald 			cptr->parameffect = effect_param;
676a4cd9b30SMilanka Ringwald 		break;
677a4cd9b30SMilanka Ringwald 
678a4cd9b30SMilanka Ringwald 		case EFFECT_TONE_PORTAMENTO:
679a4cd9b30SMilanka Ringwald 			/*
680a4cd9b30SMilanka Ringwald 			[3]: Slide to note
681a4cd9b30SMilanka Ringwald 			Where [3][x][y] means "smoothly change the period of current sample
682a4cd9b30SMilanka Ringwald 			by x*16+y after each tick in the division, never sliding beyond
683a4cd9b30SMilanka Ringwald 			current period". The period-length in this channel's division is a
684a4cd9b30SMilanka Ringwald 			parameter to this effect, and hence is not played. Sliding to a
685a4cd9b30SMilanka Ringwald 			note is similar to effects [1] and [2], but the slide will not go
686a4cd9b30SMilanka Ringwald 			beyond the given period, and the direction is implied by that
687a4cd9b30SMilanka Ringwald 			period. If x and y are both 0, then the old slide will continue.
688a4cd9b30SMilanka Ringwald 			*/
689a4cd9b30SMilanka Ringwald 
690a4cd9b30SMilanka Ringwald 			cptr->effect = EFFECT_TONE_PORTAMENTO;
691*8201da88SMatthias Ringwald 			if( effect_param != 0 )
692a4cd9b30SMilanka Ringwald 			{
693*8201da88SMatthias Ringwald 				cptr->portaspeed = (short)( effect_param );
694a4cd9b30SMilanka Ringwald 			}
695a4cd9b30SMilanka Ringwald 
696a4cd9b30SMilanka Ringwald 			if(period!=0)
697a4cd9b30SMilanka Ringwald 			{
698a4cd9b30SMilanka Ringwald 				cptr->portaperiod = period;
699a4cd9b30SMilanka Ringwald 				cptr->period = operiod;
700a4cd9b30SMilanka Ringwald 			}
701a4cd9b30SMilanka Ringwald 		break;
702a4cd9b30SMilanka Ringwald 
703a4cd9b30SMilanka Ringwald 		case EFFECT_VIBRATO:
704a4cd9b30SMilanka Ringwald 			/*
705a4cd9b30SMilanka Ringwald 			[4]: Vibrato
706a4cd9b30SMilanka Ringwald 			Where [4][x][y] means "oscillate the sample pitch using a
707a4cd9b30SMilanka Ringwald 			particular waveform with amplitude y/16 semitones, such that (x *
708a4cd9b30SMilanka Ringwald 			ticks)/64 cycles occur in the division". The waveform is set using
709a4cd9b30SMilanka Ringwald 			effect [14][4]. By placing vibrato effects on consecutive
710a4cd9b30SMilanka Ringwald 			divisions, the vibrato effect can be maintained. If either x or y
711a4cd9b30SMilanka Ringwald 			are 0, then the old vibrato values will be used.
712a4cd9b30SMilanka Ringwald 			*/
713a4cd9b30SMilanka Ringwald 
714a4cd9b30SMilanka Ringwald 			cptr->effect = EFFECT_VIBRATO;
715*8201da88SMatthias Ringwald 			if( effect_param_l != 0 ) // Depth continue or change ?
716*8201da88SMatthias Ringwald 				cptr->vibraparam = ( cptr->vibraparam & 0xF0 ) | effect_param_l;
717*8201da88SMatthias Ringwald 			if( effect_param_h != 0 ) // Speed continue or change ?
718*8201da88SMatthias Ringwald 				cptr->vibraparam = ( cptr->vibraparam & 0x0F ) | ( effect_param_h << 4 );
719a4cd9b30SMilanka Ringwald 
720a4cd9b30SMilanka Ringwald 		break;
721a4cd9b30SMilanka Ringwald 
722a4cd9b30SMilanka Ringwald 		case EFFECT_VOLSLIDE_TONEPORTA:
723a4cd9b30SMilanka Ringwald 			/*
724a4cd9b30SMilanka Ringwald 			[5]: Continue 'Slide to note', but also do Volume slide
725a4cd9b30SMilanka Ringwald 			Where [5][x][y] means "either slide the volume up x*(ticks - 1) or
726a4cd9b30SMilanka Ringwald 			slide the volume down y*(ticks - 1), at the same time as continuing
727a4cd9b30SMilanka Ringwald 			the last 'Slide to note'". It is illegal for both x and y to be
728a4cd9b30SMilanka Ringwald 			non-zero. You cannot slide outside the volume range 0..64. The
729a4cd9b30SMilanka Ringwald 			period-length in this channel's division is a parameter to this
730a4cd9b30SMilanka Ringwald 			effect, and hence is not played.
731a4cd9b30SMilanka Ringwald 			*/
732a4cd9b30SMilanka Ringwald 
733a4cd9b30SMilanka Ringwald 			if( period != 0 )
734a4cd9b30SMilanka Ringwald 			{
735a4cd9b30SMilanka Ringwald 				cptr->portaperiod = period;
736a4cd9b30SMilanka Ringwald 				cptr->period = operiod;
737a4cd9b30SMilanka Ringwald 			}
738a4cd9b30SMilanka Ringwald 
739a4cd9b30SMilanka Ringwald 			cptr->effect = EFFECT_VOLSLIDE_TONEPORTA;
740*8201da88SMatthias Ringwald 			if( effect_param != 0 )
741*8201da88SMatthias Ringwald 				cptr->volumeslide = effect_param;
742a4cd9b30SMilanka Ringwald 
743a4cd9b30SMilanka Ringwald 		break;
744a4cd9b30SMilanka Ringwald 
745a4cd9b30SMilanka Ringwald 		case EFFECT_VOLSLIDE_VIBRATO:
746a4cd9b30SMilanka Ringwald 			/*
747a4cd9b30SMilanka Ringwald 			[6]: Continue 'Vibrato', but also do Volume slide
748a4cd9b30SMilanka Ringwald 			Where [6][x][y] means "either slide the volume up x*(ticks - 1) or
749a4cd9b30SMilanka Ringwald 			slide the volume down y*(ticks - 1), at the same time as continuing
750a4cd9b30SMilanka Ringwald 			the last 'Vibrato'". It is illegal for both x and y to be non-zero.
751a4cd9b30SMilanka Ringwald 			You cannot slide outside the volume range 0..64.
752a4cd9b30SMilanka Ringwald 			*/
753a4cd9b30SMilanka Ringwald 
754a4cd9b30SMilanka Ringwald 			cptr->effect = EFFECT_VOLSLIDE_VIBRATO;
755*8201da88SMatthias Ringwald 			if( effect_param != 0 )
756*8201da88SMatthias Ringwald 				cptr->volumeslide = effect_param;
757a4cd9b30SMilanka Ringwald 		break;
758a4cd9b30SMilanka Ringwald 
759a4cd9b30SMilanka Ringwald 		case EFFECT_SET_OFFSET:
760a4cd9b30SMilanka Ringwald 			/*
761a4cd9b30SMilanka Ringwald 			[9]: Set sample offset
762a4cd9b30SMilanka Ringwald 			Where [9][x][y] means "play the sample from offset x*4096 + y*256".
763a4cd9b30SMilanka Ringwald 			The offset is measured in words. If no sample is given, yet one is
764a4cd9b30SMilanka Ringwald 			still playing on this channel, it should be retriggered to the new
765a4cd9b30SMilanka Ringwald 			offset using the current volume.
766*8201da88SMatthias Ringwald 			If xy is 00, the previous value is used.
767a4cd9b30SMilanka Ringwald 			*/
768a4cd9b30SMilanka Ringwald 
769*8201da88SMatthias Ringwald 			cptr->samppos = ( ( ((muint)effect_param_h) << 12) + ( (((muint)effect_param_l) << 8) ) ) << 10;
770a4cd9b30SMilanka Ringwald 
771*8201da88SMatthias Ringwald 			if(!cptr->samppos)
772*8201da88SMatthias Ringwald 				cptr->samppos = cptr->last_set_offset;
773*8201da88SMatthias Ringwald 
774*8201da88SMatthias Ringwald 			cptr->last_set_offset = cptr->samppos;
775a4cd9b30SMilanka Ringwald 		break;
776a4cd9b30SMilanka Ringwald 
777a4cd9b30SMilanka Ringwald 		case EFFECT_VOLUME_SLIDE:
778a4cd9b30SMilanka Ringwald 			/*
779a4cd9b30SMilanka Ringwald 			[10]: Volume slide
780a4cd9b30SMilanka Ringwald 			Where [10][x][y] means "either slide the volume up x*(ticks - 1) or
781a4cd9b30SMilanka Ringwald 			slide the volume down y*(ticks - 1)". If both x and y are non-zero,
782a4cd9b30SMilanka Ringwald 			then the y value is ignored (assumed to be 0). You cannot slide
783a4cd9b30SMilanka Ringwald 			outside the volume range 0..64.
784a4cd9b30SMilanka Ringwald 			*/
785a4cd9b30SMilanka Ringwald 
786a4cd9b30SMilanka Ringwald 			cptr->effect = EFFECT_VOLUME_SLIDE;
787*8201da88SMatthias Ringwald 			cptr->volumeslide = effect_param;
788a4cd9b30SMilanka Ringwald 		break;
789a4cd9b30SMilanka Ringwald 
790a4cd9b30SMilanka Ringwald 		case EFFECT_JUMP_POSITION:
791a4cd9b30SMilanka Ringwald 			/*
792a4cd9b30SMilanka Ringwald 			[11]: Position Jump
793a4cd9b30SMilanka Ringwald 			Where [11][x][y] means "stop the pattern after this division, and
794a4cd9b30SMilanka Ringwald 			continue the song at song-position x*16+y". This shifts the
795a4cd9b30SMilanka Ringwald 			'pattern-cursor' in the pattern table (see above). Legal values for
796a4cd9b30SMilanka Ringwald 			x*16+y are from 0 to 127.
797a4cd9b30SMilanka Ringwald 			*/
798a4cd9b30SMilanka Ringwald 
799*8201da88SMatthias Ringwald 			mod->tablepos = effect_param;
800a4cd9b30SMilanka Ringwald 			if(mod->tablepos >= mod->song.length)
801a4cd9b30SMilanka Ringwald 				mod->tablepos = 0;
802a4cd9b30SMilanka Ringwald 			mod->patternpos = 0;
803a4cd9b30SMilanka Ringwald 			mod->jump_loop_effect = 1;
804a4cd9b30SMilanka Ringwald 
805a4cd9b30SMilanka Ringwald 		break;
806a4cd9b30SMilanka Ringwald 
807a4cd9b30SMilanka Ringwald 		case EFFECT_SET_VOLUME:
808a4cd9b30SMilanka Ringwald 			/*
809a4cd9b30SMilanka Ringwald 			[12]: Set volume
810a4cd9b30SMilanka Ringwald 			Where [12][x][y] means "set current sample's volume to x*16+y".
811a4cd9b30SMilanka Ringwald 			Legal volumes are 0..64.
812a4cd9b30SMilanka Ringwald 			*/
813a4cd9b30SMilanka Ringwald 
814*8201da88SMatthias Ringwald 			cptr->volume = effect_param;
815*8201da88SMatthias Ringwald 
816*8201da88SMatthias Ringwald 			if(cptr->volume > 64)
817*8201da88SMatthias Ringwald 				cptr->volume = 64;
818*8201da88SMatthias Ringwald 
819*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
820*8201da88SMatthias Ringwald 			cptr->volume_table = mod->volume_selection_table[cptr->volume];
821*8201da88SMatthias Ringwald #endif
822a4cd9b30SMilanka Ringwald 		break;
823a4cd9b30SMilanka Ringwald 
824a4cd9b30SMilanka Ringwald 		case EFFECT_PATTERN_BREAK:
825a4cd9b30SMilanka Ringwald 			/*
826a4cd9b30SMilanka Ringwald 			[13]: Pattern Break
827a4cd9b30SMilanka Ringwald 			Where [13][x][y] means "stop the pattern after this division, and
828a4cd9b30SMilanka Ringwald 			continue the song at the next pattern at division x*10+y" (the 10
829a4cd9b30SMilanka Ringwald 			is not a typo). Legal divisions are from 0 to 63 (note Protracker
830a4cd9b30SMilanka Ringwald 			exception above).
831a4cd9b30SMilanka Ringwald 			*/
832a4cd9b30SMilanka Ringwald 
833*8201da88SMatthias Ringwald 			mod->patternpos = ( ((muint)(effect_param_h) * 10) + effect_param_l );
834*8201da88SMatthias Ringwald 
835*8201da88SMatthias Ringwald 			if(mod->patternpos >= 64)
836*8201da88SMatthias Ringwald 				mod->patternpos = 63;
837*8201da88SMatthias Ringwald 
838*8201da88SMatthias Ringwald 			mod->patternpos *= mod->number_of_channels;
839*8201da88SMatthias Ringwald 
840*8201da88SMatthias Ringwald 			if(!mod->jump_loop_effect)
841*8201da88SMatthias Ringwald 			{
842a4cd9b30SMilanka Ringwald 				mod->tablepos++;
843a4cd9b30SMilanka Ringwald 				if(mod->tablepos >= mod->song.length)
844a4cd9b30SMilanka Ringwald 					mod->tablepos = 0;
845*8201da88SMatthias Ringwald 			}
846a4cd9b30SMilanka Ringwald 
847*8201da88SMatthias Ringwald 			mod->jump_loop_effect = 1;
848a4cd9b30SMilanka Ringwald 		break;
849a4cd9b30SMilanka Ringwald 
850a4cd9b30SMilanka Ringwald 		case EFFECT_EXTENDED:
851*8201da88SMatthias Ringwald 			switch( effect_param_h )
852a4cd9b30SMilanka Ringwald 			{
853a4cd9b30SMilanka Ringwald 				case EFFECT_E_FINE_PORTA_UP:
854a4cd9b30SMilanka Ringwald 					/*
855a4cd9b30SMilanka Ringwald 					[14][1]: Fineslide up
856a4cd9b30SMilanka Ringwald 					Where [14][1][x] means "decrement the period of the current sample
857a4cd9b30SMilanka Ringwald 					by x". The incrementing takes place at the beginning of the
858a4cd9b30SMilanka Ringwald 					division, and hence there is no actual sliding. You cannot slide
859a4cd9b30SMilanka Ringwald 					beyond the note B3 (period 113).
860a4cd9b30SMilanka Ringwald 					*/
861a4cd9b30SMilanka Ringwald 
862*8201da88SMatthias Ringwald 					cptr->period -= effect_param_l;
863a4cd9b30SMilanka Ringwald 					if( cptr->period < 113 )
864a4cd9b30SMilanka Ringwald 						cptr->period = 113;
865a4cd9b30SMilanka Ringwald 				break;
866a4cd9b30SMilanka Ringwald 
867a4cd9b30SMilanka Ringwald 				case EFFECT_E_FINE_PORTA_DOWN:
868a4cd9b30SMilanka Ringwald 					/*
869a4cd9b30SMilanka Ringwald 					[14][2]: Fineslide down
870a4cd9b30SMilanka Ringwald 					Where [14][2][x] means "increment the period of the current sample
871a4cd9b30SMilanka Ringwald 					by x". Similar to [14][1] but shifts the pitch down. You cannot
872a4cd9b30SMilanka Ringwald 					slide beyond the note C1 (period 856).
873a4cd9b30SMilanka Ringwald 					*/
874a4cd9b30SMilanka Ringwald 
875*8201da88SMatthias Ringwald 					cptr->period += effect_param_l;
876a4cd9b30SMilanka Ringwald 					if( cptr->period > 856 )
877a4cd9b30SMilanka Ringwald 						cptr->period = 856;
878a4cd9b30SMilanka Ringwald 				break;
879a4cd9b30SMilanka Ringwald 
880*8201da88SMatthias Ringwald 				case EFFECT_E_GLISSANDO_CTRL:
881*8201da88SMatthias Ringwald 					/*
882*8201da88SMatthias Ringwald 					[14][3]: Set glissando on/off
883*8201da88SMatthias Ringwald 					Where [14][3][x] means "set glissando ON if x is 1, OFF if x is 0".
884*8201da88SMatthias Ringwald 					Used in conjunction with [3] ('Slide to note'). If glissando is on,
885*8201da88SMatthias Ringwald 					then 'Slide to note' will slide in semitones, otherwise will
886*8201da88SMatthias Ringwald 					perform the default smooth slide.
887*8201da88SMatthias Ringwald 					*/
888*8201da88SMatthias Ringwald 
889*8201da88SMatthias Ringwald 					cptr->glissando = effect_param_l;
890*8201da88SMatthias Ringwald 				break;
891*8201da88SMatthias Ringwald 
892a4cd9b30SMilanka Ringwald 				case EFFECT_E_FINE_VOLSLIDE_UP:
893a4cd9b30SMilanka Ringwald 					/*
894a4cd9b30SMilanka Ringwald 					[14][10]: Fine volume slide up
895a4cd9b30SMilanka Ringwald 					Where [14][10][x] means "increment the volume of the current sample
896a4cd9b30SMilanka Ringwald 					by x". The incrementing takes place at the beginning of the
897a4cd9b30SMilanka Ringwald 					division, and hence there is no sliding. You cannot slide beyond
898a4cd9b30SMilanka Ringwald 					volume 64.
899a4cd9b30SMilanka Ringwald 					*/
900a4cd9b30SMilanka Ringwald 
901*8201da88SMatthias Ringwald 					cptr->volume += effect_param_l;
902a4cd9b30SMilanka Ringwald 					if( cptr->volume > 64 )
903a4cd9b30SMilanka Ringwald 						cptr->volume = 64;
904*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
905*8201da88SMatthias Ringwald 					cptr->volume_table = mod->volume_selection_table[cptr->volume];
906*8201da88SMatthias Ringwald #endif
907a4cd9b30SMilanka Ringwald 				break;
908a4cd9b30SMilanka Ringwald 
909a4cd9b30SMilanka Ringwald 				case EFFECT_E_FINE_VOLSLIDE_DOWN:
910a4cd9b30SMilanka Ringwald 					/*
911a4cd9b30SMilanka Ringwald 					[14][11]: Fine volume slide down
912a4cd9b30SMilanka Ringwald 					Where [14][11][x] means "decrement the volume of the current sample
913a4cd9b30SMilanka Ringwald 					by x". Similar to [14][10] but lowers volume. You cannot slide
914a4cd9b30SMilanka Ringwald 					beyond volume 0.
915a4cd9b30SMilanka Ringwald 					*/
916a4cd9b30SMilanka Ringwald 
917*8201da88SMatthias Ringwald 					cptr->volume -= effect_param_l;
918a4cd9b30SMilanka Ringwald 					if( cptr->volume > 200 )
919a4cd9b30SMilanka Ringwald 						cptr->volume = 0;
920*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
921*8201da88SMatthias Ringwald 					cptr->volume_table = mod->volume_selection_table[cptr->volume];
922*8201da88SMatthias Ringwald #endif
923*8201da88SMatthias Ringwald 				break;
924*8201da88SMatthias Ringwald 
925*8201da88SMatthias Ringwald 				case EFFECT_E_SET_FINETUNE:
926*8201da88SMatthias Ringwald 					/*
927*8201da88SMatthias Ringwald 					[14][5]: Set finetune value
928*8201da88SMatthias Ringwald 					Where [14][5][x] means "sets the finetune value of the current
929*8201da88SMatthias Ringwald 					sample to the signed nibble x". x has legal values of 0..15,
930*8201da88SMatthias Ringwald 					corresponding to signed nibbles 0..7,-8..-1 (see start of text for
931*8201da88SMatthias Ringwald 					more info on finetune values).
932*8201da88SMatthias Ringwald 					*/
933*8201da88SMatthias Ringwald 
934*8201da88SMatthias Ringwald 					cptr->finetune = effect_param_l;
935*8201da88SMatthias Ringwald 
936*8201da88SMatthias Ringwald 					if( period )
937*8201da88SMatthias Ringwald 					{
938*8201da88SMatthias Ringwald 						period_table_ptr = periodtable_finetune_ptr[cptr->finetune&0xF];
939*8201da88SMatthias Ringwald 						period = period_table_ptr[getnote(mod,period)];
940*8201da88SMatthias Ringwald 						cptr->period = period;
941*8201da88SMatthias Ringwald 					}
942*8201da88SMatthias Ringwald 
943a4cd9b30SMilanka Ringwald 				break;
944a4cd9b30SMilanka Ringwald 
945a4cd9b30SMilanka Ringwald 				case EFFECT_E_PATTERN_LOOP:
946a4cd9b30SMilanka Ringwald 					/*
947a4cd9b30SMilanka Ringwald 					[14][6]: Loop pattern
948a4cd9b30SMilanka Ringwald 					Where [14][6][x] means "set the start of a loop to this division if
949a4cd9b30SMilanka Ringwald 					x is 0, otherwise after this division, jump back to the start of a
950a4cd9b30SMilanka Ringwald 					loop and play it another x times before continuing". If the start
951a4cd9b30SMilanka Ringwald 					of the loop was not set, it will default to the start of the
952a4cd9b30SMilanka Ringwald 					current pattern. Hence 'loop pattern' cannot be performed across
953a4cd9b30SMilanka Ringwald 					multiple patterns. Note that loops do not support nesting, and you
954a4cd9b30SMilanka Ringwald 					may generate an infinite loop if you try to nest 'loop pattern's.
955a4cd9b30SMilanka Ringwald 					*/
956a4cd9b30SMilanka Ringwald 
957*8201da88SMatthias Ringwald 					if( effect_param_l )
958a4cd9b30SMilanka Ringwald 					{
959a4cd9b30SMilanka Ringwald 						if( cptr->patternloopcnt )
960a4cd9b30SMilanka Ringwald 						{
961a4cd9b30SMilanka Ringwald 							cptr->patternloopcnt--;
962a4cd9b30SMilanka Ringwald 							if( cptr->patternloopcnt )
963a4cd9b30SMilanka Ringwald 							{
964a4cd9b30SMilanka Ringwald 								mod->patternpos = cptr->patternloopstartpoint;
965a4cd9b30SMilanka Ringwald 								mod->jump_loop_effect = 1;
966a4cd9b30SMilanka Ringwald 							}
967a4cd9b30SMilanka Ringwald 							else
968a4cd9b30SMilanka Ringwald 							{
969a4cd9b30SMilanka Ringwald 								cptr->patternloopstartpoint = mod->patternpos ;
970a4cd9b30SMilanka Ringwald 							}
971a4cd9b30SMilanka Ringwald 						}
972a4cd9b30SMilanka Ringwald 						else
973a4cd9b30SMilanka Ringwald 						{
974*8201da88SMatthias Ringwald 							cptr->patternloopcnt = effect_param_l;
975a4cd9b30SMilanka Ringwald 							mod->patternpos = cptr->patternloopstartpoint;
976a4cd9b30SMilanka Ringwald 							mod->jump_loop_effect = 1;
977a4cd9b30SMilanka Ringwald 						}
978a4cd9b30SMilanka Ringwald 					}
979a4cd9b30SMilanka Ringwald 					else // Start point
980a4cd9b30SMilanka Ringwald 					{
981a4cd9b30SMilanka Ringwald 						cptr->patternloopstartpoint = mod->patternpos;
982a4cd9b30SMilanka Ringwald 					}
983a4cd9b30SMilanka Ringwald 
984a4cd9b30SMilanka Ringwald 				break;
985a4cd9b30SMilanka Ringwald 
986a4cd9b30SMilanka Ringwald 				case EFFECT_E_PATTERN_DELAY:
987a4cd9b30SMilanka Ringwald 					/*
988a4cd9b30SMilanka Ringwald 					[14][14]: Delay pattern
989a4cd9b30SMilanka Ringwald 					Where [14][14][x] means "after this division there will be a delay
990a4cd9b30SMilanka Ringwald 					equivalent to the time taken to play x divisions after which the
991a4cd9b30SMilanka Ringwald 					pattern will be resumed". The delay only relates to the
992a4cd9b30SMilanka Ringwald 					interpreting of new divisions, and all effects and previous notes
993a4cd9b30SMilanka Ringwald 					continue during delay.
994a4cd9b30SMilanka Ringwald 					*/
995a4cd9b30SMilanka Ringwald 
996*8201da88SMatthias Ringwald 					mod->patterndelay = effect_param_l;
997*8201da88SMatthias Ringwald 				break;
998*8201da88SMatthias Ringwald 
999*8201da88SMatthias Ringwald 				case EFFECT_E_RETRIGGER_NOTE:
1000*8201da88SMatthias Ringwald 					/*
1001*8201da88SMatthias Ringwald 					[14][9]: Retrigger sample
1002*8201da88SMatthias Ringwald 					 Where [14][9][x] means "trigger current sample every x ticks in
1003*8201da88SMatthias Ringwald 					 this division". If x is 0, then no retriggering is done (acts as if
1004*8201da88SMatthias Ringwald 					 no effect was chosen), otherwise the retriggering begins on the
1005*8201da88SMatthias Ringwald 					 first tick and then x ticks after that, etc.
1006*8201da88SMatthias Ringwald 					*/
1007*8201da88SMatthias Ringwald 
1008*8201da88SMatthias Ringwald 					if( effect_param_l )
1009*8201da88SMatthias Ringwald 					{
1010*8201da88SMatthias Ringwald 						cptr->effect = EFFECT_EXTENDED;
1011*8201da88SMatthias Ringwald 						cptr->parameffect = (EFFECT_E_RETRIGGER_NOTE<<4);
1012*8201da88SMatthias Ringwald 						cptr->retrig_param = effect_param_l;
1013*8201da88SMatthias Ringwald 						cptr->retrig_cnt = 0;
1014*8201da88SMatthias Ringwald 					}
1015a4cd9b30SMilanka Ringwald 				break;
1016a4cd9b30SMilanka Ringwald 
1017a4cd9b30SMilanka Ringwald 				case EFFECT_E_NOTE_CUT:
1018a4cd9b30SMilanka Ringwald 					/*
1019a4cd9b30SMilanka Ringwald 					[14][12]: Cut sample
1020a4cd9b30SMilanka Ringwald 					Where [14][12][x] means "after the current sample has been played
1021a4cd9b30SMilanka Ringwald 					for x ticks in this division, its volume will be set to 0". This
1022a4cd9b30SMilanka Ringwald 					implies that if x is 0, then you will not hear any of the sample.
1023a4cd9b30SMilanka Ringwald 					If you wish to insert "silence" in a pattern, it is better to use a
1024a4cd9b30SMilanka Ringwald 					"silence"-sample (see above) due to the lack of proper support for
1025a4cd9b30SMilanka Ringwald 					this effect.
1026a4cd9b30SMilanka Ringwald 					*/
1027*8201da88SMatthias Ringwald 
1028a4cd9b30SMilanka Ringwald 					cptr->effect = EFFECT_E_NOTE_CUT;
1029*8201da88SMatthias Ringwald 					cptr->cut_param = effect_param_l;
1030a4cd9b30SMilanka Ringwald 					if( !cptr->cut_param )
1031*8201da88SMatthias Ringwald 					{
1032a4cd9b30SMilanka Ringwald 						cptr->volume = 0;
1033*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
1034*8201da88SMatthias Ringwald 						cptr->volume_table = mod->volume_selection_table[cptr->volume];
1035*8201da88SMatthias Ringwald #endif
1036*8201da88SMatthias Ringwald 					}
1037*8201da88SMatthias Ringwald 				break;
1038*8201da88SMatthias Ringwald 
1039*8201da88SMatthias Ringwald 				case EFFECT_E_NOTE_DELAY:
1040*8201da88SMatthias Ringwald 					/*
1041*8201da88SMatthias Ringwald 					 Where [14][13][x] means "do not start this division's sample for
1042*8201da88SMatthias Ringwald 					 the first x ticks in this division, play the sample after this".
1043*8201da88SMatthias Ringwald 					 This implies that if x is 0, then you will hear no delay, but
1044*8201da88SMatthias Ringwald 					 actually there will be a VERY small delay. Note that this effect
1045*8201da88SMatthias Ringwald 					 only influences a sample if it was started in this division.
1046*8201da88SMatthias Ringwald 					*/
1047*8201da88SMatthias Ringwald 
1048*8201da88SMatthias Ringwald 					cptr->effect = EFFECT_EXTENDED;
1049*8201da88SMatthias Ringwald 					cptr->parameffect = (EFFECT_E_NOTE_DELAY<<4);
1050*8201da88SMatthias Ringwald 				break;
1051*8201da88SMatthias Ringwald 
1052*8201da88SMatthias Ringwald 				case EFFECT_E_INVERT_LOOP:
1053*8201da88SMatthias Ringwald 					/*
1054*8201da88SMatthias Ringwald 					Where [14][15][x] means "if x is greater than 0, then play the
1055*8201da88SMatthias Ringwald 					current sample's loop upside down at speed x". Each byte in the
1056*8201da88SMatthias Ringwald 					sample's loop will have its sign changed (negated). It will only
1057*8201da88SMatthias Ringwald 					work if the sample's loop (defined previously) is not too big. The
1058*8201da88SMatthias Ringwald 					speed is based on an internal table.
1059*8201da88SMatthias Ringwald 					*/
1060*8201da88SMatthias Ringwald 
1061*8201da88SMatthias Ringwald 					cptr->funkspeed = effect_param_l;
1062*8201da88SMatthias Ringwald 
1063*8201da88SMatthias Ringwald 					doFunk(cptr);
1064*8201da88SMatthias Ringwald 
1065a4cd9b30SMilanka Ringwald 				break;
1066a4cd9b30SMilanka Ringwald 
1067a4cd9b30SMilanka Ringwald 				default:
1068a4cd9b30SMilanka Ringwald 
1069a4cd9b30SMilanka Ringwald 				break;
1070a4cd9b30SMilanka Ringwald 			}
1071a4cd9b30SMilanka Ringwald 		break;
1072a4cd9b30SMilanka Ringwald 
1073a4cd9b30SMilanka Ringwald 		case 0xF:
1074a4cd9b30SMilanka Ringwald 			/*
1075a4cd9b30SMilanka Ringwald 			[15]: Set speed
1076a4cd9b30SMilanka Ringwald 			Where [15][x][y] means "set speed to x*16+y". Though it is nowhere
1077a4cd9b30SMilanka Ringwald 			near that simple. Let z = x*16+y. Depending on what values z takes,
1078a4cd9b30SMilanka Ringwald 			different units of speed are set, there being two: ticks/division
1079a4cd9b30SMilanka Ringwald 			and beats/minute (though this one is only a label and not strictly
1080a4cd9b30SMilanka Ringwald 			true). If z=0, then what should technically happen is that the
1081a4cd9b30SMilanka Ringwald 			module stops, but in practice it is treated as if z=1, because
1082a4cd9b30SMilanka Ringwald 			there is already a method for stopping the module (running out of
1083a4cd9b30SMilanka Ringwald 			patterns). If z<=32, then it means "set ticks/division to z"
1084a4cd9b30SMilanka Ringwald 			otherwise it means "set beats/minute to z" (convention says that
1085a4cd9b30SMilanka Ringwald 			this should read "If z<32.." but there are some composers out there
1086a4cd9b30SMilanka Ringwald 			that defy conventions). Default values are 6 ticks/division, and
1087a4cd9b30SMilanka Ringwald 			125 beats/minute (4 divisions = 1 beat). The beats/minute tag is
1088a4cd9b30SMilanka Ringwald 			only meaningful for 6 ticks/division. To get a more accurate view
1089a4cd9b30SMilanka Ringwald 			of how things work, use the following formula:
1090a4cd9b30SMilanka Ringwald 									 24 * beats/minute
1091a4cd9b30SMilanka Ringwald 				  divisions/minute = -----------------
1092a4cd9b30SMilanka Ringwald 									  ticks/division
1093a4cd9b30SMilanka Ringwald 			Hence divisions/minute range from 24.75 to 6120, eg. to get a value
1094a4cd9b30SMilanka Ringwald 			of 2000 divisions/minute use 3 ticks/division and 250 beats/minute.
1095a4cd9b30SMilanka Ringwald 			If multiple "set speed" effects are performed in a single division,
1096a4cd9b30SMilanka Ringwald 			the ones on higher-numbered channels take precedence over the ones
1097a4cd9b30SMilanka Ringwald 			on lower-numbered channels. This effect has a large number of
1098a4cd9b30SMilanka Ringwald 			different implementations, but the one described here has the
1099a4cd9b30SMilanka Ringwald 			widest usage.
1100a4cd9b30SMilanka Ringwald 			*/
1101a4cd9b30SMilanka Ringwald 
1102*8201da88SMatthias Ringwald 
1103*8201da88SMatthias Ringwald 			if( effect_param )
1104a4cd9b30SMilanka Ringwald 			{
1105*8201da88SMatthias Ringwald 
1106*8201da88SMatthias Ringwald 				if( effect_param < 0x20 )
1107a4cd9b30SMilanka Ringwald 				{
1108*8201da88SMatthias Ringwald 					mod->song.speed = effect_param;
1109a4cd9b30SMilanka Ringwald 				}
1110*8201da88SMatthias Ringwald 				else
1111*8201da88SMatthias Ringwald 				{   // effect_param >= 0x20
1112*8201da88SMatthias Ringwald 					///	 HZ = 2 * BPM / 5
1113*8201da88SMatthias Ringwald 					mod->bpm = effect_param;
1114a4cd9b30SMilanka Ringwald 				}
1115a4cd9b30SMilanka Ringwald 
1116*8201da88SMatthias Ringwald #ifdef HXCMOD_16BITS_TARGET
1117*8201da88SMatthias Ringwald 				// song.speed = 1 <> 31
1118*8201da88SMatthias Ringwald 				// playrate = 8000 <> 22050
1119*8201da88SMatthias Ringwald 				// bpm = 32 <> 255
1120*8201da88SMatthias Ringwald 
1121*8201da88SMatthias Ringwald 				mod->patternticksem = (muint)( ( (mulong)mod->playrate * 5 ) / ( (muint)mod->bpm * 2 ) );
1122*8201da88SMatthias Ringwald #else
1123*8201da88SMatthias Ringwald 				// song.speed = 1 <> 31
1124*8201da88SMatthias Ringwald 				// playrate = 8000 <> 96000
1125*8201da88SMatthias Ringwald 				// bpm = 32 <> 255
1126*8201da88SMatthias Ringwald 
1127*8201da88SMatthias Ringwald 				mod->patternticksem = ( ( mod->playrate * 5 ) / ( (mulong)mod->bpm * 2 ) );
1128*8201da88SMatthias Ringwald #endif
1129*8201da88SMatthias Ringwald 				mod->patternticksaim = mod->song.speed * mod->patternticksem;
1130a4cd9b30SMilanka Ringwald 			}
1131a4cd9b30SMilanka Ringwald 
1132a4cd9b30SMilanka Ringwald 		break;
1133a4cd9b30SMilanka Ringwald 
1134a4cd9b30SMilanka Ringwald 		default:
1135a4cd9b30SMilanka Ringwald 		// Unsupported effect
1136a4cd9b30SMilanka Ringwald 		break;
1137a4cd9b30SMilanka Ringwald 
1138a4cd9b30SMilanka Ringwald 	}
1139a4cd9b30SMilanka Ringwald 
1140a4cd9b30SMilanka Ringwald }
1141a4cd9b30SMilanka Ringwald 
1142*8201da88SMatthias Ringwald static void workeffect( modcontext * modctx, note * nptr, channel * cptr )
1143a4cd9b30SMilanka Ringwald {
1144*8201da88SMatthias Ringwald 	doFunk(cptr);
1145c5456c21SMilanka Ringwald 
1146a4cd9b30SMilanka Ringwald 	switch(cptr->effect)
1147a4cd9b30SMilanka Ringwald 	{
1148a4cd9b30SMilanka Ringwald 		case EFFECT_ARPEGGIO:
1149a4cd9b30SMilanka Ringwald 
1150a4cd9b30SMilanka Ringwald 			if( cptr->parameffect )
1151a4cd9b30SMilanka Ringwald 			{
1152a4cd9b30SMilanka Ringwald 				cptr->decalperiod = cptr->period - cptr->Arpperiods[cptr->ArpIndex];
1153a4cd9b30SMilanka Ringwald 
1154a4cd9b30SMilanka Ringwald 				cptr->ArpIndex++;
1155a4cd9b30SMilanka Ringwald 				if( cptr->ArpIndex>2 )
1156a4cd9b30SMilanka Ringwald 					cptr->ArpIndex = 0;
1157a4cd9b30SMilanka Ringwald 			}
1158a4cd9b30SMilanka Ringwald 		break;
1159a4cd9b30SMilanka Ringwald 
1160a4cd9b30SMilanka Ringwald 		case EFFECT_PORTAMENTO_UP:
1161a4cd9b30SMilanka Ringwald 
1162a4cd9b30SMilanka Ringwald 			if( cptr->period )
1163a4cd9b30SMilanka Ringwald 			{
1164a4cd9b30SMilanka Ringwald 				cptr->period -= cptr->parameffect;
1165a4cd9b30SMilanka Ringwald 
1166a4cd9b30SMilanka Ringwald 				if( cptr->period < 113 || cptr->period > 20000 )
1167a4cd9b30SMilanka Ringwald 					cptr->period = 113;
1168a4cd9b30SMilanka Ringwald 			}
1169a4cd9b30SMilanka Ringwald 
1170a4cd9b30SMilanka Ringwald 		break;
1171a4cd9b30SMilanka Ringwald 
1172a4cd9b30SMilanka Ringwald 		case EFFECT_PORTAMENTO_DOWN:
1173a4cd9b30SMilanka Ringwald 
1174a4cd9b30SMilanka Ringwald 			if( cptr->period )
1175a4cd9b30SMilanka Ringwald 			{
1176a4cd9b30SMilanka Ringwald 				cptr->period += cptr->parameffect;
1177a4cd9b30SMilanka Ringwald 
1178a4cd9b30SMilanka Ringwald 				if( cptr->period > 20000 )
1179a4cd9b30SMilanka Ringwald 					cptr->period = 20000;
1180a4cd9b30SMilanka Ringwald 			}
1181a4cd9b30SMilanka Ringwald 
1182a4cd9b30SMilanka Ringwald 		break;
1183a4cd9b30SMilanka Ringwald 
1184a4cd9b30SMilanka Ringwald 		case EFFECT_VOLSLIDE_TONEPORTA:
1185a4cd9b30SMilanka Ringwald 		case EFFECT_TONE_PORTAMENTO:
1186a4cd9b30SMilanka Ringwald 
1187a4cd9b30SMilanka Ringwald 			if( cptr->period && ( cptr->period != cptr->portaperiod ) && cptr->portaperiod )
1188a4cd9b30SMilanka Ringwald 			{
1189a4cd9b30SMilanka Ringwald 				if( cptr->period > cptr->portaperiod )
1190a4cd9b30SMilanka Ringwald 				{
1191a4cd9b30SMilanka Ringwald 					if( cptr->period - cptr->portaperiod >= cptr->portaspeed )
1192a4cd9b30SMilanka Ringwald 					{
1193a4cd9b30SMilanka Ringwald 						cptr->period -= cptr->portaspeed;
1194a4cd9b30SMilanka Ringwald 					}
1195a4cd9b30SMilanka Ringwald 					else
1196a4cd9b30SMilanka Ringwald 					{
1197a4cd9b30SMilanka Ringwald 						cptr->period = cptr->portaperiod;
1198a4cd9b30SMilanka Ringwald 					}
1199a4cd9b30SMilanka Ringwald 				}
1200a4cd9b30SMilanka Ringwald 				else
1201a4cd9b30SMilanka Ringwald 				{
1202a4cd9b30SMilanka Ringwald 					if( cptr->portaperiod - cptr->period >= cptr->portaspeed )
1203a4cd9b30SMilanka Ringwald 					{
1204a4cd9b30SMilanka Ringwald 						cptr->period += cptr->portaspeed;
1205a4cd9b30SMilanka Ringwald 					}
1206a4cd9b30SMilanka Ringwald 					else
1207a4cd9b30SMilanka Ringwald 					{
1208a4cd9b30SMilanka Ringwald 						cptr->period = cptr->portaperiod;
1209a4cd9b30SMilanka Ringwald 					}
1210a4cd9b30SMilanka Ringwald 				}
1211a4cd9b30SMilanka Ringwald 
1212a4cd9b30SMilanka Ringwald 				if( cptr->period == cptr->portaperiod )
1213a4cd9b30SMilanka Ringwald 				{
1214a4cd9b30SMilanka Ringwald 					// If the slide is over, don't let it to be retriggered.
1215a4cd9b30SMilanka Ringwald 					cptr->portaperiod = 0;
1216a4cd9b30SMilanka Ringwald 				}
1217a4cd9b30SMilanka Ringwald 			}
1218a4cd9b30SMilanka Ringwald 
1219*8201da88SMatthias Ringwald 			if( cptr->glissando )
1220*8201da88SMatthias Ringwald 			{
1221*8201da88SMatthias Ringwald 				// TODO : Glissando effect.
1222*8201da88SMatthias Ringwald 			}
1223*8201da88SMatthias Ringwald 
1224a4cd9b30SMilanka Ringwald 			if( cptr->effect == EFFECT_VOLSLIDE_TONEPORTA )
1225a4cd9b30SMilanka Ringwald 			{
1226*8201da88SMatthias Ringwald 				if( cptr->volumeslide & 0xF0 )
1227a4cd9b30SMilanka Ringwald 				{
1228*8201da88SMatthias Ringwald 					cptr->volume += ( cptr->volumeslide >> 4 );
1229a4cd9b30SMilanka Ringwald 
1230a4cd9b30SMilanka Ringwald 					if( cptr->volume > 63 )
1231a4cd9b30SMilanka Ringwald 						cptr->volume = 63;
1232a4cd9b30SMilanka Ringwald 				}
1233a4cd9b30SMilanka Ringwald 				else
1234a4cd9b30SMilanka Ringwald 				{
1235*8201da88SMatthias Ringwald 					cptr->volume -= ( cptr->volumeslide & 0x0F );
1236a4cd9b30SMilanka Ringwald 
1237a4cd9b30SMilanka Ringwald 					if( cptr->volume > 63 )
1238a4cd9b30SMilanka Ringwald 						cptr->volume = 0;
1239a4cd9b30SMilanka Ringwald 				}
1240*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
1241*8201da88SMatthias Ringwald 				cptr->volume_table = modctx->volume_selection_table[cptr->volume];
1242*8201da88SMatthias Ringwald #endif
1243a4cd9b30SMilanka Ringwald 			}
1244a4cd9b30SMilanka Ringwald 		break;
1245a4cd9b30SMilanka Ringwald 
1246a4cd9b30SMilanka Ringwald 		case EFFECT_VOLSLIDE_VIBRATO:
1247a4cd9b30SMilanka Ringwald 		case EFFECT_VIBRATO:
1248a4cd9b30SMilanka Ringwald 
1249a4cd9b30SMilanka Ringwald 			cptr->vibraperiod = ( (cptr->vibraparam&0xF) * sintable[cptr->vibrapointeur&0x1F] )>>7;
1250a4cd9b30SMilanka Ringwald 
1251a4cd9b30SMilanka Ringwald 			if( cptr->vibrapointeur > 31 )
1252a4cd9b30SMilanka Ringwald 				cptr->vibraperiod = -cptr->vibraperiod;
1253a4cd9b30SMilanka Ringwald 
1254*8201da88SMatthias Ringwald 			cptr->vibrapointeur = ( cptr->vibrapointeur + ( ( cptr->vibraparam>>4 ) & 0x0F) ) & 0x3F;
1255a4cd9b30SMilanka Ringwald 
1256a4cd9b30SMilanka Ringwald 			if( cptr->effect == EFFECT_VOLSLIDE_VIBRATO )
1257a4cd9b30SMilanka Ringwald 			{
1258*8201da88SMatthias Ringwald 				if( cptr->volumeslide & 0xF0 )
1259a4cd9b30SMilanka Ringwald 				{
1260a4cd9b30SMilanka Ringwald 					cptr->volume += ( cptr->volumeslide >> 4 );
1261a4cd9b30SMilanka Ringwald 
1262a4cd9b30SMilanka Ringwald 					if( cptr->volume > 64 )
1263a4cd9b30SMilanka Ringwald 						cptr->volume = 64;
1264a4cd9b30SMilanka Ringwald 				}
1265a4cd9b30SMilanka Ringwald 				else
1266a4cd9b30SMilanka Ringwald 				{
1267*8201da88SMatthias Ringwald 					cptr->volume -= cptr->volumeslide;
1268a4cd9b30SMilanka Ringwald 
1269a4cd9b30SMilanka Ringwald 					if( cptr->volume > 64 )
1270a4cd9b30SMilanka Ringwald 						cptr->volume = 0;
1271a4cd9b30SMilanka Ringwald 				}
1272*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
1273*8201da88SMatthias Ringwald 				cptr->volume_table = modctx->volume_selection_table[cptr->volume];
1274*8201da88SMatthias Ringwald #endif
1275*8201da88SMatthias Ringwald 			}
1276*8201da88SMatthias Ringwald 
1277a4cd9b30SMilanka Ringwald 		break;
1278a4cd9b30SMilanka Ringwald 
1279*8201da88SMatthias Ringwald 		case EFFECT_VOLUME_SLIDE:
1280*8201da88SMatthias Ringwald 
1281*8201da88SMatthias Ringwald 			if( cptr->volumeslide & 0xF0 )
1282*8201da88SMatthias Ringwald 			{
1283*8201da88SMatthias Ringwald 				cptr->volume += ( cptr->volumeslide >> 4 );
1284*8201da88SMatthias Ringwald 
1285*8201da88SMatthias Ringwald 				if( cptr->volume > 64 )
1286*8201da88SMatthias Ringwald 					cptr->volume = 64;
1287*8201da88SMatthias Ringwald 			}
1288*8201da88SMatthias Ringwald 			else
1289*8201da88SMatthias Ringwald 			{
1290*8201da88SMatthias Ringwald 				cptr->volume -= cptr->volumeslide;
1291*8201da88SMatthias Ringwald 
1292*8201da88SMatthias Ringwald 				if( cptr->volume > 64 )
1293*8201da88SMatthias Ringwald 					cptr->volume = 0;
1294*8201da88SMatthias Ringwald 			}
1295*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
1296*8201da88SMatthias Ringwald 			cptr->volume_table = modctx->volume_selection_table[cptr->volume];
1297*8201da88SMatthias Ringwald #endif
1298*8201da88SMatthias Ringwald 		break;
1299*8201da88SMatthias Ringwald 
1300*8201da88SMatthias Ringwald 		case EFFECT_EXTENDED:
1301*8201da88SMatthias Ringwald 			switch( cptr->parameffect >> 4 )
1302*8201da88SMatthias Ringwald 			{
1303*8201da88SMatthias Ringwald 
1304a4cd9b30SMilanka Ringwald 				case EFFECT_E_NOTE_CUT:
1305a4cd9b30SMilanka Ringwald 					if( cptr->cut_param )
1306a4cd9b30SMilanka Ringwald 						cptr->cut_param--;
1307a4cd9b30SMilanka Ringwald 
1308a4cd9b30SMilanka Ringwald 					if( !cptr->cut_param )
1309*8201da88SMatthias Ringwald 					{
1310a4cd9b30SMilanka Ringwald 						cptr->volume = 0;
1311*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
1312*8201da88SMatthias Ringwald 						cptr->volume_table = modctx->volume_selection_table[cptr->volume];
1313*8201da88SMatthias Ringwald #endif
1314*8201da88SMatthias Ringwald 					}
1315*8201da88SMatthias Ringwald 				break;
1316*8201da88SMatthias Ringwald 
1317*8201da88SMatthias Ringwald 				case EFFECT_E_RETRIGGER_NOTE:
1318*8201da88SMatthias Ringwald 					cptr->retrig_cnt++;
1319*8201da88SMatthias Ringwald 					if( cptr->retrig_cnt >= cptr->retrig_param )
1320*8201da88SMatthias Ringwald 					{
1321*8201da88SMatthias Ringwald 						cptr->retrig_cnt = 0;
1322*8201da88SMatthias Ringwald 
1323*8201da88SMatthias Ringwald 						cptr->sampdata = cptr->lst_sampdata;
1324*8201da88SMatthias Ringwald 						cptr->length = cptr->lst_length;
1325*8201da88SMatthias Ringwald 						cptr->reppnt = cptr->lst_reppnt;
1326*8201da88SMatthias Ringwald 						cptr->replen = cptr->lst_replen;
1327*8201da88SMatthias Ringwald 						cptr->samppos = 0;
1328*8201da88SMatthias Ringwald 					}
1329*8201da88SMatthias Ringwald 				break;
1330*8201da88SMatthias Ringwald 
1331*8201da88SMatthias Ringwald 				case EFFECT_E_NOTE_DELAY:
1332*8201da88SMatthias Ringwald 					if( cptr->note_delay )
1333*8201da88SMatthias Ringwald 					{
1334*8201da88SMatthias Ringwald 						if( (unsigned char)( cptr->note_delay - 1 ) == modctx->tick_cnt )
1335*8201da88SMatthias Ringwald 						{
1336*8201da88SMatthias Ringwald 							cptr->sampdata = cptr->dly_sampdata;
1337*8201da88SMatthias Ringwald 							cptr->length = cptr->dly_length;
1338*8201da88SMatthias Ringwald 							cptr->reppnt = cptr->dly_reppnt;
1339*8201da88SMatthias Ringwald 							cptr->replen = cptr->dly_replen;
1340*8201da88SMatthias Ringwald 
1341*8201da88SMatthias Ringwald 							cptr->lst_sampdata = cptr->sampdata;
1342*8201da88SMatthias Ringwald 							cptr->lst_length = cptr->length;
1343*8201da88SMatthias Ringwald 							cptr->lst_reppnt = cptr->reppnt;
1344*8201da88SMatthias Ringwald 							cptr->lst_replen = cptr->replen;
1345*8201da88SMatthias Ringwald 							cptr->note_delay = 0;
1346*8201da88SMatthias Ringwald 						}
1347*8201da88SMatthias Ringwald 					}
1348*8201da88SMatthias Ringwald 				break;
1349*8201da88SMatthias Ringwald 				default:
1350*8201da88SMatthias Ringwald 				break;
1351*8201da88SMatthias Ringwald 			}
1352a4cd9b30SMilanka Ringwald 		break;
1353a4cd9b30SMilanka Ringwald 
1354a4cd9b30SMilanka Ringwald 		default:
1355a4cd9b30SMilanka Ringwald 		break;
1356a4cd9b30SMilanka Ringwald 
1357a4cd9b30SMilanka Ringwald 	}
1358a4cd9b30SMilanka Ringwald 
1359a4cd9b30SMilanka Ringwald }
1360a4cd9b30SMilanka Ringwald 
1361a4cd9b30SMilanka Ringwald ///////////////////////////////////////////////////////////////////////////////////
1362a4cd9b30SMilanka Ringwald int hxcmod_init(modcontext * modctx)
1363a4cd9b30SMilanka Ringwald {
1364*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
1365*8201da88SMatthias Ringwald 	muint c;
1366*8201da88SMatthias Ringwald 	mint  i,j;
1367*8201da88SMatthias Ringwald #endif
1368a4cd9b30SMilanka Ringwald 	if( modctx )
1369a4cd9b30SMilanka Ringwald 	{
1370a4cd9b30SMilanka Ringwald 		memclear(modctx,0,sizeof(modcontext));
1371a4cd9b30SMilanka Ringwald 		modctx->playrate = 44100;
1372a4cd9b30SMilanka Ringwald 		modctx->stereo = 1;
1373a4cd9b30SMilanka Ringwald 		modctx->stereo_separation = 1;
1374a4cd9b30SMilanka Ringwald 		modctx->bits = 16;
1375a4cd9b30SMilanka Ringwald 		modctx->filter = 1;
1376a4cd9b30SMilanka Ringwald 
1377*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
1378*8201da88SMatthias Ringwald 		c = 0;
1379*8201da88SMatthias Ringwald 		for(i=0;i<65;i++)
1380a4cd9b30SMilanka Ringwald 		{
1381*8201da88SMatthias Ringwald 			for(j=-128;j<128;j++)
1382a4cd9b30SMilanka Ringwald 			{
1383*8201da88SMatthias Ringwald 				modctx->precalc_volume_array[c] = i * j;
1384*8201da88SMatthias Ringwald 				c++;
1385a4cd9b30SMilanka Ringwald 			}
1386*8201da88SMatthias Ringwald 
1387*8201da88SMatthias Ringwald 			modctx->volume_selection_table[i] = &modctx->precalc_volume_array[(i*256) + 128];
1388a4cd9b30SMilanka Ringwald 		}
1389*8201da88SMatthias Ringwald #endif
1390a4cd9b30SMilanka Ringwald 
1391a4cd9b30SMilanka Ringwald 		return 1;
1392a4cd9b30SMilanka Ringwald 	}
1393a4cd9b30SMilanka Ringwald 
1394a4cd9b30SMilanka Ringwald 	return 0;
1395a4cd9b30SMilanka Ringwald }
1396a4cd9b30SMilanka Ringwald 
1397*8201da88SMatthias Ringwald int hxcmod_setcfg(modcontext * modctx, int samplerate, int stereo_separation, int filter)
1398a4cd9b30SMilanka Ringwald {
1399a4cd9b30SMilanka Ringwald 	if( modctx )
1400a4cd9b30SMilanka Ringwald 	{
1401a4cd9b30SMilanka Ringwald 		modctx->playrate = samplerate;
1402a4cd9b30SMilanka Ringwald 
1403a4cd9b30SMilanka Ringwald 		if(stereo_separation < 4)
1404a4cd9b30SMilanka Ringwald 		{
1405a4cd9b30SMilanka Ringwald 			modctx->stereo_separation = stereo_separation;
1406a4cd9b30SMilanka Ringwald 		}
1407a4cd9b30SMilanka Ringwald 
1408a4cd9b30SMilanka Ringwald 		if( filter )
1409a4cd9b30SMilanka Ringwald 			modctx->filter = 1;
1410a4cd9b30SMilanka Ringwald 		else
1411a4cd9b30SMilanka Ringwald 			modctx->filter = 0;
1412a4cd9b30SMilanka Ringwald 
1413a4cd9b30SMilanka Ringwald 		return 1;
1414a4cd9b30SMilanka Ringwald 	}
1415a4cd9b30SMilanka Ringwald 
1416a4cd9b30SMilanka Ringwald 	return 0;
1417a4cd9b30SMilanka Ringwald }
1418a4cd9b30SMilanka Ringwald 
1419a4cd9b30SMilanka Ringwald int hxcmod_load( modcontext * modctx, void * mod_data, int mod_data_size )
1420a4cd9b30SMilanka Ringwald {
1421*8201da88SMatthias Ringwald 	muint i, j, max, digitfactor;
1422a4cd9b30SMilanka Ringwald 	sample *sptr;
1423a4cd9b30SMilanka Ringwald 	unsigned char * modmemory,* endmodmemory;
1424a4cd9b30SMilanka Ringwald 
1425a4cd9b30SMilanka Ringwald 	modmemory = (unsigned char *)mod_data;
1426a4cd9b30SMilanka Ringwald 	endmodmemory = modmemory + mod_data_size;
1427a4cd9b30SMilanka Ringwald 
1428a4cd9b30SMilanka Ringwald 	if( modmemory )
1429a4cd9b30SMilanka Ringwald 	{
1430a4cd9b30SMilanka Ringwald 		if( modctx )
1431a4cd9b30SMilanka Ringwald 		{
1432*8201da88SMatthias Ringwald #ifdef FULL_STATE
1433*8201da88SMatthias Ringwald 			memclear(&(modctx->effects_event_counts),0,sizeof(modctx->effects_event_counts));
1434*8201da88SMatthias Ringwald #endif
1435*8201da88SMatthias Ringwald 			memcopy(&(modctx->song),modmemory,1084);
1436a4cd9b30SMilanka Ringwald 
1437a4cd9b30SMilanka Ringwald 			i = 0;
1438a4cd9b30SMilanka Ringwald 			modctx->number_of_channels = 0;
1439*8201da88SMatthias Ringwald 			while(modlist[i].numberofchannels && !modctx->number_of_channels)
1440a4cd9b30SMilanka Ringwald 			{
1441*8201da88SMatthias Ringwald 				digitfactor = 0;
1442*8201da88SMatthias Ringwald 
1443*8201da88SMatthias Ringwald 				j = 0;
1444*8201da88SMatthias Ringwald 				while( j < 4 )
1445a4cd9b30SMilanka Ringwald 				{
1446*8201da88SMatthias Ringwald 					if( modlist[i].signature[j] == '$' )
1447*8201da88SMatthias Ringwald 					{
1448*8201da88SMatthias Ringwald 						if(digitfactor)
1449*8201da88SMatthias Ringwald 							digitfactor *= 10;
1450*8201da88SMatthias Ringwald 						else
1451*8201da88SMatthias Ringwald 							digitfactor = 1;
1452*8201da88SMatthias Ringwald 					}
1453*8201da88SMatthias Ringwald 					j++;
1454*8201da88SMatthias Ringwald 				}
1455*8201da88SMatthias Ringwald 
1456*8201da88SMatthias Ringwald 				modctx->number_of_channels = 0;
1457*8201da88SMatthias Ringwald 
1458*8201da88SMatthias Ringwald 				j = 0;
1459*8201da88SMatthias Ringwald 				while( j < 4 )
1460*8201da88SMatthias Ringwald 				{
1461*8201da88SMatthias Ringwald 					if( (modlist[i].signature[j] == modctx->song.signature[j]) || modlist[i].signature[j] == '$' )
1462*8201da88SMatthias Ringwald 					{
1463*8201da88SMatthias Ringwald 						if( modlist[i].signature[j] == '$' )
1464*8201da88SMatthias Ringwald 						{
1465*8201da88SMatthias Ringwald 							if(modctx->song.signature[j] >= '0' && modctx->song.signature[j] <= '9')
1466*8201da88SMatthias Ringwald 							{
1467*8201da88SMatthias Ringwald 								modctx->number_of_channels += (modctx->song.signature[j] - '0') * digitfactor;
1468*8201da88SMatthias Ringwald 								digitfactor /= 10;
1469*8201da88SMatthias Ringwald 							}
1470*8201da88SMatthias Ringwald 							else
1471*8201da88SMatthias Ringwald 							{
1472*8201da88SMatthias Ringwald 								modctx->number_of_channels = 0;
1473*8201da88SMatthias Ringwald 								break;
1474*8201da88SMatthias Ringwald 							}
1475*8201da88SMatthias Ringwald 						}
1476*8201da88SMatthias Ringwald 						j++;
1477*8201da88SMatthias Ringwald 					}
1478*8201da88SMatthias Ringwald 					else
1479*8201da88SMatthias Ringwald 					{
1480*8201da88SMatthias Ringwald 						modctx->number_of_channels = 0;
1481*8201da88SMatthias Ringwald 						break;
1482*8201da88SMatthias Ringwald 					}
1483*8201da88SMatthias Ringwald 				}
1484*8201da88SMatthias Ringwald 
1485*8201da88SMatthias Ringwald 				if( j == 4 )
1486*8201da88SMatthias Ringwald 				{
1487*8201da88SMatthias Ringwald 					if(!modctx->number_of_channels)
1488a4cd9b30SMilanka Ringwald 						modctx->number_of_channels = modlist[i].numberofchannels;
1489a4cd9b30SMilanka Ringwald 				}
1490a4cd9b30SMilanka Ringwald 
1491a4cd9b30SMilanka Ringwald 				i++;
1492a4cd9b30SMilanka Ringwald 			}
1493a4cd9b30SMilanka Ringwald 
1494a4cd9b30SMilanka Ringwald 			if( !modctx->number_of_channels )
1495a4cd9b30SMilanka Ringwald 			{
1496a4cd9b30SMilanka Ringwald 				// 15 Samples modules support
1497a4cd9b30SMilanka Ringwald 				// Shift the whole datas to make it look likes a standard 4 channels mod.
1498*8201da88SMatthias Ringwald 				memcopy(&(modctx->song.signature), "M.K.", 4);
1499a4cd9b30SMilanka Ringwald 				memcopy(&(modctx->song.length), &(modctx->song.samples[15]), 130);
1500a4cd9b30SMilanka Ringwald 				memclear(&(modctx->song.samples[15]), 0, 480);
1501a4cd9b30SMilanka Ringwald 				modmemory += 600;
1502a4cd9b30SMilanka Ringwald 				modctx->number_of_channels = 4;
1503a4cd9b30SMilanka Ringwald 			}
1504a4cd9b30SMilanka Ringwald 			else
1505a4cd9b30SMilanka Ringwald 			{
1506a4cd9b30SMilanka Ringwald 				modmemory += 1084;
1507a4cd9b30SMilanka Ringwald 			}
1508a4cd9b30SMilanka Ringwald 
1509*8201da88SMatthias Ringwald 			if( modctx->number_of_channels > NUMMAXCHANNELS )
1510*8201da88SMatthias Ringwald 				return 0; // Too much channels ! - Increase/define HXCMOD_MAXCHANNELS !
1511*8201da88SMatthias Ringwald 
1512a4cd9b30SMilanka Ringwald 			if( modmemory >= endmodmemory )
1513a4cd9b30SMilanka Ringwald 				return 0; // End passed ? - Probably a bad file !
1514a4cd9b30SMilanka Ringwald 
1515a4cd9b30SMilanka Ringwald 			// Patterns loading
1516a4cd9b30SMilanka Ringwald 			for (i = max = 0; i < 128; i++)
1517a4cd9b30SMilanka Ringwald 			{
1518a4cd9b30SMilanka Ringwald 				while (max <= modctx->song.patterntable[i])
1519a4cd9b30SMilanka Ringwald 				{
1520a4cd9b30SMilanka Ringwald 					modctx->patterndata[max] = (note*)modmemory;
1521a4cd9b30SMilanka Ringwald 					modmemory += (256*modctx->number_of_channels);
1522a4cd9b30SMilanka Ringwald 					max++;
1523a4cd9b30SMilanka Ringwald 
1524a4cd9b30SMilanka Ringwald 					if( modmemory >= endmodmemory )
1525a4cd9b30SMilanka Ringwald 						return 0; // End passed ? - Probably a bad file !
1526a4cd9b30SMilanka Ringwald 				}
1527a4cd9b30SMilanka Ringwald 			}
1528a4cd9b30SMilanka Ringwald 
1529a4cd9b30SMilanka Ringwald 			for (i = 0; i < 31; i++)
1530a4cd9b30SMilanka Ringwald 				modctx->sampledata[i]=0;
1531a4cd9b30SMilanka Ringwald 
1532a4cd9b30SMilanka Ringwald 			// Samples loading
1533a4cd9b30SMilanka Ringwald 			for (i = 0, sptr = modctx->song.samples; i <31; i++, sptr++)
1534a4cd9b30SMilanka Ringwald 			{
1535a4cd9b30SMilanka Ringwald 				if (sptr->length == 0) continue;
1536a4cd9b30SMilanka Ringwald 
1537afc6fe18SMatthias Ringwald 				modctx->sampledata[i] = (mchar*)modmemory;
1538*8201da88SMatthias Ringwald 				modmemory += (GET_BGI_W(sptr->length)*2);
1539a4cd9b30SMilanka Ringwald 
1540*8201da88SMatthias Ringwald 				if (GET_BGI_W(sptr->replen) + GET_BGI_W(sptr->reppnt) > GET_BGI_W(sptr->length))
1541*8201da88SMatthias Ringwald 					sptr->replen = GET_BGI_W((GET_BGI_W(sptr->length) - GET_BGI_W(sptr->reppnt)));
1542a4cd9b30SMilanka Ringwald 
1543a4cd9b30SMilanka Ringwald 				if( modmemory > endmodmemory )
1544a4cd9b30SMilanka Ringwald 					return 0; // End passed ? - Probably a bad file !
1545a4cd9b30SMilanka Ringwald 			}
1546a4cd9b30SMilanka Ringwald 
1547a4cd9b30SMilanka Ringwald 			// States init
1548a4cd9b30SMilanka Ringwald 
1549a4cd9b30SMilanka Ringwald 			modctx->tablepos = 0;
1550a4cd9b30SMilanka Ringwald 			modctx->patternpos = 0;
1551a4cd9b30SMilanka Ringwald 			modctx->song.speed = 6;
1552a4cd9b30SMilanka Ringwald 			modctx->bpm = 125;
1553a4cd9b30SMilanka Ringwald 
1554*8201da88SMatthias Ringwald #ifdef HXCMOD_16BITS_TARGET
1555*8201da88SMatthias Ringwald 			// song.speed = 1 <> 31
1556*8201da88SMatthias Ringwald 			// playrate = 8000 <> 22050
1557*8201da88SMatthias Ringwald 			// bpm = 32 <> 255
1558a4cd9b30SMilanka Ringwald 
1559*8201da88SMatthias Ringwald 			modctx->patternticksem = (muint)( ( (mulong)modctx->playrate * 5 ) / ( (muint)modctx->bpm * 2 ) );
1560*8201da88SMatthias Ringwald #else
1561*8201da88SMatthias Ringwald 			// song.speed = 1 <> 31
1562*8201da88SMatthias Ringwald 			// playrate = 8000 <> 96000
1563*8201da88SMatthias Ringwald 			// bpm = 32 <> 255
1564*8201da88SMatthias Ringwald 
1565*8201da88SMatthias Ringwald 			modctx->patternticksem = ( ( modctx->playrate * 5 ) / ( (mulong)modctx->bpm * 2 ) );
1566*8201da88SMatthias Ringwald #endif
1567*8201da88SMatthias Ringwald 			modctx->patternticksaim = modctx->song.speed * modctx->patternticksem;
1568*8201da88SMatthias Ringwald 
1569*8201da88SMatthias Ringwald 			modctx->patternticks = modctx->patternticksaim + 1;
1570*8201da88SMatthias Ringwald 
1571*8201da88SMatthias Ringwald 			modctx->sampleticksconst = ((3546894UL * 16) / modctx->playrate) << 6; //8448*428/playrate;
1572a4cd9b30SMilanka Ringwald 
1573a4cd9b30SMilanka Ringwald 			for(i=0; i < modctx->number_of_channels; i++)
1574a4cd9b30SMilanka Ringwald 			{
1575a4cd9b30SMilanka Ringwald 				modctx->channels[i].volume = 0;
1576a4cd9b30SMilanka Ringwald 				modctx->channels[i].period = 0;
1577*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
1578*8201da88SMatthias Ringwald 				modctx->channels[i].volume_table = modctx->volume_selection_table[0];
1579*8201da88SMatthias Ringwald #endif
1580a4cd9b30SMilanka Ringwald 			}
1581a4cd9b30SMilanka Ringwald 
1582a4cd9b30SMilanka Ringwald 			modctx->mod_loaded = 1;
1583a4cd9b30SMilanka Ringwald 
1584a4cd9b30SMilanka Ringwald 			return 1;
1585a4cd9b30SMilanka Ringwald 		}
1586a4cd9b30SMilanka Ringwald 	}
1587a4cd9b30SMilanka Ringwald 
1588a4cd9b30SMilanka Ringwald 	return 0;
1589a4cd9b30SMilanka Ringwald }
1590a4cd9b30SMilanka Ringwald 
1591*8201da88SMatthias Ringwald void hxcmod_fillbuffer(modcontext * modctx, msample * outbuffer, mssize nbsample, tracker_buffer_state * trkbuf)
1592a4cd9b30SMilanka Ringwald {
1593*8201da88SMatthias Ringwald 	mssize i;
1594*8201da88SMatthias Ringwald 	muint  j;
1595*8201da88SMatthias Ringwald 	muint c;
1596*8201da88SMatthias Ringwald 
1597a4cd9b30SMilanka Ringwald 	unsigned long k;
1598a4cd9b30SMilanka Ringwald 	unsigned int state_remaining_steps;
1599*8201da88SMatthias Ringwald 
1600*8201da88SMatthias Ringwald #ifdef HXCMOD_OUTPUT_FILTER
1601*8201da88SMatthias Ringwald #ifndef HXCMOD_MONO_OUTPUT
1602*8201da88SMatthias Ringwald 	int ll,tl;
1603*8201da88SMatthias Ringwald #endif
1604*8201da88SMatthias Ringwald 	int lr,tr;
1605*8201da88SMatthias Ringwald #endif
1606*8201da88SMatthias Ringwald 
1607*8201da88SMatthias Ringwald #ifndef HXCMOD_MONO_OUTPUT
1608*8201da88SMatthias Ringwald 	int l;
1609*8201da88SMatthias Ringwald #endif
1610*8201da88SMatthias Ringwald 	int r;
1611*8201da88SMatthias Ringwald 
1612a4cd9b30SMilanka Ringwald 	short finalperiod;
1613a4cd9b30SMilanka Ringwald 	note	*nptr;
1614*8201da88SMatthias Ringwald 	channel *cptr;
1615a4cd9b30SMilanka Ringwald 
1616a4cd9b30SMilanka Ringwald 	if( modctx && outbuffer )
1617a4cd9b30SMilanka Ringwald 	{
1618a4cd9b30SMilanka Ringwald 		if(modctx->mod_loaded)
1619a4cd9b30SMilanka Ringwald 		{
1620a4cd9b30SMilanka Ringwald 			state_remaining_steps = 0;
1621a4cd9b30SMilanka Ringwald 
1622*8201da88SMatthias Ringwald #ifdef HXCMOD_STATE_REPORT_SUPPORT
1623a4cd9b30SMilanka Ringwald 			if( trkbuf )
1624a4cd9b30SMilanka Ringwald 			{
1625a4cd9b30SMilanka Ringwald 				trkbuf->cur_rd_index = 0;
1626a4cd9b30SMilanka Ringwald 
1627a4cd9b30SMilanka Ringwald 				memcopy(trkbuf->name,modctx->song.title,sizeof(modctx->song.title));
1628a4cd9b30SMilanka Ringwald 
1629a4cd9b30SMilanka Ringwald 				for(i=0;i<31;i++)
1630a4cd9b30SMilanka Ringwald 				{
1631a4cd9b30SMilanka Ringwald 					memcopy(trkbuf->instruments[i].name,modctx->song.samples[i].name,sizeof(trkbuf->instruments[i].name));
1632a4cd9b30SMilanka Ringwald 				}
1633a4cd9b30SMilanka Ringwald 			}
1634*8201da88SMatthias Ringwald #endif
1635a4cd9b30SMilanka Ringwald 
1636*8201da88SMatthias Ringwald #ifdef HXCMOD_OUTPUT_FILTER
1637*8201da88SMatthias Ringwald 	#ifndef HXCMOD_MONO_OUTPUT
1638a4cd9b30SMilanka Ringwald 			ll = modctx->last_l_sample;
1639*8201da88SMatthias Ringwald 	#endif
1640a4cd9b30SMilanka Ringwald 			lr = modctx->last_r_sample;
1641*8201da88SMatthias Ringwald #endif
1642a4cd9b30SMilanka Ringwald 
1643a4cd9b30SMilanka Ringwald 			for (i = 0; i < nbsample; i++)
1644a4cd9b30SMilanka Ringwald 			{
1645a4cd9b30SMilanka Ringwald 				//---------------------------------------
1646a4cd9b30SMilanka Ringwald 				if( modctx->patternticks++ > modctx->patternticksaim )
1647a4cd9b30SMilanka Ringwald 				{
1648a4cd9b30SMilanka Ringwald 					if( !modctx->patterndelay )
1649a4cd9b30SMilanka Ringwald 					{
1650a4cd9b30SMilanka Ringwald 						nptr = modctx->patterndata[modctx->song.patterntable[modctx->tablepos]];
1651a4cd9b30SMilanka Ringwald 						nptr = nptr + modctx->patternpos;
1652a4cd9b30SMilanka Ringwald 						cptr = modctx->channels;
1653a4cd9b30SMilanka Ringwald 
1654*8201da88SMatthias Ringwald 						modctx->tick_cnt = 0;
1655*8201da88SMatthias Ringwald 
1656a4cd9b30SMilanka Ringwald 						modctx->patternticks = 0;
1657a4cd9b30SMilanka Ringwald 						modctx->patterntickse = 0;
1658a4cd9b30SMilanka Ringwald 
1659a4cd9b30SMilanka Ringwald 						for(c=0;c<modctx->number_of_channels;c++)
1660a4cd9b30SMilanka Ringwald 						{
1661*8201da88SMatthias Ringwald 							worknote((note*)(nptr), (channel*)(cptr),(char)(c+1),modctx);
1662*8201da88SMatthias Ringwald 
1663*8201da88SMatthias Ringwald 							if (cptr->period != 0)
1664*8201da88SMatthias Ringwald 							{
1665*8201da88SMatthias Ringwald 								finalperiod = cptr->period - cptr->decalperiod - cptr->vibraperiod;
1666*8201da88SMatthias Ringwald 								if (finalperiod)
1667*8201da88SMatthias Ringwald 								{
1668*8201da88SMatthias Ringwald 									cptr->sampinc = ((modctx->sampleticksconst) / finalperiod);
1669*8201da88SMatthias Ringwald 								}
1670*8201da88SMatthias Ringwald 								else
1671*8201da88SMatthias Ringwald 								{
1672*8201da88SMatthias Ringwald 									cptr->sampinc = 0;
1673*8201da88SMatthias Ringwald 								}
1674*8201da88SMatthias Ringwald 							}
1675*8201da88SMatthias Ringwald 							else
1676*8201da88SMatthias Ringwald 								cptr->sampinc = 0;
1677*8201da88SMatthias Ringwald 
1678*8201da88SMatthias Ringwald 							nptr++;
1679*8201da88SMatthias Ringwald 							cptr++;
1680a4cd9b30SMilanka Ringwald 						}
1681a4cd9b30SMilanka Ringwald 
1682a4cd9b30SMilanka Ringwald 						if( !modctx->jump_loop_effect )
1683a4cd9b30SMilanka Ringwald 							modctx->patternpos += modctx->number_of_channels;
1684a4cd9b30SMilanka Ringwald 						else
1685a4cd9b30SMilanka Ringwald 							modctx->jump_loop_effect = 0;
1686a4cd9b30SMilanka Ringwald 
1687a4cd9b30SMilanka Ringwald 						if( modctx->patternpos == 64*modctx->number_of_channels )
1688a4cd9b30SMilanka Ringwald 						{
1689a4cd9b30SMilanka Ringwald 							modctx->tablepos++;
1690a4cd9b30SMilanka Ringwald 							modctx->patternpos = 0;
1691a4cd9b30SMilanka Ringwald 							if(modctx->tablepos >= modctx->song.length)
1692a4cd9b30SMilanka Ringwald 								modctx->tablepos = 0;
1693a4cd9b30SMilanka Ringwald 						}
1694a4cd9b30SMilanka Ringwald 					}
1695a4cd9b30SMilanka Ringwald 					else
1696a4cd9b30SMilanka Ringwald 					{
1697a4cd9b30SMilanka Ringwald 						modctx->patterndelay--;
1698a4cd9b30SMilanka Ringwald 						modctx->patternticks = 0;
1699a4cd9b30SMilanka Ringwald 						modctx->patterntickse = 0;
1700*8201da88SMatthias Ringwald 						modctx->tick_cnt = 0;
1701a4cd9b30SMilanka Ringwald 					}
1702a4cd9b30SMilanka Ringwald 
1703a4cd9b30SMilanka Ringwald 				}
1704a4cd9b30SMilanka Ringwald 
1705*8201da88SMatthias Ringwald 				if (modctx->patterntickse++ > modctx->patternticksem)
1706a4cd9b30SMilanka Ringwald 				{
1707a4cd9b30SMilanka Ringwald 					nptr = modctx->patterndata[modctx->song.patterntable[modctx->tablepos]];
1708a4cd9b30SMilanka Ringwald 					nptr = nptr + modctx->patternpos;
1709a4cd9b30SMilanka Ringwald 					cptr = modctx->channels;
1710a4cd9b30SMilanka Ringwald 
1711a4cd9b30SMilanka Ringwald 					for(c=0;c<modctx->number_of_channels;c++)
1712a4cd9b30SMilanka Ringwald 					{
1713*8201da88SMatthias Ringwald 						workeffect( modctx, nptr, cptr );
1714*8201da88SMatthias Ringwald 
1715*8201da88SMatthias Ringwald 						if (cptr->period != 0)
1716*8201da88SMatthias Ringwald 						{
1717*8201da88SMatthias Ringwald 							finalperiod = cptr->period - cptr->decalperiod - cptr->vibraperiod;
1718*8201da88SMatthias Ringwald 							if (finalperiod)
1719*8201da88SMatthias Ringwald 							{
1720*8201da88SMatthias Ringwald 								cptr->sampinc = ((modctx->sampleticksconst) / finalperiod);
1721*8201da88SMatthias Ringwald 							}
1722*8201da88SMatthias Ringwald 							else
1723*8201da88SMatthias Ringwald 							{
1724*8201da88SMatthias Ringwald 								cptr->sampinc = 0;
1725*8201da88SMatthias Ringwald 							}
1726*8201da88SMatthias Ringwald 						}
1727*8201da88SMatthias Ringwald 						else
1728*8201da88SMatthias Ringwald 							cptr->sampinc = 0;
1729*8201da88SMatthias Ringwald 
1730*8201da88SMatthias Ringwald 						nptr++;
1731*8201da88SMatthias Ringwald 						cptr++;
1732a4cd9b30SMilanka Ringwald 					}
1733a4cd9b30SMilanka Ringwald 
1734*8201da88SMatthias Ringwald 					modctx->tick_cnt++;
1735a4cd9b30SMilanka Ringwald 					modctx->patterntickse = 0;
1736a4cd9b30SMilanka Ringwald 				}
1737a4cd9b30SMilanka Ringwald 
1738a4cd9b30SMilanka Ringwald 				//---------------------------------------
1739a4cd9b30SMilanka Ringwald 
1740*8201da88SMatthias Ringwald #ifdef HXCMOD_STATE_REPORT_SUPPORT
1741a4cd9b30SMilanka Ringwald 				if( trkbuf && !state_remaining_steps )
1742a4cd9b30SMilanka Ringwald 				{
1743a4cd9b30SMilanka Ringwald 					if( trkbuf->nb_of_state < trkbuf->nb_max_of_state )
1744a4cd9b30SMilanka Ringwald 					{
1745a4cd9b30SMilanka Ringwald 						memclear(&trkbuf->track_state_buf[trkbuf->nb_of_state],0,sizeof(tracker_state));
1746a4cd9b30SMilanka Ringwald 					}
1747a4cd9b30SMilanka Ringwald 				}
1748*8201da88SMatthias Ringwald #endif
1749a4cd9b30SMilanka Ringwald 
1750*8201da88SMatthias Ringwald #ifndef HXCMOD_MONO_OUTPUT
1751a4cd9b30SMilanka Ringwald 				l=0;
1752*8201da88SMatthias Ringwald #endif
1753a4cd9b30SMilanka Ringwald 				r=0;
1754a4cd9b30SMilanka Ringwald 
1755a4cd9b30SMilanka Ringwald 				for( j = 0, cptr = modctx->channels; j < modctx->number_of_channels ; j++, cptr++)
1756a4cd9b30SMilanka Ringwald 				{
1757a4cd9b30SMilanka Ringwald 					if( cptr->period != 0 )
1758a4cd9b30SMilanka Ringwald 					{
1759*8201da88SMatthias Ringwald 						cptr->samppos += cptr->sampinc;
1760a4cd9b30SMilanka Ringwald 
1761*8201da88SMatthias Ringwald 						if( cptr->replen < 2 )
1762a4cd9b30SMilanka Ringwald 						{
1763*8201da88SMatthias Ringwald 							if( ( cptr->samppos >> 11) >= cptr->length )
1764a4cd9b30SMilanka Ringwald 							{
1765a4cd9b30SMilanka Ringwald 								cptr->length = 0;
1766a4cd9b30SMilanka Ringwald 								cptr->reppnt = 0;
1767a4cd9b30SMilanka Ringwald 
1768*8201da88SMatthias Ringwald 								if(cptr->update_nxt_repeat)
1769*8201da88SMatthias Ringwald 								{
1770*8201da88SMatthias Ringwald 									cptr->replen = cptr->nxt_replen;
1771*8201da88SMatthias Ringwald 									cptr->reppnt = cptr->nxt_reppnt;
1772*8201da88SMatthias Ringwald 									cptr->sampdata = cptr->nxt_sampdata;
1773*8201da88SMatthias Ringwald 									cptr->length = cptr->nxt_length;
1774*8201da88SMatthias Ringwald 
1775*8201da88SMatthias Ringwald 									cptr->lst_sampdata = cptr->sampdata;
1776*8201da88SMatthias Ringwald 									cptr->lst_length = cptr->length;
1777*8201da88SMatthias Ringwald 									cptr->lst_reppnt = cptr->reppnt;
1778*8201da88SMatthias Ringwald 									cptr->lst_replen = cptr->replen;
1779*8201da88SMatthias Ringwald 
1780*8201da88SMatthias Ringwald 									cptr->update_nxt_repeat = 0;
1781*8201da88SMatthias Ringwald 								}
1782*8201da88SMatthias Ringwald 
1783a4cd9b30SMilanka Ringwald 								if( cptr->length )
1784*8201da88SMatthias Ringwald 									cptr->samppos = cptr->samppos % (((unsigned long)cptr->length)<<11);
1785a4cd9b30SMilanka Ringwald 								else
1786a4cd9b30SMilanka Ringwald 									cptr->samppos = 0;
1787a4cd9b30SMilanka Ringwald 							}
1788a4cd9b30SMilanka Ringwald 						}
1789a4cd9b30SMilanka Ringwald 						else
1790a4cd9b30SMilanka Ringwald 						{
1791*8201da88SMatthias Ringwald 							if( ( cptr->samppos >> 11 ) >= (unsigned long)(cptr->replen+cptr->reppnt) )
1792a4cd9b30SMilanka Ringwald 							{
1793*8201da88SMatthias Ringwald 								if( cptr->update_nxt_repeat )
1794*8201da88SMatthias Ringwald 								{
1795*8201da88SMatthias Ringwald 									cptr->replen = cptr->nxt_replen;
1796*8201da88SMatthias Ringwald 									cptr->reppnt = cptr->nxt_reppnt;
1797*8201da88SMatthias Ringwald 									cptr->sampdata = cptr->nxt_sampdata;
1798*8201da88SMatthias Ringwald 									cptr->length = cptr->nxt_length;
1799*8201da88SMatthias Ringwald 
1800*8201da88SMatthias Ringwald 									cptr->lst_sampdata = cptr->sampdata;
1801*8201da88SMatthias Ringwald 									cptr->lst_length = cptr->length;
1802*8201da88SMatthias Ringwald 									cptr->lst_reppnt = cptr->reppnt;
1803*8201da88SMatthias Ringwald 									cptr->lst_replen = cptr->replen;
1804*8201da88SMatthias Ringwald 
1805*8201da88SMatthias Ringwald 									cptr->update_nxt_repeat = 0;
1806*8201da88SMatthias Ringwald 								}
1807*8201da88SMatthias Ringwald 
1808*8201da88SMatthias Ringwald 								if( cptr->sampdata )
1809*8201da88SMatthias Ringwald 								{
1810*8201da88SMatthias Ringwald 									cptr->samppos = ((unsigned long)(cptr->reppnt)<<11) + (cptr->samppos % ((unsigned long)(cptr->replen+cptr->reppnt)<<11));
1811*8201da88SMatthias Ringwald 								}
1812a4cd9b30SMilanka Ringwald 							}
1813a4cd9b30SMilanka Ringwald 						}
1814a4cd9b30SMilanka Ringwald 
1815a4cd9b30SMilanka Ringwald 						k = cptr->samppos >> 10;
1816a4cd9b30SMilanka Ringwald 
1817*8201da88SMatthias Ringwald #ifdef HXCMOD_MONO_OUTPUT
1818*8201da88SMatthias Ringwald 						if( cptr->sampdata!=0 )
1819a4cd9b30SMilanka Ringwald 						{
1820*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
1821*8201da88SMatthias Ringwald 							r += cptr->volume_table[cptr->sampdata[k]];
1822*8201da88SMatthias Ringwald #else
1823a4cd9b30SMilanka Ringwald 							r += ( cptr->sampdata[k] *  cptr->volume );
1824*8201da88SMatthias Ringwald #endif
1825a4cd9b30SMilanka Ringwald 						}
1826*8201da88SMatthias Ringwald #else
1827*8201da88SMatthias Ringwald 						if (cptr->sampdata != 0)
1828a4cd9b30SMilanka Ringwald 						{
1829*8201da88SMatthias Ringwald 							if ( !(j & 3) || ((j & 3) == 3) )
1830*8201da88SMatthias Ringwald 							{
1831*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
1832*8201da88SMatthias Ringwald 								l += cptr->volume_table[cptr->sampdata[k]];
1833*8201da88SMatthias Ringwald #else
1834a4cd9b30SMilanka Ringwald 								l += (cptr->sampdata[k] * cptr->volume);
1835*8201da88SMatthias Ringwald #endif
1836a4cd9b30SMilanka Ringwald 							}
1837*8201da88SMatthias Ringwald 							else
1838*8201da88SMatthias Ringwald 							{
1839*8201da88SMatthias Ringwald #ifdef HXCMOD_USE_PRECALC_VOLUME_TABLE
1840*8201da88SMatthias Ringwald 								r += cptr->volume_table[cptr->sampdata[k]];
1841*8201da88SMatthias Ringwald #else
1842*8201da88SMatthias Ringwald 								r += (cptr->sampdata[k] * cptr->volume);
1843*8201da88SMatthias Ringwald #endif
1844*8201da88SMatthias Ringwald 							}
1845*8201da88SMatthias Ringwald 						}
1846*8201da88SMatthias Ringwald #endif
1847a4cd9b30SMilanka Ringwald 
1848*8201da88SMatthias Ringwald #ifdef HXCMOD_STATE_REPORT_SUPPORT
1849a4cd9b30SMilanka Ringwald 						if( trkbuf && !state_remaining_steps )
1850a4cd9b30SMilanka Ringwald 						{
1851a4cd9b30SMilanka Ringwald 							if( trkbuf->nb_of_state < trkbuf->nb_max_of_state )
1852a4cd9b30SMilanka Ringwald 							{
1853a4cd9b30SMilanka Ringwald 								trkbuf->track_state_buf[trkbuf->nb_of_state].number_of_tracks = modctx->number_of_channels;
1854a4cd9b30SMilanka Ringwald 								trkbuf->track_state_buf[trkbuf->nb_of_state].buf_index = i;
1855a4cd9b30SMilanka Ringwald 								trkbuf->track_state_buf[trkbuf->nb_of_state].cur_pattern = modctx->song.patterntable[modctx->tablepos];
1856a4cd9b30SMilanka Ringwald 								trkbuf->track_state_buf[trkbuf->nb_of_state].cur_pattern_pos = modctx->patternpos / modctx->number_of_channels;
1857a4cd9b30SMilanka Ringwald 								trkbuf->track_state_buf[trkbuf->nb_of_state].cur_pattern_table_pos = modctx->tablepos;
1858a4cd9b30SMilanka Ringwald 								trkbuf->track_state_buf[trkbuf->nb_of_state].bpm = modctx->bpm;
1859a4cd9b30SMilanka Ringwald 								trkbuf->track_state_buf[trkbuf->nb_of_state].speed = modctx->song.speed;
1860a4cd9b30SMilanka Ringwald 								trkbuf->track_state_buf[trkbuf->nb_of_state].tracks[j].cur_effect = cptr->effect_code;
1861a4cd9b30SMilanka Ringwald 								trkbuf->track_state_buf[trkbuf->nb_of_state].tracks[j].cur_parameffect = cptr->parameffect;
1862*8201da88SMatthias Ringwald 								if(cptr->sampinc)
1863*8201da88SMatthias Ringwald 									trkbuf->track_state_buf[trkbuf->nb_of_state].tracks[j].cur_period = (muint)(modctx->sampleticksconst / cptr->sampinc);
1864*8201da88SMatthias Ringwald 								else
1865*8201da88SMatthias Ringwald 									trkbuf->track_state_buf[trkbuf->nb_of_state].tracks[j].cur_period = 0;
1866a4cd9b30SMilanka Ringwald 								trkbuf->track_state_buf[trkbuf->nb_of_state].tracks[j].cur_volume = cptr->volume;
1867a4cd9b30SMilanka Ringwald 								trkbuf->track_state_buf[trkbuf->nb_of_state].tracks[j].instrument_number = (unsigned char)cptr->sampnum;
1868a4cd9b30SMilanka Ringwald 							}
1869a4cd9b30SMilanka Ringwald 						}
1870*8201da88SMatthias Ringwald #endif
1871a4cd9b30SMilanka Ringwald 					}
1872a4cd9b30SMilanka Ringwald 				}
1873a4cd9b30SMilanka Ringwald 
1874*8201da88SMatthias Ringwald #ifdef HXCMOD_STATE_REPORT_SUPPORT
1875a4cd9b30SMilanka Ringwald 				if( trkbuf && !state_remaining_steps )
1876a4cd9b30SMilanka Ringwald 				{
1877a4cd9b30SMilanka Ringwald 					state_remaining_steps = trkbuf->sample_step;
1878a4cd9b30SMilanka Ringwald 
1879a4cd9b30SMilanka Ringwald 					if(trkbuf->nb_of_state < trkbuf->nb_max_of_state)
1880a4cd9b30SMilanka Ringwald 						trkbuf->nb_of_state++;
1881a4cd9b30SMilanka Ringwald 				}
1882a4cd9b30SMilanka Ringwald 				else
1883*8201da88SMatthias Ringwald #endif
1884a4cd9b30SMilanka Ringwald 				{
1885a4cd9b30SMilanka Ringwald 					state_remaining_steps--;
1886a4cd9b30SMilanka Ringwald 				}
1887a4cd9b30SMilanka Ringwald 
1888*8201da88SMatthias Ringwald #ifdef HXCMOD_MONO_OUTPUT
1889*8201da88SMatthias Ringwald 
1890*8201da88SMatthias Ringwald 	#ifdef HXCMOD_OUTPUT_FILTER
1891*8201da88SMatthias Ringwald 				tr = (short)r;
1892*8201da88SMatthias Ringwald 
1893*8201da88SMatthias Ringwald 				if ( modctx->filter )
1894*8201da88SMatthias Ringwald 				{
1895*8201da88SMatthias Ringwald 					// Filter
1896*8201da88SMatthias Ringwald 					r = (r+lr)>>1;
1897*8201da88SMatthias Ringwald 				}
1898*8201da88SMatthias Ringwald 	#endif
1899*8201da88SMatthias Ringwald 
1900*8201da88SMatthias Ringwald 	#ifdef HXCMOD_CLIPPING_CHECK
1901*8201da88SMatthias Ringwald 				// Level limitation
1902*8201da88SMatthias Ringwald 				if( r > 32767 ) r = 32767;
1903*8201da88SMatthias Ringwald 				if( r < -32768 ) r = -32768;
1904*8201da88SMatthias Ringwald 	#endif
1905*8201da88SMatthias Ringwald 				// Store the final sample.
1906*8201da88SMatthias Ringwald 	#ifdef HXCMOD_8BITS_OUTPUT
1907*8201da88SMatthias Ringwald 
1908*8201da88SMatthias Ringwald 		#ifdef HXCMOD_UNSIGNED_OUTPUT
1909*8201da88SMatthias Ringwald 				*outbuffer++ = (r >> 8) + 127;
1910*8201da88SMatthias Ringwald 		#else
1911*8201da88SMatthias Ringwald 				*outbuffer++ = r >> 8;
1912*8201da88SMatthias Ringwald 		#endif
1913*8201da88SMatthias Ringwald 
1914*8201da88SMatthias Ringwald 	#else
1915*8201da88SMatthias Ringwald 
1916*8201da88SMatthias Ringwald 		#ifdef HXCMOD_UNSIGNED_OUTPUT
1917*8201da88SMatthias Ringwald 				*outbuffer++ = r + 32767;
1918*8201da88SMatthias Ringwald 		#else
1919*8201da88SMatthias Ringwald 				*outbuffer++ = r;
1920*8201da88SMatthias Ringwald 		#endif
1921*8201da88SMatthias Ringwald 
1922*8201da88SMatthias Ringwald 	#endif
1923*8201da88SMatthias Ringwald 
1924*8201da88SMatthias Ringwald 	#ifdef HXCMOD_OUTPUT_FILTER
1925*8201da88SMatthias Ringwald 				lr = tr;
1926*8201da88SMatthias Ringwald 	#endif
1927*8201da88SMatthias Ringwald 
1928*8201da88SMatthias Ringwald #else
1929*8201da88SMatthias Ringwald 
1930*8201da88SMatthias Ringwald 	#ifdef HXCMOD_OUTPUT_FILTER
1931a4cd9b30SMilanka Ringwald 				tl = (short)l;
1932a4cd9b30SMilanka Ringwald 				tr = (short)r;
1933a4cd9b30SMilanka Ringwald 
1934a4cd9b30SMilanka Ringwald 				if ( modctx->filter )
1935a4cd9b30SMilanka Ringwald 				{
1936a4cd9b30SMilanka Ringwald 					// Filter
1937a4cd9b30SMilanka Ringwald 					l = (l+ll)>>1;
1938a4cd9b30SMilanka Ringwald 					r = (r+lr)>>1;
1939a4cd9b30SMilanka Ringwald 				}
1940*8201da88SMatthias Ringwald 	#endif
1941a4cd9b30SMilanka Ringwald 
1942*8201da88SMatthias Ringwald 	#ifdef HXCMOD_OUTPUT_STEREO_MIX
1943a4cd9b30SMilanka Ringwald 				if ( modctx->stereo_separation == 1 )
1944a4cd9b30SMilanka Ringwald 				{
1945a4cd9b30SMilanka Ringwald 					// Left & Right Stereo panning
1946a4cd9b30SMilanka Ringwald 					l = (l+(r>>1));
1947a4cd9b30SMilanka Ringwald 					r = (r+(l>>1));
1948a4cd9b30SMilanka Ringwald 				}
1949*8201da88SMatthias Ringwald 	#endif
1950a4cd9b30SMilanka Ringwald 
1951*8201da88SMatthias Ringwald 	#ifdef HXCMOD_CLIPPING_CHECK
1952a4cd9b30SMilanka Ringwald 				// Level limitation
1953a4cd9b30SMilanka Ringwald 				if( l > 32767 ) l = 32767;
1954a4cd9b30SMilanka Ringwald 				if( l < -32768 ) l = -32768;
1955a4cd9b30SMilanka Ringwald 				if( r > 32767 ) r = 32767;
1956a4cd9b30SMilanka Ringwald 				if( r < -32768 ) r = -32768;
1957*8201da88SMatthias Ringwald 	#endif
1958a4cd9b30SMilanka Ringwald 				// Store the final sample.
1959a4cd9b30SMilanka Ringwald 
1960*8201da88SMatthias Ringwald 
1961*8201da88SMatthias Ringwald 	#ifdef HXCMOD_8BITS_OUTPUT
1962*8201da88SMatthias Ringwald 
1963*8201da88SMatthias Ringwald 		#ifdef HXCMOD_UNSIGNED_OUTPUT
1964*8201da88SMatthias Ringwald 				*outbuffer++ = ( l >> 8 ) + 127;
1965*8201da88SMatthias Ringwald 				*outbuffer++ = ( r >> 8 ) + 127;
1966*8201da88SMatthias Ringwald 		#else
1967*8201da88SMatthias Ringwald 				*outbuffer++ = l >> 8;
1968*8201da88SMatthias Ringwald 				*outbuffer++ = r >> 8;
1969*8201da88SMatthias Ringwald 		#endif
1970*8201da88SMatthias Ringwald 
1971*8201da88SMatthias Ringwald 	#else
1972*8201da88SMatthias Ringwald 
1973*8201da88SMatthias Ringwald 		#ifdef HXCMOD_UNSIGNED_OUTPUT
1974*8201da88SMatthias Ringwald 				*outbuffer++ = l + 32767;
1975*8201da88SMatthias Ringwald 				*outbuffer++ = r + 32767;
1976*8201da88SMatthias Ringwald 		#else
1977*8201da88SMatthias Ringwald 				*outbuffer++ = l;
1978*8201da88SMatthias Ringwald 				*outbuffer++ = r;
1979*8201da88SMatthias Ringwald 		#endif
1980*8201da88SMatthias Ringwald 
1981*8201da88SMatthias Ringwald 	#endif
1982*8201da88SMatthias Ringwald 
1983*8201da88SMatthias Ringwald 	#ifdef HXCMOD_OUTPUT_FILTER
1984a4cd9b30SMilanka Ringwald 				ll = tl;
1985a4cd9b30SMilanka Ringwald 				lr = tr;
1986*8201da88SMatthias Ringwald 	#endif
1987*8201da88SMatthias Ringwald 
1988*8201da88SMatthias Ringwald #endif // HXCMOD_MONO_OUTPUT
1989a4cd9b30SMilanka Ringwald 
1990a4cd9b30SMilanka Ringwald 			}
1991a4cd9b30SMilanka Ringwald 
1992*8201da88SMatthias Ringwald #ifdef HXCMOD_OUTPUT_FILTER
1993*8201da88SMatthias Ringwald 	#ifndef HXCMOD_MONO_OUTPUT
1994a4cd9b30SMilanka Ringwald 			modctx->last_l_sample = ll;
1995*8201da88SMatthias Ringwald 	#endif
1996a4cd9b30SMilanka Ringwald 			modctx->last_r_sample = lr;
1997*8201da88SMatthias Ringwald #endif
1998a4cd9b30SMilanka Ringwald 		}
1999a4cd9b30SMilanka Ringwald 		else
2000a4cd9b30SMilanka Ringwald 		{
2001a4cd9b30SMilanka Ringwald 			for (i = 0; i < nbsample; i++)
2002a4cd9b30SMilanka Ringwald 			{
2003a4cd9b30SMilanka Ringwald 				// Mod not loaded. Return blank buffer.
2004*8201da88SMatthias Ringwald #ifdef HXCMOD_MONO_OUTPUT
2005*8201da88SMatthias Ringwald 				outbuffer[i] = 0;
2006*8201da88SMatthias Ringwald #else
2007*8201da88SMatthias Ringwald 				*outbuffer++ = 0;
2008*8201da88SMatthias Ringwald 				*outbuffer++ = 0;
2009*8201da88SMatthias Ringwald #endif
2010a4cd9b30SMilanka Ringwald 			}
2011a4cd9b30SMilanka Ringwald 
2012*8201da88SMatthias Ringwald #ifdef HXCMOD_STATE_REPORT_SUPPORT
2013a4cd9b30SMilanka Ringwald 			if(trkbuf)
2014a4cd9b30SMilanka Ringwald 			{
2015a4cd9b30SMilanka Ringwald 				trkbuf->nb_of_state = 0;
2016a4cd9b30SMilanka Ringwald 				trkbuf->cur_rd_index = 0;
2017a4cd9b30SMilanka Ringwald 				trkbuf->name[0] = 0;
2018a4cd9b30SMilanka Ringwald 				memclear(trkbuf->track_state_buf,0,sizeof(tracker_state) * trkbuf->nb_max_of_state);
2019a4cd9b30SMilanka Ringwald 				memclear(trkbuf->instruments,0,sizeof(trkbuf->instruments));
2020a4cd9b30SMilanka Ringwald 			}
2021*8201da88SMatthias Ringwald #endif
2022a4cd9b30SMilanka Ringwald 		}
2023a4cd9b30SMilanka Ringwald 	}
2024a4cd9b30SMilanka Ringwald }
2025a4cd9b30SMilanka Ringwald 
2026a4cd9b30SMilanka Ringwald void hxcmod_unload( modcontext * modctx )
2027a4cd9b30SMilanka Ringwald {
2028a4cd9b30SMilanka Ringwald 	if(modctx)
2029a4cd9b30SMilanka Ringwald 	{
2030a4cd9b30SMilanka Ringwald 		memclear(&modctx->song,0,sizeof(modctx->song));
2031a4cd9b30SMilanka Ringwald 		memclear(&modctx->sampledata,0,sizeof(modctx->sampledata));
2032a4cd9b30SMilanka Ringwald 		memclear(&modctx->patterndata,0,sizeof(modctx->patterndata));
2033a4cd9b30SMilanka Ringwald 		modctx->tablepos = 0;
2034a4cd9b30SMilanka Ringwald 		modctx->patternpos = 0;
2035a4cd9b30SMilanka Ringwald 		modctx->patterndelay  = 0;
2036a4cd9b30SMilanka Ringwald 		modctx->jump_loop_effect = 0;
2037a4cd9b30SMilanka Ringwald 		modctx->bpm = 0;
2038a4cd9b30SMilanka Ringwald 		modctx->patternticks = 0;
2039a4cd9b30SMilanka Ringwald 		modctx->patterntickse = 0;
2040a4cd9b30SMilanka Ringwald 		modctx->patternticksaim = 0;
2041a4cd9b30SMilanka Ringwald 		modctx->sampleticksconst = 0;
2042a4cd9b30SMilanka Ringwald 
2043a4cd9b30SMilanka Ringwald 		memclear(modctx->channels,0,sizeof(modctx->channels));
2044a4cd9b30SMilanka Ringwald 
2045a4cd9b30SMilanka Ringwald 		modctx->number_of_channels = 0;
2046a4cd9b30SMilanka Ringwald 
2047a4cd9b30SMilanka Ringwald 		modctx->mod_loaded = 0;
2048a4cd9b30SMilanka Ringwald 
2049a4cd9b30SMilanka Ringwald 		modctx->last_r_sample = 0;
2050a4cd9b30SMilanka Ringwald 		modctx->last_l_sample = 0;
2051a4cd9b30SMilanka Ringwald 	}
2052a4cd9b30SMilanka Ringwald }
2053