home *** CD-ROM | disk | FTP | other *** search
/ Crawly Crypt Collection 1 / crawlyvol1.bin / program / compiler / nasm20b / nasm_src / md_suck.c < prev    next >
C/C++ Source or Header  |  1993-01-19  |  11KB  |  428 lines

  1. /* ---------------------------------------------------------------------- */
  2. /*                   Copyright (C) 1991 by Natürlich!                     */
  3. /*                      This file is copyrighted!                         */
  4. /*                Refer to the documentation for details.                 */
  5. /* ---------------------------------------------------------------------- */
  6. /* Code that tokenizes and differentiates between MACRO calls and */
  7. /* real life 6502 assembler mnemos. Also tokenizes directives     */
  8.  
  9. #if OS == MSDOS
  10. # define _brk  xbrk
  11. #endif
  12.  
  13.  
  14. /* These are all the characters that happen to appear in 6502 mnemos */
  15. extern byte
  16.    _adc[],_and[],_asl[],_bcc[],_bcs[],_beq[],_bit[],_bmi[],_bne[],
  17.    _bpl[],_bra[],_brk[],_bvc[],_bvs[],_clc[],_cld[],_cli[],_clv[],
  18.    _cmp[],_cpx[],_cpy[],_dea[],_dec[],_dex[],_dey[],_eor[],_ina[],
  19.    _inc[],_inx[],_iny[],_jmp[],_jsr[],_lda[],_ldx[],_ldy[],_lsr[],
  20.    _nop[],_ora[],_pha[],_php[],_phx[],_phy[],_pla[],_plp[],_plx[],
  21.    _ply[],_rol[],_ror[],_rti[],_rts[],_sbc[],_sec[],_sed[],_sei[],
  22.    _sta[],_stx[],_sty[],_stz[],_tax[],_tay[],_trb[],_tsb[],_tsx[],
  23.    _txa[],_txs[],_tya[];
  24.  
  25. /* -------------------------------------------------------------- */
  26. /* We use the first character of the instruction (or macro call)  */
  27. /* to decide on a (struct instr) that happens to keep the remain- */
  28. /* ing two letters. If a match is made, a alphabetically index is */
  29. /* sent over.                                                     */
  30. /*       [this looked pretty fast in the beginning, but...]       */
  31. /* -------------------------------------------------------------- */
  32. #if BIGENDIAN
  33. # define drop( b, a) ( ((word) (a) << 8) | (word) (b))
  34. #else
  35. # define drop( a, b) ( ((word) (a) << 8) | (word) (b))
  36. #endif
  37.  
  38. #define EOA    { 0, 0 }
  39.  
  40. struct instr
  41. {
  42.    word        d;
  43.    byte huge   *tab;
  44. };
  45.  
  46. static struct instr
  47.    a_[] =
  48.    {
  49.       { drop('D','C'), _adc }, { drop('N','D'), _and },
  50.       { drop('S','L'), _asl }, EOA
  51.    },
  52.    b_[] =
  53.    {
  54.       { drop('C','C'), _bcc }, { drop('C','S'), _bcs },
  55.       { drop('E','Q'), _beq }, { drop('I','T'), _bit },
  56.       { drop('M','I'), _bmi }, { drop('N','E'), _bne },
  57.       { drop('P','L'), _bpl }, { drop('R','K'), _brk },
  58.       { drop('R','A'), _bra }, { drop('V','C'), _bvc },
  59.       { drop('V','S'), _bvs }, EOA
  60.    },
  61.    c_[] =
  62.    {
  63.       { drop('L','C'), _clc }, { drop('L','D'), _cld },
  64.       { drop('L','I'), _cli }, { drop('L','V'), _clv },
  65.       { drop('M','P'), _cmp }, { drop('P','X'), _cpx },
  66.       { drop('P','Y'), _cpy }, EOA
  67.    },
  68.    d_[] =
  69.    {
  70.       { drop('E','A'), _dea }, { drop('E','C'), _dec },
  71.       { drop('E','X'), _dex }, { drop('E','Y'), _dey }, EOA
  72.    },
  73.    e_[] =
  74.    {
  75.       { drop('O','R'), _eor }, EOA
  76.    },
  77.    i_[] =
  78.    {
  79.       { drop('N','A'), _ina }, { drop('N','C'), _inc },
  80.       { drop('N','X'), _inx }, { drop('N','Y'), _iny }, EOA
  81.    },
  82.    j_[] =
  83.    {
  84.       { drop('M','P'), _jmp }, { drop('S','R'), _jsr }, EOA
  85.    },
  86.    l_[] =
  87.    {
  88.       { drop('D','A'), _lda }, { drop('D','X'), _ldx },
  89.       { drop('D','Y'), _ldy }, { drop('S','R'), _lsr }, EOA
  90.    },
  91.    n_[] =
  92.    {
  93.       { drop('O','P'), _nop }, EOA
  94.    },
  95.    o_[] =
  96.    {
  97.       { drop('R','A'), _ora }, EOA
  98.    },
  99.    p_[] =
  100.    {
  101.       { drop('H','A'), _pha }, { drop('H','P'), _php },
  102.       { drop('H','X'), _phx }, { drop('H','Y'), _phy },
  103.       { drop('L','A'), _pla }, { drop('L','P'), _plp },
  104.       { drop('L','X'), _plx }, { drop('L','Y'), _ply }, EOA
  105.    },
  106.    r_[] =
  107.    {
  108.       { drop('O','L'), _rol }, { drop('O','R'), _ror },
  109.       { drop('T','I'), _rti }, { drop('T','S'), _rts }, EOA
  110.    },
  111.    s_[] =
  112.    {
  113.       { drop('B','C'), _sbc }, { drop('E','C'), _sec },
  114.       { drop('E','D'), _sed }, { drop('E','I'), _sei },
  115.       { drop('T','A'), _sta }, { drop('T','X'), _stx },
  116.       { drop('T','Y'), _sty }, { drop('T','Z'), _stz }, EOA
  117.    },
  118.    t_[] =
  119.    {
  120.       { drop('A','X'), _tax }, { drop('A','Y'), _tay },
  121.       { drop('R','B'), _trb }, { drop('S','B'), _tsb },
  122.       { drop('S','X'), _tsx }, { drop('X','A'), _txa },
  123.       { drop('X','S'), _txs }, { drop('Y','A'), _tya }, EOA
  124.    },
  125.  
  126.    *i_arr[] =
  127.    {
  128.       (struct instr *) 0, a_, b_, c_, d_, e_, i_,
  129.       j_, l_, n_, o_, p_, r_, s_, t_
  130.    };
  131.  
  132. /* Indexes for the Instruction_ARRay, note that    i_arr[0] = 0   */
  133. static int       
  134.    starters[] = 
  135.    {     
  136.    /* 0 1 2 3 4 5 6 7 8 9 :         ? @                        */
  137.       0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
  138.    /* A B C D E F G H I J K L M N  O  P Q  R  S  T U V W X Y Z */
  139.       1,2,3,4,5,0,0,0,6,7,0,8,0,9,10,11,0,12,13,14,0,0,0,0,0,0,
  140.    /*         _ */   
  141.       0,0,0,0,0 
  142.    };
  143.  
  144. macro_suckin()
  145. {
  146.    register byte  *p = (byte *) yytext,
  147.                   c_ = c,
  148.                   *p_table = is_what;
  149.    register word  i = 1;
  150.  
  151.    ENTER("macro_suckin");
  152. #if VERSION && FINPUT_IO && QINPUT_IO && QMACRO
  153.    {
  154.       register byte huge   *pt  = bp->p;
  155.       register byte        *tab = _uptable; 
  156.       register lword       rem  = bp->remain;
  157.    
  158.       while( tis_ident( c_))
  159.       {
  160.          *p++ = c_;
  161.          c_   = quinput( rem, pt, tab);
  162.          i++;
  163.       }
  164.       if( bp)
  165.       {
  166.          bp->remain = rem;
  167.          bp->p      = pt;
  168.       }
  169.     }
  170. #else
  171.    while( tis_ident(c_))                     /* Suck in macro call or   */
  172.    {                                         /* instruction             */
  173.       *p++ = c_;                             /* convert to upper & save */
  174.       c_   = uinput();                       /* get fresh input         */
  175.       i++;
  176.    }
  177. #endif
  178.    *p = 0;
  179.    c  = c_;
  180.    p  = (byte *) yytext;                     /* (*) */
  181.    IMESS("Macro/Instr.: %s", (lword) p, 4);
  182.  
  183.    if( i == 4)
  184.    {
  185.       register struct instr huge *q;
  186.  
  187.       if( q = i_arr[ starters[ *p - '0']])   /* instr ? */
  188.       {
  189. #if WORD_EVEN
  190.          p++;
  191.          c_ = p[1];                          /* looks very possible al- */
  192.          i  = ((word) *p << 8) | c_;         /* beit not certain        */
  193. #else
  194.          i  = *(word *) &yytext[ 1];
  195. #endif
  196.          IMESS("two chars together %4lX", (lword) i, 4);
  197.          do
  198.             if( i == q->d)
  199.             {
  200.                yylval = (lword) q->tab;      /* Yup. Send index & token */
  201.                LEAVE();
  202.                return( T_INSTR);
  203.             }
  204.          while( (++q)->d);
  205.          i = 4;
  206.       }
  207.    }
  208.    yy_txt2val( i);
  209.    state  = AFTERELSE;
  210.    LEAVE();
  211.    return( T_IDENT);                         /* It's a MACRO call */
  212. }
  213.  
  214. /* -------------------------------------------------------------------- */
  215. /*   There are only that few people who use directives often. So here   */
  216. /*   speed isn't of that much importance.                               */
  217. /* -------------------------------------------------------------------- */
  218. #define AF  AFTERFLOAT
  219. #define AI  AFTERINCLUDE
  220. #define AO  AFTEROPTION
  221. #undef  EOA
  222. #define EOA { "", 0, 0 }
  223.  
  224. struct direc
  225. {
  226.    char  *string;
  227.    int   token, state;
  228. };  
  229.  
  230. static struct direc
  231.    da_[] =
  232.    {
  233.       { "AND",    T_AND,   0 },  EOA
  234.    },
  235.    db_[] =
  236.    {
  237.       { "BYTE",   T_BYTE,  0 },  EOA
  238.    },
  239.    dc_[] =
  240.    {
  241.       { "CALL",   T_CALL,  0 },  { "CBYTE",  T_CBYTE, 0 },  EOA
  242.    },
  243.    dd_[] =
  244.    {
  245.       { "DBYTE",  T_DBYTE, 0 },  { "DEF",     T_DEF,   0 },
  246.       { "DS",     T_DS,    0 },  EOA
  247.    },
  248.    de_[] =
  249.    {
  250.       { "ELSE",   T_ELSE,  0 },  { "END",    T_END,   0 },
  251.       { "ENDIF",  T_ENDIF, 0 },  { "ENDM",   T_ENDM,  0 },
  252.       { "EQU",    '=',     0 },  { "ERROR",  T_ERROR, 0 },    EOA
  253.    },
  254.    df_[] =
  255.    {
  256.       { "FLOAT",  T_FLOAT, AF }, EOA
  257.    },
  258.    di_[] =
  259.    {
  260.       { "IF",     T_IF,    0 },  { "INCLUDE",T_INCLUDE, AI }, EOA
  261.    },
  262.    dl_[] =
  263.    {
  264.       { "LOCAL",  T_LOCAL, 0 },  EOA
  265.    },
  266.    dm_[] =
  267.    {
  268.       { "MACRO",  T_MACRO, 0 },  EOA
  269.    },
  270.    dn_[] =
  271.    {
  272.       { "NOT",    T_NOT,   0 },  EOA
  273.    },
  274.    do_[] =
  275.    {
  276.       { "OPT",    T_OPT,   AO},  { "OR",     T_OR, 0 },  
  277.       { "ORG",    T_ORG,   0 },  EOA
  278.    },
  279.    dp_[] =
  280.    {
  281.       { "PAGE",   T_PAGE,  0 },  EOA
  282.    },
  283.    dr_[] =
  284.    {
  285.       { "REF",    T_REF,   0 },  { "REPT",   T_REPT,  0 },  EOA
  286.    },
  287.    ds_[] =
  288.    {
  289.       { "SBYTE",  T_SBYTE, 0 },  { "SET",    T_SET,   0 },  EOA
  290.    },
  291.    dt_[] =
  292.    {
  293.       { "TAB",    T_TAB,   0 },  { "TITLE",  T_TITLE, 0 },  EOA
  294.    },
  295.    du_[] =
  296.    {
  297.       { "UNDEF",  T_UNDEF, 0 },  EOA
  298.    },
  299.    dv_[] =
  300.    {
  301.       { "VFL_BOCHUM", T_ZEXT, 0},EOA
  302.    },
  303.    dw_[] =
  304.    {
  305.       { "WARNING",   T_WARN, 0 }, { "WORD",   T_WORD,  0 },  EOA
  306.    },
  307.    dz_[] =
  308.    {
  309.       { "ZEXT",   T_ZEXT,  0 },  EOA
  310.    },
  311.  
  312.    *d_arr[] =
  313.    {
  314.       (struct direc *) 0, da_, db_, dc_, dd_, de_, df_, di_, dl_, 
  315.       dm_, dn_, do_, dp_, dr_, ds_, dt_, du_, dv_, dw_, dz_
  316.    };
  317.  
  318. /* Indexes for the Instruction_ARRay, note that    i_arr[0] = 0   */
  319. static int       
  320.    dstarters[] =
  321.    {     
  322.    /* 0 1 2 3 4 5 6 7 8 9 :         ? @                        */
  323.       0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
  324.    /* A B C D E F G H I J K L M  N  O  P Q  R  S  T  U  V  W X Y  Z */
  325.       1,2,3,4,5,6,0,0,7,0,0,8,9,10,11,12,0,13,14,15,16,17,18,0,0,19,
  326.    /*         _ */   
  327.       0,0,0,0,0 
  328.    };
  329.  
  330. directive_suckin()
  331. {
  332.    register char  *p = yytext,
  333.                   c_ = c,
  334.                   *p_table = (char *) is_what;
  335.    
  336.    ENTER("directive_suckin");
  337.    if( (c_ = uinput()) == '=')       /* is .= ?? */
  338.       fdreturn( T_DOTEQ);
  339.    *p++ = '.';
  340. #if VERSION && FINPUT_IO && QINPUT_IO && QDIRECT
  341.    {
  342.       register byte huge   *pt  = bp->p;
  343.       registe byte         *tab = _uptable;
  344.       register lword       rem  = bp->remain;
  345.  
  346.       do
  347.          *p++ = c_;
  348.       while( tis_ident( c_ = quinput( rem, pt, tab)));
  349.       if( bp)
  350.       {
  351.          bp->remain = rem;
  352.          bp->p      = pt;
  353.       }
  354.     }
  355. #else
  356.    do
  357.       *p++ = c_;                             /* convert to upper & save */
  358.    while( tis_ident(c_ = uinput()));
  359. #endif 
  360.    c  = c_;
  361.    *p = 0;
  362.    p  = yytext + 1;     
  363.    {
  364.       register struct direc   *q;
  365.       
  366.       if( q = d_arr[ dstarters[ *p - '0']])      /* get directive start */
  367.          do
  368.             if( ! strcmp( q->string, p))
  369.             {
  370.                if( q->state)
  371.                   state = q->state;
  372.                dreturn( q->token);
  373.             }
  374.          while( (++q)->string);
  375.    }
  376.    lsyntax("unknown directive");
  377. }
  378.  
  379.  
  380. struct opt
  381. {
  382.    char   *name;
  383.    int    token;
  384. };
  385.  
  386. static struct  opt
  387.    options[] =
  388.    {
  389.       { "NO",         T_NO    },
  390.       { "OBJ",        T_OBJ   },
  391.       { "LIST",       T_LIST  },
  392.       { "MLIST",      T_MLIST },
  393.       { "CLIST",      T_CLIST },
  394.       { "EJECT",      T_EJECT },
  395.       { "ERR",        T_ERR   },
  396.       { "NUM",        T_NUM   },
  397.       { "XREF",       T_XREF  },
  398.       { "",           0       }
  399.    };
  400.  
  401.  
  402. option_suckin()
  403. {
  404.    register struct opt huge   *q = options;
  405.    register char              *p = yytext;
  406.  
  407.    while( is_letter(c))
  408.    {
  409.       *p++ = c;
  410.       c    = uinput();
  411.    }
  412.    *p = 0;
  413.  
  414.    while( q->token)
  415.    {
  416.       if( ! strcmp( yytext, q->name))
  417.          return( q->token);
  418.       q++;
  419.    }
  420.    lsyntax("unknown option");
  421. }
  422.  
  423. /* (*)
  424.    Turbo-C very cleverly (no irony this time) compiles the "-'0'" as a
  425.    negative offset for the LEA. Therefore this isn't wasting any time 
  426.    at least on the ST. Else a 256 word array would be better
  427. */
  428.