[alt.sources] Music Scales Program

penneyj@servio.UUCP (D. Jason Penney) (12/27/89)

I posted this program (with a few cosmetic differences) to
rec.music.makers a couple of months ago.  Since our newsfeed is
now 100%, it seems appropriate for me to put it in alt.sources.

This program generates a list of scales or chords that can be
used for practice.  This can be an excellent help for people who
are trying to solidify their familiarity with scales and chords
say, for jazz improvisation.

It has compiled properly on VAX/VMS, Suns, and Microsoft C 5.1.  I
would be surprised if their were any significant porting problems
to other hosts.

Enjoy...

#! /bin/sh
# This is a shell archive.  Remove anything before this line, then unpack
# it by saving it into a file and typing "sh file".  To overwrite existing
# files, type "sh file -c".  You can also feed this as standard input via
# unshar, or by typing "sh <file", e.g..  If this archive is complete, you
# will see the following message at the end:
#		"End of archive 1 (of 1)."
# Contents:  MANIFEST scales.c
# Wrapped by penneyj@slc.com on Tue Dec 26 13:53:38 1989
PATH=/bin:/usr/bin:/usr/ucb ; export PATH
if test -f 'MANIFEST' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'MANIFEST'\"
else
echo shar: Extracting \"'MANIFEST'\" \(176 characters\)
sed "s/^X//" >'MANIFEST' <<'END_OF_FILE'
X   File Name		Archive #	Description
X-----------------------------------------------------------
X MANIFEST                   1	This shipping list
X scales.c                   1	
END_OF_FILE
if test 176 -ne `wc -c <'MANIFEST'`; then
    echo shar: \"'MANIFEST'\" unpacked with wrong size!
