home *** CD-ROM | disk | FTP | other *** search
/ The C Users' Group Library 1994 August / wc-cdrom-cusersgrouplibrary-1994-08.iso / vol_100 / 113_01 / a68.c < prev    next >
Text File  |  1985-03-10  |  6KB  |  244 lines

  1. /*
  2.     HEADER:        CUG113;
  3.     TITLE:        6800 Cross-Assembler (BDS C Version);
  4.     FILENAME:    A68.C;
  5.     VERSION:    2.6;
  6.     DATE:        07/22/1985;
  7.  
  8.     DESCRIPTION:    "This program lets you use your CP/M-80-based computer
  9.             to assemble code for the Motorola 6800, 6801, 6802,
  10.             6803, 6808, and 68701 microprocessors.  The program is
  11.             written in BDS C for the best possible performance on
  12.             8-bit machines.  All assembler features are supported
  13.             except relocation, linkage, listing control, and
  14.             macros.";
  15.  
  16.     KEYWORDS:    Software Development, Assemblers, Cross-Assemblers,
  17.             Motorola, MC6800, MC6801;
  18.  
  19.     SEE-ALSO:    CUG149, 6801 Cross-Assembler (Portable);
  20.  
  21.     SYSTEM:        CP/M-80;
  22.     COMPILERS:    BDS C;
  23.  
  24.     WARNINGS:    "This package is specifically tailored to CP/M-80
  25.             machines and the rather non-standard, but high-
  26.             performance BDS C compiler.  For other environments,
  27.             use the portable version of this package on CUG149.";
  28.  
  29.     AUTHORS:    William C. Colley III;
  30. */
  31.  
  32. /*
  33.     6800/6801 Cross-Assembler  v. 2.6
  34.  
  35.     May, 1980
  36.  
  37.     July, 1980 -- Rev. 2.2 consisting of fixing the M errors that
  38.         come from forward references in FDB and FCB pseudo-ops.
  39.  
  40.     October, 1980 -- Rev. 2.3 consisting of updating the assembly
  41.         language file and I/O routines to match and take
  42.         advantage of BDS C V1.4.
  43.  
  44.     October, 1983 -- Rev. 2.4 consisting of adding the CPU pseudo-op,
  45.         adding the 6801 CPU's extra opcodes, and speeding up the
  46.         code a bit.
  47.  
  48.     September, 1984 -- Rev. 2.5 consisting of fixing bugs with the symbol
  49.         table sort, the writing of files to specified drives, and the
  50.         handling of blank input lines.
  51.  
  52.     June, 1985 -- Rev. 2.6 consisting of fixing a bug in the IF block
  53.         nesting mechanism.
  54.  
  55.     Copyright (c) 1980,83,84,85 William C. Colley, III.
  56.  
  57. File:    a68.c
  58.  
  59. It all begins here.
  60. */
  61.  
  62. /*  Get globals:  */
  63.  
  64. #include "a68.h"
  65.  
  66. /*  The assembler starts here.  */
  67.  
  68. main(argc,argv)
  69. int argc;
  70. char *argv[];
  71. {
  72.     int n, m;
  73.  
  74.     puts("6800/6801 Cross-Assembler  v. 2.6\n");
  75.     puts("   Copyright (c) 1980,83,84,85 William C. Colley, III\n");
  76.  
  77.     curdrive = bdos(GETDISK);    /*  Initialize file system.        */
  78.     setfiles(argc,argv);
  79.  
  80.     sympoint = symtbl;        /*  Initialize working areas.        */
  81.     symend = symtbl[SYMBOLS].symname;
  82.     setmem(sympoint,(SYMBOLS * (SYMLEN + 2)),'\0');
  83.     ifstack[ifsp = pc = 0] = pass = 1;
  84.     flshhbf(extend = errcount = hxbytes = 0);
  85.     puts("\nEntering Pass 1.\n");
  86.  
  87.     while (pass != 3)        /*  The actual assembly starts here.    */
  88.     {
  89.     errcode = ' ';
  90.     if (!getlin()) {
  91.         strcpy(linbuf,"\tEND\t\t;You forgot this!\n");
  92.         linptr = linbuf;
  93.         markerr('*');
  94.         ifstack[ifsp] = ON;
  95.     }
  96.     asmline();        /*  Get binary from line.    */
  97.     if (pass > 1) {
  98.         lineout();        /*  In pass 2, list line.    */
  99.         hexout();        /*  In pass 2, build hex file.    */
  100.     }
  101.     pc += nbytes;
  102.     if (!pass) {        /*  This indicates end of pass 1.    */
  103.         pass = 2;
  104.         rewind(source);
  105.  
  106.             /*  Mark symbols as not for direct addressing.    */
  107.  
  108.         for (sympoint = symtbl; sympoint < symend; ++sympoint)
  109.         sympoint -> symname[0] |= 0x80;
  110.  
  111.         ifsp = pc = errcount = extend = 0;
  112.         puts("Entering Pass 2.\n\n");
  113.     }
  114.     }
  115.                 /*  List number of errors.        */
  116.     linptr = linbuf;  *linptr++ = '\n';
  117.     if (!errcount) strcpy(linptr,"No");
  118.     else { putdec(errcount,&linptr);  *linptr = '\0'; }
  119.     strcat(linbuf," error(s).\n");
  120.     puts(linbuf);  putchar('\n');
  121.     if (list != CONO && list != NOFILE) {
  122.     fputs(linbuf,list);  putc('\f',list);
  123.     }
  124.     if (list != NOFILE) {    /*  If needed, sort and list symbols.    */
  125.     n = sortsym();
  126.  
  127.     sympoint = symtbl;
  128.     while (n) {
  129.         linptr = linbuf;
  130.         for (m = 4; ; ) {
  131.         movmem(sympoint->symname,linptr,SYMLEN);
  132.         linptr += 8;  *linptr++ = *linptr++ = ' ';
  133.         puthex4((sympoint++)->symvalu,&linptr);
  134.         if (--n == 0 || --m == 0) break;
  135.         *linptr++ = *linptr++ = *linptr++ = *linptr++ = ' ';
  136.         }
  137.         *linptr++ = '\n';  *linptr = '\0';  fputs(linbuf,list);
  138.     }
  139.     if (list >= LODISK) putc(CPMEOF,list);
  140.     else if (list == LST) putc('\f',list);
  141.     }
  142.     fflush(list);
  143.     fclose(list);
  144.  
  145.     fclose(source);
  146.     wipeout("\n");
  147. }
  148.  
  149. /*
  150. Function to set up the file structure.  Routine is called with
  151. the original argc and argv from main().
  152. */
  153.  
  154. setfiles(argc,argv)
  155. int argc;
  156. char *argv[];
  157. {
  158.     char c, *tptr, sorfname[16],lstfname[16],hexfname[16];
  159.  
  160.     if (!--argc) wipeout("\nNo file info supplied.\n");
  161.     source = list = hex = NOFILE;
  162.  
  163.     sorfname[0] = curdrive + 'A';  sorfname[1] = ':';  tptr = &sorfname[2];
  164.     for (++argv; (c = *(*argv)++) && c != '.'; *tptr++ = c);
  165.     *tptr = '\0';
  166.  
  167.     strcpy(lstfname,sorfname);
  168.     strcpy(hexfname,lstfname);
  169.     strcat(sorfname,".68H");
  170.     strcat(lstfname,".PRN");
  171.     strcat(hexfname,".HEX");
  172.  
  173.     if (!--argc) goto defsorf;
  174.     for (++argv; **argv; ) {
  175.     switch (*(*argv)++) {
  176.         case 'S':    switch (c = *(*argv)++) {
  177.                 case 'A':
  178.                 case 'B':
  179.                 case 'C':
  180.                 case 'D':    sorfname[0] = c;
  181.  
  182.                 case '-':    if (fopen(sorfname,source = &_source)
  183.                         != ERROR) break;
  184.                     wipeout("\nCan't open source.\n");
  185.  
  186.                 default:    goto badcomnd;
  187.             }
  188.             break;
  189.  
  190.         case 'L':    switch (c = *(*argv)++)    {
  191.                 case 'A':
  192.                 case 'B':
  193.                 case 'C':
  194.                 case 'D':    lstfname[0] = c;
  195.  
  196.                 case '-':    if (fcreat(lstfname,list = &_list)
  197.                         != ERROR) break;
  198.                     wipeout("\nCan't open list.\n");
  199.  
  200.                 case 'X':    list = CONO;
  201.                     break;
  202.  
  203.                 case 'Y':    list = LST;
  204.                     break;
  205.  
  206.                 default:    goto badcomnd;
  207.             }
  208.             break;
  209.  
  210.         case 'H':    switch(c = *(*argv)++) {
  211.                 case 'A':
  212.                 case 'B':
  213.                 case 'C':
  214.                 case 'D':    hexfname[0] = c;
  215.  
  216.                 case '-':    if (fcreat(hexfname,hex = &_hex)
  217.                         != ERROR) break;
  218.                     wipeout("\nCan't open hex.\n");
  219.  
  220.                 case 'X':    hex = CONO;
  221.                     break;
  222.  
  223.                 case 'Y':    hex = LST;
  224.                     break;
  225.  
  226.                 default:    goto badcomnd;
  227.             }
  228.             break;
  229.  
  230.         badcomnd:
  231.         default:    wipeout("\nIllegal command line.\n");
  232.     }
  233.     }
  234.     if (source != NOFILE) return;
  235.  
  236.     defsorf:
  237.  
  238.     if (fopen(sorfname,source = &_source) == ERROR)
  239.     wipeout("\nCan't open source.\n");
  240. }
  241.     break;
  242.  
  243.         case 'L':    switch (c = *(*argv)++)    {
  244.                 case 'A':