/*USE MEDIUM MODEL!!!*/ #include #include #include #include FILE *mod,*tbrmod; void makenames(char *,char *); /* Amiga note values */ int notes[36]={856,808,762,720,678,640,604,570,538,508,480,453, 428,404,381,360,339,320,302,285,269,254,240,226, 214,202,190,180,170,160,151,143,135,127,120,113}; char sambuf[64000]; /* Temporary buffer for samples */ void main(int argc,char *argv[]) { int n; /*loop variable*/ unsigned int b2,b,m,seg=0; unsigned char by,by2,by3,by4,re1,re2,re3,re4; char segpad[32]; unsigned long pos; unsigned char buffer[1024],hi_pattern; char songpos[128]; unsigned int sam_lenght[32],rep_beg[32],rep_len[32]; unsigned int sam_reallen[32]; unsigned char sam_vol[32],sam_finetune[32],songlenght; char tbmname[256],modname[256]; printf("ProTracker 1.1B module to Black Rain module 1.0 compiler\n"); printf("Version 1.1 (C) 1993 Erwin / TBR\n"); if(argc!=2){ printf("Usage: mod2tbm infile[.mod]\n"); exit(1); } strcpy(modname,argv[1]); makenames(modname,tbmname); mod=fopen(modname,"rb"); if(mod==NULL){ printf("Can't open %s!\n",modname); exit(1); } tbrmod=fopen(tbmname,"wb"); if(tbrmod==NULL){ printf("Can't open %s!\n",tbmname); exit(1); } fread(buffer,1,20,mod); printf("Processing song %s\n",buffer); printf("Song includes following samples:\n"); for(n=0;n<31;n++){ fread(buffer,1,22,mod); buffer[22]=0; if(strlen(buffer)) printf("%d: %s\n",n+1,buffer); m=fgetc(mod); b=fgetc(mod); sam_lenght[n]=((m<<8)+b)*2; /* do amiga byte conversion */ m=fgetc(mod); sam_finetune[n]=m; /* fine tune & vol are bytes - no converion needed*/ m=fgetc(mod); sam_vol[n]=m; m=fgetc(mod); b=fgetc(mod); rep_beg[n]=((m<<8)+b)*2; m=fgetc(mod); b=fgetc(mod); rep_len[n]=((m<<8)+b)*2; } songlenght=getc(mod); m=fgetc(mod); /* this byte isn't used */ fread(songpos,1,128,mod); /* read song positions (128 of them)*/ printf("\n"); hi_pattern=0; /* highes pattern #, used by our gusplayer - that was written in 2 days an pretty much sucks - to figure out how many there are to be loaded*/ for(n=0;nhi_pattern) hi_pattern=songpos[n]; fread(buffer,1,4,mod); /* these 4 bytes contain letters 'M.K.' or something else */ pos=(448+1024*hi_pattern+1024);/* position in tbm module*/ printf("Converting sample data...\n"); for(n=0;n<31;n++){ segpad[n]=pos%16; /*since the samples are 32-bit aligned we sometimes need to add a few bytes in frot if them to make it start at a page boundary */ if(segpad[n]){ segpad[n]=16-segpad[n]; pos+=segpad[n]; } seg=pos>>4; putw(seg,tbrmod); /* samples segment address in tbm mod */ if(rep_len[n]>2) sam_reallen[n]=rep_beg[n]+rep_len[n]; else sam_reallen[n]=sam_lenght[n]; if(sam_reallen[n]<=1) putw(0,tbrmod); /*the lenght of the sample */ else putw(sam_reallen[n]-1,tbrmod); putc(sam_vol[n],tbrmod); /*volume*/ putc(sam_finetune[n],tbrmod); /*finetune*/ putw(sam_reallen[n]-rep_beg[n],tbrmod);/*repeat begin*/ if(rep_len[n]<=2) putw(0,tbrmod); /* if zero don't loop sample*/ else putw(1,tbrmod); /*if 1 loop it */ pos+=sam_reallen[n]; /*add position*/ } putc(songlenght,tbrmod); /* write song lenght */ putc(hi_pattern,tbrmod); /* write highest pattern */ printf("Converting patterns...\n"); fwrite(songpos,1,128,tbrmod); /*write song positions */ fwrite(songpos,1,8,tbrmod); /*these bytes are here to make the patterns start at a page boundary */ for(n=0;n<=hi_pattern;n++) for(m=0;m<256;m++){ by=fgetc(mod); /* read channel's data (see fformat.txt for more*/ by2=fgetc(mod); /* info)*/ by3=fgetc(mod); by4=fgetc(mod); re1=by&0x0f; b=(re1<<8)+by2; if(b){ for(re1=0;re1<36;re1++) /*get note number:C-1=1, C#1 = 2 etc.*/ if(notes[re1]==b){ re1++; break; } } fputc(re1,tbrmod); re2=(by&0xf0)+(by3>>4); /*# of sample*/ fputc(re2,tbrmod); re3=by3&0x0f; fputc(re3,tbrmod); /*effect cmd*/ fputc(by4,tbrmod); /*cmd info*/ } for(n=0;n<16;n++) buffer[n]=0;//0x80; printf("Converting samples...\n"); for(n=0;n<31;n++){ if(segpad[n]) fwrite(buffer,1,segpad[n],tbrmod); /*make sample start at a page boundary*/ fread(sambuf,1,sam_lenght[n],mod); /*read sample*/ for(m=sam_reallen[n]-1;m!=0xffff;m--) /*write it BACKWARDS and convert*/ fputc((sambuf[m]^0x80),tbrmod);/*it into 8-bit unsigned format*/ } printf("Done.\n"); /*we are done now*/ fclose(mod); /*close files*/ fclose(tbrmod); } void makenames(char *infile,char *outfile) { char *inbak; inbak=infile; while(*inbak) inbak++; while(*inbak!=':'&&*inbak!='\\'&&inbak>=infile){ inbak--; } inbak++; while(*inbak!=0&&*inbak!='.') *outfile=*inbak,outfile++,inbak++; *outfile=0; strcat(outfile,".tbm"); if(*inbak==0) strcat(inbak,".mod"); return; }