fi
# end of 'MANIFEST'
fi
if test -f 'scales.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'scales.c'\"
else
echo shar: Extracting \"'scales.c'\" \(19564 characters\)
sed "s/^X//" >'scales.c' <<'END_OF_FILE'
X/* Random Scale and Chord Generation by D. Jason Penney.  
X   Please acknowledge the author in any reproduction or modification. */
X
X#include <stdio.h>
X#include <time.h>
X
X#if defined(MSDOS)
Xtime_t time(); /* brain-dead MicroSlop C 5.0 doesn't declare it! */
X#endif
X
X#if !defined(FALSE)
X#define FALSE 0
X#define TRUE 1
X#endif
X
X#define NORMAL_EXIT exit(0)
X#define ERROR_EXIT exit(1)
X
X/* Random Number Support */
Xstatic unsigned long randomSeed;
X
X#define RAND_INIT {randomSeed = time(NULL);}
X
X/* cyclic random would be criticized by Knuth, but quite adequate here! */
X#define RAND_NEXT (randomSeed = (unsigned long)((13849L + \
X    27181L * randomSeed) & 65535L))
X
X#define RAND_RANGE(i, j) ((i) + RAND_NEXT % (unsigned long)((j) - (i) + 1))
X
X#define NOTES_IN_CHROMATIC 12
X#define MODAL_SCALE_SIZE 7
X#define MAX_NOTES_IN_LIST 8
X#define OUTFILE_NAME "scales.lst"
X#define HELP_MESSAGE "\
XUsage: %s [-h] [-d] [-a] [-m] [-c] [outname]\n\n\
X             -h: This message only\n\
X             -d: include diatonic scales\n\
X             -a: include altered scales\n\
X             -m: include modal scales\n\
X	     -c: include chords\n\n\
XNo scales or chords are given as a default.\n"
X
X#define LET_C 0
X#define LET_F 3
X
Xtypedef enum {majorScale, pentatonicScale, 
X    dorianScale, phrygianScale, lydianScale, 
X    mixolydianScale, minorScale, locrianScale, harmonicScale, 
X    melodicScale, diminishedScale, hungarianMinorScale, milesDavisScale,
X    wholeToneScale,
X    major7Chord, major9Chord, minorSh7Chord, minor9Sh7Chord, minor7Chord, 
X    minor9Chord, minor7b5Chord, major6Chord, minor6Chord, dominant9Chord,
X    dominant7Chord,
X} ListEType;
X
X#define LIST_SUCCESSOR(x) ((ListEType)((int)(x) + 1))
X#define FIRST_DIATONIC majorScale
X#define LAST_DIATONIC pentatonicScale
X#define FIRST_MODAL dorianScale
X#define LAST_MODAL locrianScale
X#define FIRST_ALTERED harmonicScale
X#define LAST_ALTERED wholeToneScale
X#define LAST_DIATONIC_LIST milesDavisScale
X#define FIRST_CHORD major7Chord
X#define LAST_CHORD dominant7Chord
X
X#define NUM_SCALE_KINDS ((int)(dominant7Chord) + 1)
X				/*different possible scales*/
X
Xtypedef  struct { 
X  int  letter;
X  int  accidental;
X  }  NoteSType; 
X
Xtypedef struct {
X  int size;
X  NoteSType notes[MAX_NOTES_IN_LIST];
X  } NoteListSType;
X
Xtypedef struct {
X  ListEType scaleKind;
X  int itsKey;
X  NoteListSType * theScale;
X  } CardSType;
X
X#define ALL_KEY_SIGS (7 * 2 + 1)
X#define SIG_BIAS 7
X#define NUM_LISTS (ALL_KEY_SIGS * NUM_SCALE_KINDS)
X
Xstatic int MajorIntervals[] = {0, 2, 2, 1, 2, 2, 2};
X
Xstatic NoteSType cycleOfFifths[NOTES_IN_CHROMATIC + 1];
Xstatic NoteSType cycleOfFourths[NOTES_IN_CHROMATIC + 1];
Xstatic NoteListSType allSpellings[NUM_LISTS];
X#define LIST_AT(key, kind) allSpellings[((key) + SIG_BIAS) * NUM_SCALE_KINDS +\
X    (int)(kind)]
X
Xstatic CardSType thisDeck[NUM_LISTS], thisHand[NUM_LISTS];
Xstatic int cardsInDeck, cardsInHand, deckSize;
Xstatic unsigned char includeDiatonics, includeAltereds, 
X          includeModals, includeChords;
Xstatic FILE * outFile;
X
Xstatic void sayNote(f, aNote)
XFILE * f; 
XNoteSType * aNote; 
X{
Xint accidental = aNote->accidental;
Xstatic char letterNames[] = "CDEFGAB";
X
Xfprintf(f, "%c", letterNames[aNote->letter]);
Xfor (; accidental > 0; accidental --) fprintf(f, "#");
Xfor (; accidental < 0; accidental ++) fprintf(f, "b");
X}
X
Xstatic void sayListName(f, aCard)
XFILE     * f; 
XCardSType * aCard;
X{
Xchar * p;
X
Xswitch (aCard->scaleKind) {
Xcase majorScale:        p = " Major (Ionian) "; break;
Xcase dorianScale:       p = " Dorian         "; break;
Xcase phrygianScale:     p = " Phrygian       "; break;
Xcase lydianScale:       p = " Lydian         "; break;
Xcase mixolydianScale:   p = " Mixolydian     "; break;
Xcase minorScale:        p = " Minor (Aeolian)"; break;
Xcase locrianScale:      p = " Locrian        "; break;
Xcase harmonicScale:     p = " Harmonic Minor "; break;
Xcase melodicScale:      p = " Melodic Minor  "; break;
Xcase pentatonicScale:   p = " Pentatonic     "; break;
Xcase diminishedScale:   p = " Diminished     "; break;
Xcase hungarianMinorScale: p = " Hungarian Minor"; break;
Xcase milesDavisScale:   p = " Miles Davis    "; break;
Xcase wholeToneScale:    p = " Whole Tone     "; break;
Xcase major7Chord:       p = "M7              "; break;
Xcase major9Chord:       p = "M9              "; break;
Xcase minorSh7Chord:     p = "- (maj 7)       "; break;
Xcase minor7Chord:       p = "-7              "; break;
Xcase minor9Sh7Chord:	p = "-9 (maj 7)      "; break;
Xcase minor9Chord:       p = "-9              "; break;
Xcase minor7b5Chord:     p = "-7 (b5)         "; break;
Xcase major6Chord:       p = "6               "; break;
Xcase minor6Chord:       p = "-6              "; break;
Xcase dominant7Chord:    p = "7               "; break;
Xcase dominant9Chord:    p = "9               "; break;
Xdefault:                p = " Internal Error!"; break;
X}
X
XsayNote(f, &aCard->theScale->notes[0]);
Xfprintf(f, "%s", p);
X}
X
Xstatic void raiseNote(aNote, aLetterInterval, aChromaticInterval)
XNoteSType     * aNote; 
Xint     aLetterInterval; 
Xint     aChromaticInterval; 
X{
X/*Establish proper letter interval*/
Xwhile (aLetterInterval != 0) {
X  aChromaticInterval --;
X  aNote->letter = (aNote->letter + 1) % 7;
X  aLetterInterval --;
X  if ((aNote->letter == LET_F) || (aNote->letter == LET_C))
X    continue;
X  aChromaticInterval --; /* whole step */
X  }
XaNote->accidental += aChromaticInterval;
X}
X
Xstatic void addCard(keySig, scaleKind)
Xint keySig;
XListEType scaleKind;
X{
X  thisDeck[deckSize].itsKey = keySig;
X  thisDeck[deckSize].scaleKind = scaleKind;
X  thisDeck[deckSize].theScale = &LIST_AT(keySig, scaleKind);
X  deckSize ++;
X}
X
Xstatic void buildDeck() {
Xint keySig;
XListEType thisScale;
X
XdeckSize = 0;
Xfor (keySig = -SIG_BIAS; keySig <= SIG_BIAS; keySig ++) {
X  if (includeDiatonics) {
X    for (thisScale = FIRST_DIATONIC; (int)thisScale <= (int)LAST_DIATONIC;
X	thisScale = LIST_SUCCESSOR(thisScale))
X      addCard(keySig, thisScale);
X    }
X  if (includeAltereds) {
X    for (thisScale = FIRST_ALTERED; (int)thisScale <= (int)LAST_ALTERED;
X	thisScale = LIST_SUCCESSOR(thisScale))
X      addCard(keySig, thisScale);
X    }
X  if (includeModals) {
X    for (thisScale = FIRST_MODAL; (int)thisScale <= (int)LAST_MODAL;
X	thisScale = LIST_SUCCESSOR(thisScale))
X      addCard(keySig, thisScale);
X    }
X  if (includeChords) {
X    for (thisScale = FIRST_CHORD; (int)thisScale <= (int)LAST_CHORD;
X	thisScale = LIST_SUCCESSOR(thisScale))
X      addCard(keySig, thisScale);
X    }
X  }
X}
X
Xstatic void dealCard(return_value)
XCardSType * return_value;
X{
Xint i = (int)RAND_RANGE(0, cardsInDeck - 1); /*face value on card*/
X
X*return_value = thisDeck[i];
X
X/*Move all remaining cards over to fill vacant slot*/
Xfor (; i < (cardsInDeck - 1); i++)
X  thisDeck[i] = thisDeck[i + 1];
XcardsInDeck --;
X}
X
Xstatic void dealDeck() {
X
XcardsInDeck = deckSize;
Xfor (cardsInHand = 0; cardsInHand < deckSize; cardsInHand ++)
X  dealCard(&thisHand[cardsInHand]);
X}
X
Xstatic void sayList(f, thisCard)
XFILE     * f; 
XCardSType * thisCard;
X{
Xint i;
XNoteListSType * thisList = thisCard->theScale;
Xint itsKey = thisCard->itsKey;
XListEType itsKind = thisCard->scaleKind;
X
Xfor (i = 0; i < thisList->size; i++) {
X  sayNote(f, &thisList->notes[i]);
X
X  /* ad hoc for altered scales */
X  if ((itsKind == melodicScale && (i == 5 || i == 6)) ||
X     (itsKind == harmonicScale && i == 6)) {
X    if (LIST_AT(itsKey, minorScale).notes[i].accidental == -1)
X      fprintf(f, "n");
X    }
X  else
X  if (itsKind == milesDavisScale && i == 3) {
X    if (LIST_AT(itsKey, milesDavisScale).notes[2].accidental == -1)
X      fprintf(f, "n");
X    }
X  else
X  if (itsKind == hungarianMinorScale && i == 4) {
X    if (LIST_AT(itsKey, hungarianMinorScale).notes[3].accidental == -1)
X      fprintf(f, "n");
X    }
X  else
X  if (itsKind == hungarianMinorScale && i == 7) {
X    if (LIST_AT(itsKey, minorScale).notes[6].accidental == -1)
X      fprintf(f, "n");
X    }
X  else
X  if (itsKind == diminishedScale && i == 7) {
X    if (LIST_AT(itsKey, minorScale).notes[6].accidental == -1)
X      fprintf(f, "n");
X    }
X  else
X  if (itsKind == diminishedScale && i == 6) {
X    if (LIST_AT(itsKey, diminishedScale).notes[5].accidental == -1)
X      fprintf(f, "n");
X    }
X  else
X  if (itsKind == diminishedScale && i == 4) {
X    if (LIST_AT(itsKey, minorScale).notes[4].accidental == 1)
X      fprintf(f, "n");
X    }
X
X  if (i != thisList->size - 1)
X    fprintf(f, " ");
X  }
X
Xif (itsKind == melodicScale) {
X  fprintf(f, " ");
X  sayNote(f, &LIST_AT(itsKey, melodicScale).notes[0]);
X  fprintf(f, " ");
X  for (i = thisList->size - 1; i >= 0; i--) {
X    /*7th and 6th lowered when descending*/
X    sayNote(f, &LIST_AT(itsKey, minorScale).notes[i]);
X    if (i == 5 || i == 6) {
X      if (LIST_AT(itsKey, minorScale).notes[i].accidental == 0)
X	fprintf(f, "n");
X      }
X    if (i != 0)
X      fprintf(f, " ");
X    }
X  }
X}
X
Xstatic void dumpAccidentals( f, theScale )
XFILE     * f; 
Xint     theScale; 
X{
Xint i;
X
Xif (theScale > 0)
X  for (i = 1; i <= theScale; i++) {
X    sayNote(f, &cycleOfFifths[5 + i]);
X    if (i != theScale)
X      fprintf(f, " ");
X    }
Xelse
X  for (i = 1; i <=  -theScale; i++) {
X    sayNote(f, &cycleOfFourths[i + 1]);
X    if (i !=  -theScale)
X      fprintf(f, " ");
X    }
X}
X
Xstatic void dumpShuffle( f )
XFILE     * f; 
X{
Xint i;
XListEType theKind;
Xint theKey;
X
Xfprintf(f, "Random Order of %d Possible Scales or Chords\n\n", deckSize);
Xfor (i = 0; i < deckSize; i++) { /*write a card*/
X  theKey = thisHand[i].itsKey;
X  theKind = thisHand[i].scaleKind;
X  fprintf(f, "___ %3d ", i + 1);
X  sayListName(f, &thisHand[i]);
X  if ((int)theKind <= (int)LAST_DIATONIC_LIST) {
X    if (theKey > 0) {
X      fprintf(f, "\t(%d sharp%s:  ", theKey, (theKey > 1 ? "s" : " "));
X      dumpAccidentals(f, theKey);
X      fprintf(f, ")");
X      }
X    else
X    if (theKey < 0) {
X      fprintf(f, "\t(%d  flat%s:  ", -theKey, (theKey < -1 ? "s" : " "));
X      dumpAccidentals(f, theKey);
X      fprintf(f, ")");
X      }
X  }
X  fprintf(f, "\n\tSpelling:\t");
X  sayList(f, &thisHand[i]);
X  fprintf(f, "\n");
X  if ((i + 1) % 30 == 0)
X    fprintf(f, "\014\n"); /* form-feed */
X  }
Xfprintf(f, "\n\n");
X}
X
Xstatic void initialize() {
XNoteSType thisNote;
Xint i,j;
XListEType theScale;
X
XRAND_INIT;
X
X/*fill in cycles of fifths and fourths*/
XthisNote.letter = LET_C;
XthisNote.accidental = 0;
XcycleOfFifths[0] = thisNote;
Xfor (i = 1; i <= NOTES_IN_CHROMATIC; i++) {
X  raiseNote(&thisNote, 4, 7); /* perfect fifth */
X  cycleOfFifths[i] = thisNote;
X  }
XthisNote.letter = LET_C;
XthisNote.accidental = 0;
XcycleOfFourths[0] = thisNote;
Xfor (i = 1; i <= NOTES_IN_CHROMATIC; i++) {
X  raiseNote(&thisNote, 3, 5); /* perfect fourth */
X  cycleOfFourths[i] = thisNote;
X  }
X
X/*spell scales for all signatures:*/
Xfor (i =  -SIG_BIAS; i <= SIG_BIAS; i++) {
X  /*fill in all scales for this key signature*/
X
X  /*for each key signature, major scale tonic is spelled in cycle of fifths.*/
X  if (i < 0)
X    thisNote = cycleOfFourths[ -i];
X  else
X    thisNote = cycleOfFifths[i];
X  LIST_AT(i, majorScale).notes[0] = thisNote;
X  /*Spell the rest of the notes in this key signature*/
X  for (j = 1; j < MODAL_SCALE_SIZE; j++) {
X    raiseNote(&thisNote, 1, MajorIntervals[j]); /* a second */
X    LIST_AT(i, majorScale).notes[j] = thisNote;
X    }
X  LIST_AT(i, majorScale).size = MODAL_SCALE_SIZE;
X
X  /*Fill in modal versions of key signature by simple rotation*/
X  for (theScale = FIRST_MODAL;
X      (int)theScale <= (int)LAST_MODAL;
X      theScale = LIST_SUCCESSOR(theScale)) {
X    for (j = 0; j < MODAL_SCALE_SIZE; j++)
X      LIST_AT(i, theScale).notes[j] = LIST_AT(i, majorScale).notes[
X	      ((unsigned int)(theScale) - (unsigned int)(dorianScale) + 1
X	      + j) % MODAL_SCALE_SIZE];
X    LIST_AT(i, theScale).size = MODAL_SCALE_SIZE;
X    }
X
X  /*copy minor to harmonic*/
X  LIST_AT(i, harmonicScale) = LIST_AT(i, minorScale);
X  /*raise 7th*/
X  raiseNote(&LIST_AT(i, harmonicScale).notes[6], 0, 1);
X
X  /*copy harmonic to melodic*/
X  LIST_AT(i, melodicScale) = LIST_AT(i, harmonicScale);
X  /*raise 6th*/
X  raiseNote(&LIST_AT(i, melodicScale).notes[5], 0, 1);
X
X  /* Build pentatonic */
X  LIST_AT(i, pentatonicScale) = LIST_AT(i, majorScale);
X  LIST_AT(i, pentatonicScale).notes[3] = LIST_AT(i, majorScale).notes[4];
X  LIST_AT(i, pentatonicScale).notes[4] = LIST_AT(i, majorScale).notes[5];
X  LIST_AT(i, pentatonicScale).size = 5;
X
X  /* Hungarian Minor -- harmonic minor with raised fourth as extra note */
X  LIST_AT(i, hungarianMinorScale) = LIST_AT(i, harmonicScale);
X  for (j = 5; j <= 7; j ++)
X    LIST_AT(i, hungarianMinorScale).notes[j] =
X	LIST_AT(i, harmonicScale).notes[j - 1];
X  LIST_AT(i, hungarianMinorScale).notes[4] =
X      LIST_AT(i, hungarianMinorScale).notes[3];
X  raiseNote(&LIST_AT(i, hungarianMinorScale).notes[4], 0, 1);
X  LIST_AT(i, hungarianMinorScale).size = 8;
X
X  /* Miles Davis scale -- a rather warped phrygian scale */
X  LIST_AT(i, milesDavisScale) = LIST_AT(i, phrygianScale);
X  for (j = 4; j <= 7; j ++)
X    LIST_AT(i, milesDavisScale).notes[j] =
X	LIST_AT(i, phrygianScale).notes[j - 1];
X  LIST_AT(i, milesDavisScale).notes[3] =
X      LIST_AT(i, milesDavisScale).notes[2];
X  raiseNote(&LIST_AT(i, milesDavisScale).notes[3], 0, 1);
X  LIST_AT(i, milesDavisScale).size = 8;
X
X  /* Somewhat arbitrarily build whole-tone scale on each major tonic */
X   LIST_AT(i, wholeToneScale).notes[0] = LIST_AT(i, majorScale).notes[0];
X  for (j = 1; j <= 5; j ++) {
X    LIST_AT(i, wholeToneScale).notes[j] = LIST_AT(i, wholeToneScale).notes[j - 1];
X    raiseNote(&LIST_AT(i, wholeToneScale).notes[j], 1, 2);
X    }
X  LIST_AT(i, wholeToneScale).size = 6;
X
X  /* Diminished scale, really weird... */
X  LIST_AT(i, diminishedScale) = LIST_AT(i, minorScale);
X  LIST_AT(i, diminishedScale).notes[7] = LIST_AT(i, melodicScale).notes[6];
X  LIST_AT(i, diminishedScale).notes[6] = LIST_AT(i, melodicScale).notes[5];
X  raiseNote(&LIST_AT(i, diminishedScale).notes[4], 0, -1);
X  LIST_AT(i, diminishedScale).size = 8;
X
X  /* major 7 chord */
X  LIST_AT(i, major7Chord).size = 4;
X  LIST_AT(i, major7Chord).notes[0] = LIST_AT(i, majorScale).notes[0];
X  LIST_AT(i, major7Chord).notes[1] = LIST_AT(i, majorScale).notes[2];
X  LIST_AT(i, major7Chord).notes[2] = LIST_AT(i, majorScale).notes[4];
X  LIST_AT(i, major7Chord).notes[3] = LIST_AT(i, majorScale).notes[6];
X
X  /* major 9 chord */
X  LIST_AT(i, major9Chord).size = 5;
X  LIST_AT(i, major9Chord).notes[0] = LIST_AT(i, majorScale).notes[0];
X  LIST_AT(i, major9Chord).notes[1] = LIST_AT(i, majorScale).notes[1];
X  LIST_AT(i, major9Chord).notes[2] = LIST_AT(i, majorScale).notes[2];
X  LIST_AT(i, major9Chord).notes[3] = LIST_AT(i, majorScale).notes[4];
X  LIST_AT(i, major9Chord).notes[4] = LIST_AT(i, majorScale).notes[6];
X
X  /* minor maj 7 chord */
X  LIST_AT(i, minorSh7Chord).size = 4;
X  LIST_AT(i, minorSh7Chord).notes[0] = LIST_AT(i, minorScale).notes[0];
X  LIST_AT(i, minorSh7Chord).notes[1] = LIST_AT(i, minorScale).notes[2];
X  LIST_AT(i, minorSh7Chord).notes[2] = LIST_AT(i, minorScale).notes[4];
X  LIST_AT(i, minorSh7Chord).notes[3] = LIST_AT(i, harmonicScale).notes[6];
X
X  /* minor 9 maj 7 chord */
X  LIST_AT(i, minor9Sh7Chord).size = 5;
X  LIST_AT(i, minor9Sh7Chord).notes[0] = LIST_AT(i, minorScale).notes[0];
X  LIST_AT(i, minor9Sh7Chord).notes[1] = LIST_AT(i, minorScale).notes[1];
X  LIST_AT(i, minor9Sh7Chord).notes[2] = LIST_AT(i, minorScale).notes[2];
X  LIST_AT(i, minor9Sh7Chord).notes[3] = LIST_AT(i, minorScale).notes[4];
X  LIST_AT(i, minor9Sh7Chord).notes[4] = LIST_AT(i, harmonicScale).notes[6];
X
X  /* minor 7 chord */
X  LIST_AT(i, minor7Chord).size = 4;
X  LIST_AT(i, minor7Chord).notes[0] = LIST_AT(i, minorScale).notes[0];
X  LIST_AT(i, minor7Chord).notes[1] = LIST_AT(i, minorScale).notes[2];
X  LIST_AT(i, minor7Chord).notes[2] = LIST_AT(i, minorScale).notes[4];
X  LIST_AT(i, minor7Chord).notes[3] = LIST_AT(i, minorScale).notes[6];
X
X  /* minor 9 chord */
X  LIST_AT(i, minor9Chord).size = 5;
X  LIST_AT(i, minor9Chord).notes[0] = LIST_AT(i, minorScale).notes[0];
X  LIST_AT(i, minor9Chord).notes[1] = LIST_AT(i, minorScale).notes[1];
X  LIST_AT(i, minor9Chord).notes[2] = LIST_AT(i, minorScale).notes[2];
X  LIST_AT(i, minor9Chord).notes[3] = LIST_AT(i, minorScale).notes[4];
X  LIST_AT(i, minor9Chord).notes[4] = LIST_AT(i, minorScale).notes[6];
X
X  /* minor 7 flat 5 chord */
X  LIST_AT(i, minor7b5Chord).size = 4;
X  LIST_AT(i, minor7b5Chord).notes[0] = LIST_AT(i, minorScale).notes[0];
X  LIST_AT(i, minor7b5Chord).notes[1] = LIST_AT(i, minorScale).notes[2];
X  LIST_AT(i, minor7b5Chord).notes[2] = LIST_AT(i, minorScale).notes[4];
X  LIST_AT(i, minor7b5Chord).notes[3] = LIST_AT(i, minorScale).notes[6];
X  raiseNote(&LIST_AT(i, minor7b5Chord).notes[2], 0, -1);
X
X  /* dominant 7 chord */
X  LIST_AT(i, dominant7Chord).size = 4;
X  LIST_AT(i, dominant7Chord).notes[0] = LIST_AT(i, majorScale).notes[4];
X  LIST_AT(i, dominant7Chord).notes[1] = LIST_AT(i, majorScale).notes[6];
X  LIST_AT(i, dominant7Chord).notes[2] = LIST_AT(i, majorScale).notes[1];
X  LIST_AT(i, dominant7Chord).notes[3] = LIST_AT(i, majorScale).notes[3];
X
X  /* dominant 9 chord */
X  LIST_AT(i, dominant9Chord).size = 5;
X  LIST_AT(i, dominant9Chord).notes[0] = LIST_AT(i, majorScale).notes[4];
X  LIST_AT(i, dominant9Chord).notes[1] = LIST_AT(i, majorScale).notes[5];
X  LIST_AT(i, dominant9Chord).notes[2] = LIST_AT(i, majorScale).notes[6];
X  LIST_AT(i, dominant9Chord).notes[3] = LIST_AT(i, majorScale).notes[1];
X  LIST_AT(i, dominant9Chord).notes[4] = LIST_AT(i, majorScale).notes[3];
X
X  /* major 6 chord */
X  LIST_AT(i, major6Chord).size = 4;
X  LIST_AT(i, major6Chord).notes[0] = LIST_AT(i, majorScale).notes[0];
X  LIST_AT(i, major6Chord).notes[1] = LIST_AT(i, majorScale).notes[2];
X  LIST_AT(i, major6Chord).notes[2] = LIST_AT(i, majorScale).notes[4];
X  LIST_AT(i, major6Chord).notes[3] = LIST_AT(i, majorScale).notes[5];
X
X  /* minor 6 chord */
X  LIST_AT(i, minor6Chord).size = 4;
X  LIST_AT(i, minor6Chord).notes[0] = LIST_AT(i, dorianScale).notes[0];
X  LIST_AT(i, minor6Chord).notes[1] = LIST_AT(i, dorianScale).notes[2];
X  LIST_AT(i, minor6Chord).notes[2] = LIST_AT(i, dorianScale).notes[4];
X  LIST_AT(i, minor6Chord).notes[3] = LIST_AT(i, dorianScale).notes[5];
X
X   } /* end of this key signature */
X} /* end of initialize */
X
Xmain(argc, argv)
X  int argc;
X  char *argv[];
X{
Xchar * outname;
Xint i;
X
X/* Analyze input arguments, looking for modes */
XincludeDiatonics = FALSE;
XincludeAltereds = FALSE;
XincludeModals = FALSE;
XincludeChords = FALSE;
Xoutname = OUTFILE_NAME;
Xif (argc <= 1) {
X  printf(HELP_MESSAGE, argv[0]);
X  NORMAL_EXIT;
X  }
Xfor (i = 1; i < argc; i ++) {
X  if (argv[i][0] != '-') {
X    if (i != argc -1) {
X      printf(HELP_MESSAGE, argv[0]);
X      ERROR_EXIT;
X      }
X    outname = argv[i];
X    continue;
X    }
X  if (strlen(argv[i]) != 2) {
X    printf(HELP_MESSAGE, argv[0]);
X    ERROR_EXIT;
X    }
X  switch (argv[i][1]) {
X  case 'h':
X    printf(HELP_MESSAGE, argv[0]);
X    NORMAL_EXIT;
X
X  case 'd': includeDiatonics = TRUE; break;
X  case 'a': includeAltereds = TRUE;  break;
X  case 'm': includeModals = TRUE;    break;
X  case 'c': includeChords = TRUE;    break;
X
X  default:
X    printf(HELP_MESSAGE, argv[0]);
X    ERROR_EXIT;
X    }
X  }
Xif (! (includeDiatonics || includeAltereds || includeModals || includeChords)) {
X  printf("Just what exactly did you have in mind?\n");
X  ERROR_EXIT;
X  }
X
Xprintf("Initializing...\n");
Xinitialize();
X
Xprintf("Building deck...");
XbuildDeck();
Xprintf("%d cards made\n", deckSize);
X
Xprintf("Shuffling list...\n");
XdealDeck();
XoutFile = fopen(outname, "w");
Xif (outFile == NULL) {
X  printf("Can't open %s\n", outname);
X  return 2;
X  }
Xprintf("Writing list to %s\n", outname);
XdumpShuffle(outFile);
Xfclose(outFile);
Xprintf("Done!\n");
XNORMAL_EXIT;
Xreturn 0; /* for lint */
X}
END_OF_FILE
if test 19564 -ne `wc -c <'scales.c'`; then
    echo shar: \"'scales.c'\" unpacked with wrong size!
fi
# end of 'scales.c'
fi
echo shar: End of archive 1 \(of 1\).
cp /dev/null ark1isdone
MISSING=""
for I in 1 ; do
    if test ! -f ark${I}isdone ; then
	MISSING="${MISSING} ${I}"
    fi
done
if test "${MISSING}" = "" ; then
    echo You have the archive.
    rm -f ark[1-9]isdone
else
    echo You still need to unpack the following archives:
    echo "        " ${MISSING}
fi
##  End of shell archive.
exit 0
-- 
D. Jason Penney                  Ph: (503) 629-8383
Beaverton, OR 97006              uucp: ...uunet!servio!penneyj
STANDARD DISCLAIMER:  Should I or my opinions be caught or killed, the
company will disavow any knowledge of my actions...