1 /*************************************/
2 /* STD MIDI file converter / player */
3 /*************************************/
6 This code is brought from Takayuki Toda's 'rc_converters'.
8 Modified 2000 by Daisuke Nagano <breeze.nagano@nifty.ne.jp>
14 #endif /* HAVE_CONFIG_H */
28 # define memcpy(d, s, n) bcopy ((s), (d), (n))
29 # define memmove(d, s, n) bcopy ((s), (d), (n))
33 #define TRACK_LEN 65536
48 static int opt, comment;
51 static unsigned char *rcpptr, *lastptr;
52 static unsigned char *inptr, *buf;
53 static unsigned char *note, *note_data;
59 static int tb_mode,tb_max, ratio,rcp_base;
60 static int step, stepx;
61 static int barlen, barunit, stepsum;
63 static char std_name[256];
65 static const char memoinit[] = " ";
66 static const char ttlinit[] = " ";
70 static int chfixflag,chbport;
73 static int exc_no,exc_id,barno,devno_fix,notoff,chport;
80 static int nbuf[16], vbuf[16], gbuf[16], cbuf[16];
82 const static int beat[] = { 1, 2, 4, 8, 16, 32, 64, 128 };
83 static int barlenb[2048];
85 static char rc_path[256];
86 static char exc_buf[32*1024+4];
88 static int tai_compres(int);
89 static int same_compres(int);
90 static int add_set(int, int *);
91 static int meas_len(int, int);
93 static unsigned char * strncpy0( unsigned char *dst, unsigned char *src, int n )
97 for( i = 0; i < n; i++ ) {
104 static int alloc_mem( void )
108 if( ( work = (void *)malloc( TRACK_LEN * 8 ) ) < 0 ) {
109 fprintf( stderr, "Memory exhausted\n" );
113 note_data = ( unsigned char * )work;
114 buf = ( unsigned char * )( (unsigned char *)work + TRACK_LEN * 4 );
119 static void destroy_mem( void )
121 if ( note_data != NULL )
127 static void get_data( unsigned char *s, int bc )
129 memmove( ( char * )s, ( char *)( inptr + incount ), bc );
135 static void put_data( unsigned char *s, int bc )
137 if( lastptr <= rcpptr + bc ) {
138 fprintf( stderr, "Buffer exhausted\n" );
141 memmove( ( char * )rcpptr, ( char * )s, bc );
147 static void strpaste( unsigned char *dst, unsigned char *src )
154 static void strnpaste( unsigned char *dst, unsigned char *src, int n )
161 static void ctrlcut( char *s )
164 if( *s == 13 ) { *s = 32; }
165 if( *s == 27 ) { *s = 32; }
172 static int get_delta( int p )
174 register int val, i, d;
179 for( i = 0; i < 4; i++ ) {
182 val = ( val << 7 ) + ( d & 0x7f );
188 fprintf( stderr, "Invalid delta time.\n" );
189 return(0); /**//*warning*//**/
193 static void proc_beat( int high, int low )
201 RCP_HEAD.Beathigh = high;
202 RCP_HEAD.Beatlow = low;
205 barlen = (RCP_HEAD.Timebase+RCP_HEAD.Timebaseh*256) * 4 * high / low;
206 if(trk==0 && barno<2048){barlenb[barno]=barlen;}
209 static int proc_header( void )
216 if( strncmp( (char*)b, "MThd", 4 ) ) {
217 unsigned char tmp[128];
218 get_data( tmp, 128-14 ); /* Mac binary */
222 if( strncmp( (char*)b, "MThd", 4 ) ) {
223 /*fprintf( stderr, "This file is not SMF file (MThd).\n" );*/
228 std_head.length = b[4]*256*256*256 + b[5]*65536 + b[6]*256 + b[7];
229 std_head.format = b[8]*256 + b[9];
230 std_head.ntrks = b[10]*256 + b[11];
231 std_head.division = b[12]*256 + b[13];
234 printf( "format =%3d ntrk =%3d division =%4d\n",
235 std_head.format, std_head.ntrks, std_head.division );
238 if( ( fmt = std_head.format ) != 0 && fmt != 1 ) {
239 fprintf( stderr, "Cannot treat format %d.\n", fmt );
243 if(std_head.ntrks>18){
244 RCP_HEAD.trkmax = 36;
246 RCP_HEAD.trkmax = 18;
250 strpaste( RCP_HEAD.memo + 28, ( unsigned char * )" ¤³¤Î¥Ç¡¼¥¿¤Ï¡¢" );
251 strpaste( RCP_HEAD.memo + 84, ( unsigned char * )" ɸ½àMIDI¥Õ¥©¡¼¥Þ¥Ã¥È¤«¤
\81E );
252 strpaste( RCP_HEAD.memo + 140, ( unsigned char * )" ItoR.x (v1.00)¤Ë¤è¤
\81E );
253 strpaste( RCP_HEAD.memo + 151, ( unsigned char * )version );
254 strpaste( RCP_HEAD.memo + 196, ( unsigned char * )" ÊÑ´¹¤µ¤
\81EÞ¤·¤¿¡£" );
255 strpaste( RCP_HEAD.memo + 252, ( unsigned char * )" Copyright 1990-97" );
256 strpaste( RCP_HEAD.memo + 280, ( unsigned char * )" HARPOON,TURBO" );
259 if( !tb_mode || std_head.division > tb_max ) {
260 rcp_base=48;if( tb_mode ) {rcp_base=tb_max;}
262 RCP_HEAD.Timebase = rcp_base;
263 RCP_HEAD.Timebaseh = rcp_base>>8;
265 ratio = std_head.division;
268 if( std_head.division > tb_max ) {
269 printf( "¥¿¥¤¥à¥Ù¡¼¥¹¤
\81Ed¤ËÊѹ¹¤·¤Þ¤¹¡£\n\n",tb_max );
274 RCP_HEAD.Timebase = std_head.division;
275 RCP_HEAD.Timebaseh = std_head.division>>8;
278 printf( "¥¿¥¤¥à¥Ù¡¼¥¹¤òÊѹ¹¤·¤Þ¤»¤ó¡£\n\n" );
283 RCP_HEAD.Tempo = 120;
287 RCP_HEAD.Playbias = 0;
293 for(i=0;i<2048;i++){barlenb[i]=0;}
298 static void entry( int d0, int d1, int d2, int d3 )
301 /*if(len && d0==0xe6 && note[len-4]==0xe6){len-=4;d1=note[len+1];}*//**/
308 if( len >= 65492+65536*3 ) {
309 fprintf( stderr, "Track buffer overflow\n" );
317 static void flash( int dt )
329 if( dx + barunit > barlen ) {
330 dx = barlen - barunit;
333 for( i = 0; i < 16; i++ ) {
336 if(fmt!=0 && !chfixflag && midi_ch!=cbuf[i]){
337 if( midi_ch == -1 ) {
338 TRACK.MIDI_CH = cbuf[i];
340 entry( 0xe6, 0x00, cbuf[i]+1, 0x00 );
345 /*if( gbuf[i] <= dx ) {*/
346 if( gbuf[i] <= 0xf0 ) {/**/
347 entry( nbuf[i], 0, gbuf[i], vbuf[i] );
348 for( j = i; j < 15; j++ ) {
354 nbuf[15] = vbuf[15] = gbuf[15] = cbuf[15] = 0;
357 entry( nbuf[i], 0, dx + 1, vbuf[i] );
365 if( note[ len - 4 ] !=0xde &&
366 note[ len - 4 ] < 0xf0 && ( note[ len - 3 ] + dx ) <= 0xf0 ) {
367 note[ len - 3 ] += dx ;
369 if(note[len-4]==0xf7){
371 while(note[ll]==0xf7){ll-=4;}
372 if(note[ll]==0x98 && ( note[ ll + 1 ] + dx ) <= 0xf0 ) {
373 note[ ll + 1 ] += dx ;
375 entry( 0x00, dx, 0, 0 );
378 entry( 0x00, dx, 0, 0 );
384 if( ( barunit += dx ) == barlen ) {
385 entry( 0xfd, 0x00, 0x00, 0x00 );
387 if(barlenb[barno]>0 && trk>0){barlen=barlenb[barno];}
396 static void proc_dummy( int dt )
400 dt = ( step * rcp_base / ratio ) - stepx;
411 static void check( int data )
415 /* if(cmd==0x80){return;}*/
418 data &= 0x0f;data+=chport;
419 if( midi_ch != data ) {
422 if( midi_ch == -1 ) {
423 TRACK.MIDI_CH = data;
426 entry( 0xe6, 0x00, data+1, 0x00 );
435 static int search( int pp )
437 /* int n, dt, cc, ch, ccmd, last, i,ocmd;*/
439 short n,cc, ch, ccmd,ocmd;
444 last = std_trk.length;
450 if(notoff!=0 && dt>255){return( 1 );}
452 dt += get_delta( pp );
454 if( ( cc = buf[pp] ) < 0x80 ) {
455 if( ccmd == 0x80 && cc == n && ( fixflag || ch+chport == midi_ch ) ) {
458 if( ccmd == 0x90 && cc == n &&
459 buf[pp+1] == 0x00 && ( fixflag || ch+chport == midi_ch ) ) {
463 if(ccmd>=0xc0 && ccmd<=0xdf){pp--;}
468 switch( cc & 0xf0 ) {
470 if( buf[pp+1] == n &&
471 ( fixflag || cc == ( 0x80 + (midi_ch&15) ) ) ) {
478 if( buf[pp+1] == n && buf[pp+2] == 0x00 &&
479 ( fixflag || cc == ( 0x90 + (midi_ch&15) ) ) ) {
512 fprintf( stderr, "Invalid format\n" );
526 static void ent_buf( int nt, int vl, int gt )
532 printf( "<nt=%d vl=%d gt=%d>\n", nt, vl, gt );
537 entry( nt, 0, gt,vl );return;
539 entry( nt, 0, 255,vl );
542 for( i = 0; i < 16; i++ ) {
543 if( !gbuf[i] || (nbuf[i] == nt && cbuf[i] == midi_ch) ) {
552 for( i = 0; i < 15; i++ ) {
565 fprintf( stderr, "¥Î¡¼¥È¥ª¡¼¥Ð¥Õ¥ú½¼\n" ); exit(18);
569 static void note_off( int p )
574 static void note_on( int p )
579 if( midi_ch != TRACK.MIDI_CH ) {
586 if( !( gt = search( p ) ) ) {
590 if( !( gt = gt * rcp_base / ratio ) ) {
591 /* if( !( gt = (gt * rcp_base+(ratio>>1)) / ratio ) ) {*/
595 ent_buf( buf[p], buf[p+1], gt );
599 static void aft_key( int p )
602 if( midi_ch != TRACK.MIDI_CH ) {
608 entry( 0xed, 0x00, buf[p], buf[p+1] );
611 static void ctl_chg( int p )
614 if( midi_ch != TRACK.MIDI_CH ) {
620 entry( 0xeb, 0x00, buf[p], buf[p+1] );
623 static void prg_chg( int p )
626 if( midi_ch != TRACK.MIDI_CH ) {
632 entry( 0xec, 0x00, buf[p], 0x00 );
635 static void aft_tch( int p )
638 if( midi_ch != TRACK.MIDI_CH ) {
644 entry( 0xea, 0x00, buf[p], 0x00 );
647 static void pt_bend( int p )
650 if( midi_ch != TRACK.MIDI_CH ) {
656 entry( 0xee, 0x00, buf[p], buf[p+1] );
659 static void run_sts( int p )
662 if( midi_ch != TRACK.MIDI_CH ) {
669 case 0x80 : note_off(p); break;
670 case 0x90 : note_on(p); break;
671 case 0xa0 : aft_key(p); break;
672 case 0xb0 : ctl_chg(p); break;
673 case 0xc0 : prg_chg(p); break;
674 case 0xd0 : aft_tch(p); break;
675 case 0xe0 : pt_bend(p); break;
679 static int num_check( int num, int limit )
688 static void clr_ttl( void )
690 strpaste( ( unsigned char * )RCP_HEAD.title, ( unsigned char * )ttlinit );
693 static void proc_meta( int meta, unsigned char *text, int length )
696 unsigned char work[128];
698 if( fmt == 0 /*&& trk*/ ) {
705 ctrlcut((char*)text);
708 if((127<text[35] && 161>text[35]) || 224<text[35]){
710 strnpaste( TRACK.Memo, text, num_check( length, 36 ) );
711 if(strncmp((char*)text,"PartA",5)==0){chport=0;}
712 if(strncmp((char*)text,"PartB",5)==0){chport=16;}
716 if((127<text[63] && 161>text[63]) || 224<text[63]){
718 strnpaste( RCP_HEAD.title, text, num_check( length, 64 ) );
726 ctrlcut((char*)text);
729 if((127<text[35] && 161>text[35]) || 224<text[35]){
731 strnpaste( TRACK.Memo, text, num_check( length, 36 ) );
732 if(strncmp((char*)text,"PartA",5)==0){chport=0;}
733 if(strncmp((char*)text,"PartB",5)==0){chport=16;}
737 if((127<text[63] && 161>text[63]) || 224<text[63]){
739 strnpaste( RCP_HEAD.title, text, num_check( length, 64 ) );
749 ctrlcut((char*)text);
751 strcpy( ( char * )work, ( char * )memoinit );
752 strnpaste( work, text, num_check( length, 64 ) );
753 if(length<20){length=20;}
754 entry( 0xf6, 0x00, work[0], work[1] );
755 for( i = 2; i < 20; i += 2 ) {
756 entry( 0xf7, 0x00, work[i], work[i+1] );
758 if(length>20){strcpy((char*)text,(char*)&text[20]);length-=20;goto next;}
760 /* for( i = 2; i < length; i += 2 ) {
761 entry( 0xf7, 0x00, work[i], work[i+1] );
768 if(!chfixflag || fmt==0){entry( 0xe6, 0x00, (text[0]+1)+chport, 0x00 );}
771 if( !tempoflag && trk == 0 && tempofix==0) {
772 i = 60000000 / ( ( text[0] << 16 ) + ( text[1] << 8 ) + text[2] );
786 RCP_HEAD.Tempo = 255;goto skip;}
790 if( !tempoflag && trk == 0 ) {
791 i = 60000000 / ( ( text[0] << 16 ) + ( text[1] << 8 ) + text[2] );
792 RCP_HEAD.Tempo = i>>1;
796 i = 60000000 / ( ( text[0] << 16 ) + ( text[1] << 8 ) + text[2] );
797 i = 64 * i / RCP_HEAD.Tempo;
798 /*ÀßÄꤷ¤¿¤¤¥Æ¥ó¥Ý¡à½é´
\81EßÄ
\81EÆ¥ó¥Ý¡ß64*/
806 entry( 0xe7, 0x00, i, 0x00 );
811 proc_beat( text[0], beat[ text[1] ] );
815 if((text[0])==1){chport=16;}else{chport=0;}
816 /*entry( 0xe6, 0x00, (midi_ch+1)+chport, 0x00 );*/
827 printf( "FF %02X (Unknown meta event)\n", meta );
833 static void proc_excl( unsigned char *text, int length ,int code)
839 if( fmt == 0 /*&& trk*/ ) {
843 text[ length ] = 0xf7 ;
845 if( devno_fix !=0 && text[0] == 0x41 && text[3] == 0x12){
848 if( length < 9 || length > 15 ||
849 text[0] != 0x41 || text[3] != 0x12 ||
850 text[ length-1 ] != 0xf7 ) {
852 if( text[0] == 0x41 && text[3] == 0x12 && length<9 ){return;}
857 entry( 0x98, 0, 0, 0 );
859 entry( 0xf7, 0, text[i], text[i+1] );
860 if( text[i] == 0xf7 || text[ i+1 ] == 0xf7 ) {break;}
864 if(len==0 || note[len-4]!=0xf7){goto nor;}
867 if(note[len-2]==0xf7){note[len-2]=text[i++];}
868 if(note[len-1]==0xf7){note[len-1]=text[i++];}
871 entry( 0xf7, 0, text[i], text[i+1] );
872 if( text[i] == 0xf7 || text[ i+1 ] == 0xf7 ) {break;}
877 /*fprintf( stderr, "ÉÔÀµEXCLUSIVE¥á¥Ã¥»¡¼¥¸ \n" );
883 if( exc_no != text[1] || exc_id != text[2] ) {
884 exc_no = text[1];exc_id = text[2];
885 entry( 0xdf, 0, exc_no, exc_id );
888 h = text[4]; m = text[5]; l = text[6];
891 for( i = 7; i < length - 2; i++ ) {
892 if( hh != h || mm != m ) {
893 entry( 0xdd, 0x00, h, m );
894 hh = h; mm = m; ll = l;
896 entry( 0xde, 0x00, l, text[i] );
904 static int proc_next( void )
906 int meta, code, length,last;
907 unsigned char text[4096];
909 last = std_trk.length;
915 proc_dummy( get_delta(pt) );
918 if( ( code = buf[pt] ) == 0xff ) {
921 length = get_delta(pt);
923 strncpy0( text, buf + pt, length );
924 if( fmt == 1 || trk == 0 ) {
925 proc_meta( meta, text, length );
932 switch( code & 0xf0 ) {
933 case 0x80: /*check( buf[pt] ); note_off(pt+1);*/
934 cmd = buf[pt] & 0xf0;
936 case 0x90: check( buf[pt] ); note_on(pt+1); pt += 3; break;
937 case 0xa0: check( buf[pt] ); aft_key(pt+1); pt += 3; break;
938 case 0xb0: check( buf[pt] ); ctl_chg(pt+1); pt += 3; break;
939 case 0xc0: check( buf[pt] ); prg_chg(pt+1); pt += 2; break;
940 case 0xd0: check( buf[pt] ); aft_tch(pt+1); pt += 2; break;
941 case 0xe0: check( buf[pt] ); pt_bend(pt+1); pt += 3; break;
943 if( code != 0xf0 && code != 0xf7 ) {
944 fprintf( stderr, "Invalid MIDI message (%02X)\n", code );
948 length = get_delta(pt);
950 if( fmt == 1 || trk == 0 ) {
952 strncpy0( (uint8*)exc_buf, buf + pt, length );
953 proc_excl( (uint8*)exc_buf, length ,code);
958 default : run_sts(pt); pt += 2;
959 if(cmd>=0xc0 && cmd<=0xdf){pt--;}
966 static void track_end( void )
974 if( ( note[ len - 4 ] == 0x00 && note[ len - 2 ] == 0x00 ) ||
975 note[ len - 4 ] == 0xfd ) {
983 entry( 0xfe, 0, 0, 0 );
984 len=tai_compres(len);
985 if(sameflag){len=same_compres(len);}
988 fprintf( stderr, "Track overflow.\n" );
990 entry( 0xfe, 0, 0, 0 );*/
993 TRACK.len_high = ( len + 44 ) >> 8;
994 TRACK.len_low = (( len + 44 ) >> 16 ) + ( len + 44 ) & 0xff;
997 static int proc_track( void )
1002 exc_no=0x10;exc_id=0x16;chport=0;
1004 if( fmt == 1 || trk == 0 ) {
1006 strncpy(std_trk.chunk, (char*)b, 4);
1007 std_trk.length = b[4]*256*256*256 + b[5]*65536 + b[6]*256 + b[7];
1008 if( strncmp( std_trk.chunk, "MTrk", 4 ) ) {
1009 fprintf( stderr, "Invalid SMF file (MTrk)\n" );
1012 get_data( buf, std_trk.length );
1015 for( i = 0; i < 16; i++ ) {
1016 nbuf[i] = vbuf[i] = gbuf[i] = cbuf[i] = 0;
1022 barunit = 0; stepsum = 0;
1025 TRACK.track_no = trk;
1026 TRACK.rhythm_flag = 0x00;
1029 TRACK.MIDI_CH = midi_ch = trk ;
1035 TRACK.Play_bias = 0x00;
1036 TRACK.ST_offset = 0x00;
1039 strpaste( TRACK.Memo, ( unsigned char * )memoinit );
1042 if(barlenb[0]>0 && trk>0){barlen=barlenb[barno++];}
1045 printf( "Track= %2d %04X\n", trk, std_trk.length );
1048 if(chbport!=0 && trk>16 ){chport=16;}
1051 if ( proc_next() != 0 ) return 1;
1056 put_data( RCP_HEAD.mark, 0x0586 );
1060 if( std_head.format==0 ){
1061 TRACK.MIDI_CH = trk ;
1063 if(trk){TRACK.MIDI_CH = trk-1 ;}
1067 put_data( ( unsigned char * )&TRACK.len_low, 44 );
1068 put_data( ( unsigned char * )note, len );
1074 static void dummy_track( void )
1078 TRACK.track_no = trk;
1079 TRACK.rhythm_flag = 0x00;
1080 TRACK.MIDI_CH = 255;
1081 TRACK.Play_bias = 0x00;
1082 TRACK.ST_offset = 0x00;
1084 strpaste( TRACK.Memo, ( unsigned char * )memoinit );
1087 printf( "Track= %2d dummy\n", trk );
1092 put_data( ( unsigned char * )&TRACK.len_low, 44 );
1093 put_data( ( unsigned char * )note, len );
1098 static void option( char *s )
1146 while(*s>='0' && *s<='9'){
1147 tb_max=tb_max*10+((*s++)-'0');
1149 if(tb_max<48){tb_max=240;}
1187 int itor( char *smf_data, char *rcp_buf )
1191 /* Initialize all configurable valuables */
1197 tb_mode = 1; /* 0:time base is converted into 48 */
1198 tb_max = 480; /* Max number of time base */
1199 chbport = 1; /* translate all tracks > 16 into port B */
1200 tempofix = 1; /* fixes errors of tempo change */
1201 sameflag = 1; /* unifies all tracks with SAME MEAS */
1202 comment = 1; /* suppress all comments */
1205 /* allocate internal work memory */
1209 if ( alloc_mem() != 0 ) return 0;
1211 inptr = (uint8 *)smf_data;
1212 rcpptr = (uint8 *)rcp_buf;
1214 lastptr = rcpptr + 512*1024; /* DATA_ADR_SIZE */
1216 for( i = 0; i < 16; i++ ) {
1217 note_data[i] = 0xff;
1220 note = note_data + 16;
1223 /* process all tracks */
1225 if ( proc_header() != 0 ) {
1231 for( trk = 0; trk < 16; trk++ ) {
1232 if ( proc_track() != 0 ) {
1238 for( trk = 16; trk < 18; trk++ ) {
1243 for( trk = 0; trk < std_head.ntrks; trk++ ) {
1244 if ( proc_track()!= 0 ) {
1250 if( std_head.ntrks>18){
1251 for( trk = std_head.ntrks; trk < 36; trk++ ) {
1255 for( trk = std_head.ntrks; trk < 18; trk++ ) {
1262 /* free all minternal work memory */
1266 /* all works finished */
1268 return (int)(rcpptr - (uint8*)rcp_buf);
1271 /***************************/
1273 static int tai_compres(int ln)
1275 int i,ad,ch,rbh=-1,rbm=-1;
1276 unsigned char a,b,c,d;
1278 ch=(TRACK.MIDI_CH+1)&0xff;
1282 a=note[i];b=note[i+1];c=note[i+2];d=note[i+3];
1284 if(a<128 && c>b && d>0){
1289 unsigned char da=note[ad2];
1290 if(da==0xe6){cc=note[ad2+2];}
1292 if(ad2>i && cc==ch && a==da && note[ad2+2]!=0 && note[ad2+3]!=0 ){
1293 if(sum+note[ad2+2]<=255){
1303 if(da<0xf0){sum+=note[ad2+1];if(sum>255 || sum>=c){break;}}
1305 if(da>=0xfc||da==0xf8||da==0xf9||da==0xe2||da==0xec){break;}
1310 /* if(note[i]>=0xfc){ch=-1;}*/
1312 if(note[i]>=0xfc){rbh=-1;rbm=-1;}
1315 if(note[i+2]==rbh && note[i+3]==rbm){
1316 note[i]=0;note[i+2]=0;note[i+3]=0;
1321 if(ad && note[ad-4]==0xdd){
1322 note[ad-2]=note[i+2];
1323 note[ad-1]=note[i+3];
1324 note[i]=0;note[i+2]=0;note[i+3]=0;
1329 /* if(note[i]==0xe6){
1331 note[i]=0;note[i+2]=0;note[i+3]=0;
1335 if(ad && note[ad-4]==0xe6){
1336 note[ad-2]=note[i+2];
1337 note[i]=0;note[i+2]=0;note[i+3]=0;
1344 if(ad && note[ad-4]==note[i] && note[ad-3]==0){
1345 note[ad-2]=note[i+2];
1346 note[i]=0;note[i+2]=0;note[i+3]=0;
1350 if((note[i]<0x80 &&(note[i+2]==0||note[i+3]==0))&&
1351 ad>0 && note[ad-4]<0xf0 && note[ad-3]+note[i+1]<=240){
1352 note[ad-3]+=note[i+1];
1354 note[ad++]=note[i];note[ad++]=note[i+1];
1355 note[ad++]=note[i+2];note[ad++]=note[i+3];
1362 /***************************/
1363 static int same_compres(int size)
1365 int i,j=0,k,match,count=0;
1366 int po=0,m_max,ln,co=0,me=0,ad;
1367 int add[1024],add2[1024],leng[1024];
1369 m_max=add_set(size,add);if(m_max<2 || m_max>1024){return(size);}
1371 for(i=0;i<m_max;i++){
1372 po=add[i];ln=meas_len(size,po);match=0;
1373 if(ln>4 && note[po+ln-4]==0xfc){ln=ln-4;}
1375 if(note[po]<0xfc && me>0){
1377 if(ln==leng[j] && note[add2[j]]<0xfc){
1380 if(note[po+k]!=note[ad]){match=0;break;}
1384 if(match!=0){break;}
1389 if(match!=0 && j<1024 && add2[j]<65536-44){
1391 if(me<1024){add2[me]=co;leng[me]=4;me++;}
1393 note[co+1]=j&0xff;note[co+2]=(j>>8)+(ad&0xfc);note[co+3]=ad>>8;
1396 if(me<1024){add2[me]=co;leng[me]=ln;me++;}
1397 for(k=0;k<ln;k++){note[co]=note[po];po++;co++;}
1400 note[co]=0xfe;co=co+4;
1404 static int add_set(int size,int *add)
1410 if(note[i]>=0xfc||note[i+4]==0xfc){
1411 co++;if(co<1024){add[co]=i+4;}
1415 if(note[i+2]==0 || note[i+3]==0){note[i]=0;note[i+2]=0;note[i+3]=0;}
1423 static int meas_len(int size,int j)
1429 if( d==0xfe ){break;}
1431 if( d>0xfb ){break;}
1437 /***************************/