/[projet1]/public/pc/tools/osdk/main/SampleTweaker/main.cpp
Defence Force logotype

Contents of /public/pc/tools/osdk/main/SampleTweaker/main.cpp

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1508 - (show annotations)
Sat Apr 13 12:01:40 2019 UTC (7 months, 3 weeks ago) by dbug
File size: 12178 byte(s)
Just commented out some old code.
1 //
2 //
3 //
4 #define _CRT_SECURE_NO_WARNINGS
5
6 #include <stdio.h>
7 #include <stdlib.h>
8 #include <memory.h>
9 #include <io.h>
10 #include <string.h>
11 #include <fcntl.h>
12 #include <sys/stat.h>
13
14 #include <math.h>
15
16
17
18 /*
19 bug: having the output (your 0-255) in 0 <= y <= 1 gives "x = 15-2*(log10(1/y)/log10(2))"
20 <_Stefan> x is the psg volume from 0 to 15
21 */
22
23 unsigned char SampleToVolume(unsigned char sample)
24 {
25 if (!sample)
26 {
27 // To avoid a divide by 0
28 return 0;
29 }
30 else
31 {
32 double y=(double)sample;
33 y=y/255.0;
34
35 double x;
36 x = 15.0-2.0*(log10(1.0/y)/log10(2.0));
37
38 if (x<0.0)
39 {
40 x=0.0;
41 }
42 else
43 if (x>15.0)
44 {
45 x=15.0;
46 }
47 return (unsigned char)x;
48 }
49 }
50
51
52
53 bool LoadFile(const char *ptr_filename,unsigned char *&ptr_buffer,int &size)
54 {
55 struct _finddata_t file_info_src;
56 int result;
57
58 result=_findfirst(ptr_filename,&file_info_src);
59 if (result==-1.L)
60 {
61 return false;
62 }
63 _findclose(result);
64
65
66 size=file_info_src.size;
67
68 ptr_buffer=new unsigned char[size];
69
70 long handle;
71 long size_read;
72
73 if (!(handle=_open(ptr_filename,_O_RDONLY|_O_BINARY)))
74 {
75 return false;
76 }
77 size_read=_read(handle,ptr_buffer,size);
78 _close(handle);
79
80 if (size!=size_read)
81 {
82 // Read error
83 return false;
84 }
85
86 return true;
87 }
88
89
90
91 bool SaveFile(const char *ptr_filename,unsigned char *ptr_buffer,int size)
92 {
93 long handle;
94
95 if (!(handle=_open(ptr_filename,_O_TRUNC|O_BINARY|O_CREAT|O_WRONLY,_S_IREAD|_S_IWRITE )))
96 {
97 return false;
98 }
99 _write(handle,ptr_buffer,size);
100 _close(handle);
101
102 return true;
103 }
104
105
106
107
108
109 // Usage:
110 // FilePack <source_file> <dest_file>
111 //
112
113
114 void DisplayError()
115 {
116 printf("\n");
117 printf("\nÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿");
118 printf("\n³ 4bits Sample Merger ³");
119 printf("\n³ vers format ORIC ³");
120 printf("\n³ V0.001 ³");
121 printf("\n³ (c) 2002 POINTIER Mickael ³");
122 printf("\nÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ");
123 printf("\n");
124 exit(1);
125 }
126
127
128
129 #define NB_ARG 2
130
131
132 bool get_switch(const char *&ptr_arg,const char *ptr_switch)
133 {
134 int lenght=strlen(ptr_switch);
135
136 if (_memicmp(ptr_arg,ptr_switch,lenght))
137 {
138 // Not a match
139 return false;
140 }
141 // Validate the parameter
142 ptr_arg+=lenght;
143 return true;
144 }
145
146
147 int get_value(const char *&ptr_arg,long default_value)
148 {
149 char *ptr_end;
150 long value=strtoul(ptr_arg,&ptr_end,10);
151 if (ptr_arg==ptr_end)
152 {
153 value=default_value;
154 }
155 ptr_arg=ptr_end;
156 return value;
157 }
158
159
160 #if 0
161 // Actually not in use anymore...?
162 2>d:\svn\public\pc\tools\osdk\main\sampletweaker\main.cpp(170) : error C2556 : 'float log2(double)' : overloaded function differs only by return type from 'double log2(double)'
163 2>c:\program files(x86)\windows kits\10\include\10.0.10240.0\ucrt\math.h(506) : note: see declaration of 'log2'
164 2>d:\svn\public\pc\tools\osdk\main\sampletweaker\main.cpp(169) : error C2371 : 'log2' : redefinition; different basic types
165 2>c:\program files(x86)\windows kits\10\include\10.0.10240.0\ucrt\math.h(506) : note: see declaration of 'log2'
166
167 // Calculates log2 of number.
168 // http://www-crca.ucsd.edu/~msp/techniques/v0.08/book-html/node8.html
169 // http://poi.ribbon.free.fr/tmp/freq2regs.htm
170 // http://logbase2.blogspot.com/2007/12/log-base-2.html
171 //
172 // log2(1)=0
173 // log2(2)=1
174 // log2(4)=2
175 // log2(8)=4
176 float log2( double n )
177 {
178 // log(n)/log(2) is log2.
179 return (float)(log( n ) / log( 2.0 ));
180 }
181 #endif
182
183 void main(int argc,char *argv[])
184 {
185 long param;
186 long nb_arg;
187
188 bool flag_pack=true;
189 param=1;
190
191 if (argc>1)
192 {
193 for (;;)
194 {
195 nb_arg=argc;
196 const char *ptr_arg=argv[param];
197 /*
198 if (get_switch(ptr_arg,"-u")) // UNPACK
199 {
200 flag_pack=false;
201 argc--;
202 param++;
203 }
204 else
205 if (get_switch(ptr_arg,"-p")) // PACK
206 {
207 flag_pack=true;
208 argc--;
209 param++;
210 }
211 */
212 if (nb_arg==argc) break;
213 }
214 }
215
216
217 if (argc!=(NB_ARG+1))
218 {
219 DisplayError();
220 }
221
222
223 //
224 // Copy last parameters
225 //
226 char source_name[_MAX_PATH];
227 char dest_name[_MAX_PATH];
228
229 strncpy(source_name,argv[param],sizeof(source_name));
230 source_name[sizeof(source_name)-1]=0;
231
232 param++;
233 strncpy(dest_name,argv[param],sizeof(dest_name));
234 dest_name[sizeof(dest_name)-1]=0;
235
236
237 unsigned char *ptr_buffer;
238 int size_buffer_src;
239
240 if (!LoadFile(source_name,ptr_buffer,size_buffer_src))
241 {
242 printf("\nUnable to load file '%s'",source_name);
243 printf("\n");
244 exit(1);
245 }
246
247 /*
248 //
249 // Stupid Raw=>nibble conversion, no frequency change
250 //
251 ptr_buffer_dst=new unsigned char[size_buffer_src+8];
252 size_buffer_dst=size_buffer_src/2;
253
254 unsigned char b0,b1,b;
255 int i;
256 unsigned char *ptr_src;
257 unsigned char *ptr_dst;
258
259 ptr_src=ptr_buffer;
260 ptr_dst=ptr_buffer_dst;
261 for (i=0;i<size_buffer_dst;i++)
262 {
263 b0=*ptr_src++;
264 b1=*ptr_src++;
265 b=(b1&0xF0)|(b0>>4);
266 *ptr_dst++=b;
267 }
268 */
269
270 //
271 // Try to adapt the size of dest buffer based on complex calculations:
272 // Move from source frequency to dest frequency, while trying to round
273 // on a multiple of 80 samples (or 40 bytes)
274 //
275 //size_buffer_dst=(size_buffer_src*4000)/44100; // overflow and get negative on a 581114 bytes sample...
276
277 /*
278 int delta=size_buffer_dst%80;
279 if (!delta)
280 {
281 // Perfectly on a 80 multiple (yoohoo)
282 }
283 else
284 if (delta<40)
285 {
286 // Reduce the size of dest buffer
287 size_buffer_dst-=delta;
288 }
289 else
290 {
291 // Increase the size of dest buffer
292 size_buffer_dst-=delta;
293 size_buffer_dst+=80;
294 }
295 */
296
297 int size_buffer_dst;
298 unsigned char *ptr_buffer_dst;
299
300 // 4.b 'RIFF'
301 // 4.b size
302 // 4.b 'WAVE'
303 // 4.b 'fmt '
304 #if 0 // ATARI DELTA PACK CODE
305 size_buffer_dst=1+(size_buffer_src/2);
306 ptr_buffer_dst=new unsigned char[size_buffer_dst+1];
307
308 // Stores a first byte which is the starting value,
309 // then encode each value as a 4 bit signed delta relative to the first value
310 unsigned char *ptr_src=ptr_buffer;
311 unsigned char *ptr_dst=ptr_buffer_dst;
312
313 // Store first byte twice, so the delta are not on an odd address
314 unsigned char prev=ptr_src[0];
315 *ptr_dst++=prev;
316
317 bool flip=false;
318 unsigned char store=0;
319
320 // Then compute the deltas, they will match the following table:
321 // Delta: 0 1 2 4 8 16 32 64 128 -64 -32 -16 -8 -4 -2 -1
322 // Code: $0 $1 $2 $3 $4 $5 $6 $7 $8 $9 $A $B $C $D $E $F
323 char delta_table[16]=
324 {
325 -64,
326 -32,
327 -16,
328 -8,
329 -4,
330 -2,
331 -1,
332 0,
333 1,
334 2,
335 4,
336 8,
337 16,
338 32,
339 64,
340 127
341 };
342
343 int delta_usage[16]={0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0};
344
345
346 for (int i=1;i<size_buffer_src;i++)
347 {
348 unsigned char delta_index;
349
350 unsigned char next=ptr_src[i];
351
352 int max_error=999;
353 delta_index=0;
354 for (int delta_entry=0;delta_entry<16;delta_entry++)
355 {
356 unsigned char new_next=prev+delta_table[delta_entry];
357 int error=next-new_next;
358 if (error<0)
359 {
360 error=-error;
361 }
362 /*
363 if (error>127)
364 {
365 __asm int 3
366 }
367 */
368 if (error<max_error)
369 {
370 max_error=error;
371 delta_index=delta_entry;
372 if (max_error==0)
373 {
374 // Can't do better than no error
375 break;
376 }
377 }
378 }
379
380 unsigned char delta_value=delta_table[delta_index];
381 delta_usage[delta_index]++;
382 prev+=delta_value;
383
384 store<<=4;
385 store|=delta_index;
386 flip=!flip;
387 if (!flip)
388 {
389 *ptr_dst++=store;
390 }
391 }
392
393 #else // ORIC 4BIT CODE
394 size_buffer_dst=(size_buffer_src/2)+1; // +1 for the 00 final
395 ptr_buffer_dst=new unsigned char[size_buffer_dst];
396
397 // ln(1) -> 0
398 // ln(2) -> 0.6931
399 // ln(16) -> 2.77
400
401 // log(1)=0
402 // log(16)=1.204
403 // 1/log(16)= 0.830482
404 // ACHANGERDESUITE
405
406
407 // Volume levels
408 int voltab[] = { 0, 513/257, 828/257, 1239/257, 1923/257, 3238/257, 4926/257, 9110/257, 10344/257, 17876/257, 24682/257, 30442/257, 38844/257, 47270/257, 56402/257, 65535/257};
409
410 // Create a log table
411 // 15 -> 1.0 -> 255
412 // 14 -> 0.707 -> 180,285
413 // 13 -> 0.5 -> 128
414 // 12 -> 0.303 -> 77,265
415 // 11 -> 0.25 -> 63,75
416 // 10 -> 0.1515 -> 38,6325
417 // 9 -> 0.125 -> 31,875
418 // 8 -> ?
419 // 7 -> 0,0625 -> 15,9375
420 // 6 -> ?
421 // 5 -> 0,03125 -> 7,96875
422 // 4 -> ?
423 // 3 -> 0,015625 -> 3,984375
424 // 2 -> ?
425 // 1 -> 0,0078125 -> 1,9921875
426 // 0 -> 0
427 unsigned char logVolume[256];
428 int vol=0;
429 for (int i=0;i<16;i++)
430 {
431 int maxvol=voltab[i];
432 while (vol<=maxvol)
433 {
434 logVolume[vol]=i;
435 vol++;
436 }
437 }
438
439 // Convert to 4 bit sample,
440 // each byte contains to sample values; one per nibble
441 unsigned char *ptr_src=ptr_buffer;
442 unsigned char *ptr_dst=ptr_buffer_dst;
443 for (int i=0;i<(size_buffer_dst-1);i++)
444 {
445 #if 1
446 // Log conversion
447 unsigned char b0=*ptr_src++;
448 b0=logVolume[b0]; //>>4;
449
450 unsigned char b1=*ptr_src++;
451 b1=logVolume[b1]; //>>4;
452 unsigned char b=(b1<<4)|(b0);
453 #else
454 /*
455 // Raw conversion
456 unsigned char b0=*ptr_src++;
457 b0=(((unsigned int)b0)*15)/255;
458
459 unsigned char b1=*ptr_src++;
460 b1=(((unsigned int)b1)*15)/255;
461
462 unsigned char b=(b1<<4)|(b0);
463 */
464 // Error based conversion
465 unsigned char b0=*ptr_src++;
466 b0=(((unsigned int)b0)*15)/255;
467
468 unsigned char b1=*ptr_src++;
469 b1=(((unsigned int)b1)*15)/255;
470
471 unsigned char b=(b1<<4)|(b0);
472 #endif
473
474 if (!b)
475 {
476 // To avoid a spurious null terminator
477 //b=1;
478 }
479 *ptr_dst++=b;
480 }
481 // Null terminator
482 *ptr_dst++=0;
483 #endif
484
485 #if 0
486 // Depack and save in the source file :p
487 ptr_src=ptr_buffer_dst;
488 ptr_dst=ptr_buffer;
489
490 // Store first byte
491 prev=ptr_src[0];
492 *ptr_dst++=prev;
493
494 for (int i=1;i<size_buffer_dst;i++)
495 {
496 unsigned char store=ptr_src[i];
497 unsigned char b1=(store&15);
498 unsigned char b0=((store>>4)&15);
499
500 prev+=delta_table[b0];
501 *ptr_dst++=prev;
502
503 prev+=delta_table[b1];
504 *ptr_dst++=prev;
505 }
506
507 if (!SaveFile(dest_name,ptr_buffer,size_buffer_src))
508 {
509 printf("\nUnable to save file '%s'",source_name);
510 printf("\n");
511 exit(1);
512 }
513 #else
514 // Save the resulting file
515 if (!SaveFile(dest_name,ptr_buffer_dst,size_buffer_dst))
516 {
517 printf("\nUnable to save file '%s'",source_name);
518 printf("\n");
519 exit(1);
520 }
521 #endif
522
523 //
524 // Make some cleaning
525 //
526 delete[] ptr_buffer;
527 delete[] ptr_buffer_dst;
528 }
529
530
531 /*
532
533 15 1.0
534 14 0.707 <= 0.606 ???
535 13 0.5
536 12 0.303
537 11 0.25
538 10 0.1515
539 9 0.125
540 8 0.07575
541 7 0.0625
542 6 0.037875
543 5 0.03125
544 4 0.0189375
545 3 0.015625
546 2 0.00946875
547 1 0.0078125
548 0 0.0
549
550
551 V[13]=V[15]/2
552
553
554
555 // calculate the volume->voltage conversion table
556 // The AY-3-8910 has 16 levels, in a logarithmic scale (3dB per step)
557 // The YM2149 still has 16 levels for the tone generators, but 32 for
558 // the envelope generator (1.5dB per step).
559 for (i = 31;i > 0;i--)
560 {
561 // limit volume to avoid clipping
562 if (out > MAX_OUTPUT) PSG->VolTable[i] = MAX_OUTPUT;
563 else PSG->VolTable[i] = (unsigned int)out;
564
565 if (AY_filetype==0)
566 out = out - (MAX_OUTPUT / 32);
567 else
568 out /= 1.188502227; // = 10 ^ (1.5/20) = 1.5dB
569 }
570
571
572
573 Volume Dac output Volume Raw Corrected
574 Corrected
575
576 15 1.0 15.0 255 255
577 14 0.707 12.62 238
578 13 0.5 10.61 221
579 12 0.303 8.93 204
580 11 0.25 7.51 187
581 10 0.1515 6.32 170
582 9 0.125 5.32 153
583 8 0.07575 4.47 136
584 7 0.0625 3.76 119
585 6 0.037875 3.17 102
586 5 0.03125 2.66 85
587 4 0.0189375 2.244 68
588 3 0.015625 1.888 51
589 2 0.00946875 1.58 34
590 1 0.0078125 1.33 17
591 0 0.0 0.0 0 0
592
593 */

  ViewVC Help
Powered by ViewVC 1.1.26