/***********************************************************************/
/*       inst2iff.c                                August 3, 1986      */
/*                                                                     */
/* Converts sampled sound files on the Instruments dealer demo disks   */
/* to IFF sampled sound files (FORM 8SVX).                             */
/*                                                                     */
/* This program is unconditionally placed in the public domain.  Feel  */
/* free to use code from it for anything you want (even for commercial */
/* purposes).  However, don't just sell this program.  Make some       */
/* improvements first.  Let's see some music programs out there!!!     */
/*                                                                     */
/* Author:  Bobby Deen                                                 */
/*          2506 Morning Glory                                         */
/*          Richardson, Tx. 75081                                      */
/*          (214) 235-4391  (voice)                                    */
/* Send Electronic Mail to:                                            */
/*          Rising Star BBS @ (214) 231-1372 (Echomail)                */
/*       or Amiga Scope BBS @ (214) 288-1537                           */
/***********************************************************************/

#include "exec/types.h"
#include "exec/memory.h"
#include "libraries/dosextens.h"
#include "iff_8svx.h"

struct CompressedSample {
   UWORD technique;
   UWORD numSegments;
   UWORD loopStart;
   UBYTE highOctSize;
   UBYTE lowOctSize;
};


main(argc, argv)
int argc;
char *argv[];
{
int offset;

if (argc != 4 && argc != 5) {
   usage(argv[0]);
   exit(10);
}

offset = 0;
if (argc == 5) {
   offset = atoi (argv[4]);
   if (offset < -9 || offset > 2)
      printf("\nWarning: Octave offset should be in the range -9 to 2\n");
}

convert_inst2iff (argv[1], argv[2], argv[3], offset);

printf("Done\n");
exit(0);

}

/************************************************************************/

convert_inst2iff (origname, IFFname, sampname, offset)
char *origname, *IFFname, *sampname, offset;
{
struct CompressedSample samp;
struct Voice8Header v8hdr;
int status, segsize, size;
long sampfile, IFFfile;
UBYTE *waveform;

sampfile = Open(origname, MODE_OLDFILE);
if (sampfile == 0) {
   Close(sampfile);
   error ("can't open sample file");
}

status = Read (sampfile, &samp, sizeof (samp));
if (status != sizeof(samp)) {
   Close(sampfile);
   error ("can't read sample file");
}

size = 0;
v8hdr.ctOctave = samp.lowOctSize-samp.highOctSize+1;
segsize = 1 << (samp.highOctSize);
v8hdr.oneShotHiSamples = samp.loopStart * segsize;
v8hdr.repeatHiSamples = (samp.numSegments - samp.loopStart) * segsize;
/* (3579545 clocks/sec) / (214 clocks/sample) / (261.6 cycles/sec) */
/* = 64 samples/cycle         (calculated for middle C)            */
if (offset >= 0)  /* each octave is a power of 2 difference in the length */
   v8hdr.samplesPerHiCycle = 64 >> offset;
else
   v8hdr.samplesPerHiCycle = 64 << offset;
/*  convert samples per low cycle to samples per hi cycle */
/*  high octaves are basically useless, though */
v8hdr.samplesPerHiCycle >>= (v8hdr.ctOctave-1);
v8hdr.samplesPerSec = 16726; /* = 214 playback rate = C (B on music demo) */
v8hdr.sCompression = sCmpNone;
v8hdr.volume = Unity;

/* 2^0 + 2^1 + 2^2 + ... + 2^(n-1) = 2^n - 1 */
size = ((1 << v8hdr.ctOctave) - 1)
            * (v8hdr.oneShotHiSamples + v8hdr.repeatHiSamples);

/* MEMF_CHIP not needed since we are not playing the samples */

waveform = (UBYTE *)AllocMem (size, MEMF_PUBLIC);
if (waveform == NULL) {
   Close (sampfile);
   error ("can't allocate waveform");
}

status = Read (sampfile, waveform, size);
Close (sampfile);
if (status != size) {
   FreeMem (waveform, size);
   error ("can't read waveform");
}

/* Now write the sound back out to an IFF file */

IFFfile = Open (IFFname, MODE_NEWFILE);
if (IFFfile == 0) {
   FreeMem (waveform, size);
   error ("can't open IFF file");
}

status = PutSamp (IFFfile, &v8hdr, sampname, NULL, "Commodore-Amiga",
               "From Dealer Demo Instruments disk", waveform, size);

Close(IFFfile);
FreeMem (waveform, size);

if (status)
   error (IffErr());

}

usage(pname)
char *pname;
{
printf("Convert instruments from the Dealer Demo disks to IFF files\n");
printf("\nUsage:\n");
printf("%s InstFileName IFFfileName InstName [octave]\n\n", pname);
printf("where InstFileName = input file name (probably on Instruments: disk\n");
printf("      IFFfileName  = output (IFF) file name\n");
printf("      InstName     = instrument name that goes in IFF file; for example\n");
printf("                       'Guitar', not 'Guitar.samples' or 'Guitar.iff'\n");
printf("      octave       = optional octave offset.  If 'x' key in music demo\n");
printf("                       is 1 octave above middle C, enter 1.  If one\n");
printf("                       octave below, enter -1, etc.  Default = 0\n");

}

/************************************************************************/

error (s)
char *s;
{
printf ("%s\n", s);
exit(20);
}

