/* ** routines for reading and writing dx7 voices */ #include #include #include /* Need a header & trailer in dx7 file for da(1) */ static char header[6] = {SX_CMD,ID_DX7,0,0,1,0x1b}; static char trailer[2] = {0x42,SX_EOB}; /* random checksum & end of block */ char dx7CheckSum(); Dx7Voice * dx7readVoice(f, name) FILE *f; char *name; /* filename (used only in diagnostics) */ /* ** Read a 'Dx7Voice' from 'f' and return it, ** or NULL if there was a problem. ** The 'Dx7Voice' is expected to be 155 hex bytes. ** Should probably understand alternate formats, ** like `da`(1) output, C-style format, etc. */ { Dx7Voice *v = Alloc(Dx7Voice); #define n SizeofDx7Voice if (!v) return MidiError("dx7readDx7Voice(%s): no memory.\n",name),v; if (read(fileno(f),v,sizeof header) != sizeof(header) || read(fileno(f),v,n) != n) MidiError("dx7readVoice(%s): byte count error\n",name), v = (Dx7Voice *)0; else v->name[10] = '\0'; return v; #undef n } Dx7Voice * dx7ReadVoice(name) char *name; /* ** Read a 'Dx7Voice' from the file 'name' and return it, ** or NULL if there was a problem. See 'readDx7Voice()'. */ { FILE *f = fopen(name,"r"); Dx7Voice *v; if (!f) return MidiError("dx7ReadVoice: can't open '%s'\n",name), (Dx7Voice *)0; v = dx7readVoice(f,name); fclose(f); return v; } dx7writeVoice(v,f) Dx7Voice *v; FILE *f; /* ** Write 'v' to 'f', ** Return 1 if successful, 0 if not. ** Should perhaps accommodate different formats (C, da). ** As it is, just writes out 155 hex bytes. */ { int r; write(fileno(f),header,sizeof header), r = write(fileno(f),v,SizeofDx7Voice)==SizeofDx7Voice; trailer[0] = dx7CheckSum(v); write(fileno(f),trailer,sizeof trailer); return r; } dx7WriteVoice(v,name) Dx7Voice *v; char *name; /* ** Write 'v' to the file called 'name'. ** Return 1 if successful, 0 if not. */ { FILE *f = fopen(name,"w"); int r=0; if (f) r=dx7writeVoice(v,f),fclose(f); else MidiError("dx7WriteVoice: couldn't write on '%s'\n",name); return r; } /* main(){ Dx7Voice *v = dx7ReadVoice("flute"); if (v) dx7WriteVoice(v,"wingo"); } */