home *** CD-ROM | disk | FTP | other *** search
/ APDL Public Domain 1 / APDL_PD1A.iso / program / assembler / as / src / c / code < prev    next >
Encoding:
Text File  |  1993-03-07  |  7.1 KB  |  259 lines

  1. /*
  2.  * code.c
  3.  * Copyright © 1992 Niklas Röjemo
  4.  */
  5.  
  6. #include <stdio.h>
  7. #include <stdlib.h>
  8. #include "code.h"
  9. #include "error.h"
  10. #include "eval.h"
  11. #include "area.h"
  12. #include "option.h"
  13. #include "input.h"
  14. #include "AofFile.h"
  15. #include "storage.h"
  16.  
  17. static Code Program[CODE_SIZECODE];
  18. static int FirstFreeIns;
  19. static Value  Stack[CODE_SIZESTACK];
  20.  
  21. static LateInfo LateHeap[CODE_SIZELATE];
  22. static int      LateHeapPtr;
  23.  
  24. LateInfo *codeNewLateInfo(Symbol *symbol)
  25. {
  26.   if(LateHeapPtr<CODE_SIZELATE) {
  27.     LateHeap[LateHeapPtr].next = 0;
  28.     LateHeap[LateHeapPtr].factor = 1;
  29.     LateHeap[LateHeapPtr].symbol = symbol;
  30.   } else
  31.     error(ErrorSerious,FALSE,"Internal codeNewLateInfo: Out of memory.");
  32.   return &LateHeap[LateHeapPtr++];
  33.  
  34. void codeInit(void)
  35. {
  36.   FirstFreeIns = LateHeapPtr =0;
  37. }
  38.  
  39. void codeOperator(Operator op)
  40. {
  41.   if(FirstFreeIns<CODE_SIZECODE) {
  42.     Program[FirstFreeIns].Tag = CodeOperator;
  43.     Program[FirstFreeIns++].CodeOperator.op = op;
  44.   } else
  45.     error(ErrorSerious,FALSE,"Internal codeOp: Overflow.");
  46. }
  47.  
  48. void codeSymbol(Symbol *symbol)
  49. {
  50.   if(FirstFreeIns<CODE_SIZECODE) {
  51.     if(symbol->type & SYMBOL_DEFINED &&
  52.        !(symbol->type & SYMBOL_AREA)) {
  53.       switch(symbol->value.Tag) {
  54.         case ValueInt:    case ValueFloat:
  55.         case ValueString: case ValueBool:
  56.           Program[FirstFreeIns  ].Tag = CodeValue;
  57.           Program[FirstFreeIns++].CodeValue.value = symbol->value;
  58.           break;
  59.         case ValueCode:
  60.           if(FirstFreeIns+symbol->value.ValueCode.len<=CODE_SIZECODE) {
  61.             int i;
  62.             for(i=0; i<symbol->value.ValueCode.len; i++)
  63.               Program[FirstFreeIns++] = symbol->value.ValueCode.c[i];
  64.           } else
  65.             error(ErrorSerious,FALSE,"Internal codeSymbol: Overflow.(n)");
  66.           break;
  67.         default:
  68.           error(ErrorSerious,FALSE,"Internal codeSymbol:Illegal symbol value.");
  69.       }
  70.     } else {
  71.       Program[FirstFreeIns  ].Tag = CodeSymbol;
  72.       Program[FirstFreeIns++].CodeSymbol.symbol = symbol;
  73.     }
  74.   } else
  75.     error(ErrorSerious,FALSE,"Internal codeSymbol: Overflow.(1)");
  76. }
  77.  
  78. void codePosition(Symbol *area)
  79. {
  80.   if(area) {
  81.     codeSymbol(area);
  82.     codeInt(area->value.ValueInt.i);
  83.     codeOperator(Op_add);
  84.   } else
  85.     error(ErrorError,FALSE,"'.' but no area is defined.");
  86. }
  87.  
  88. void codeStorage(void)
  89. {
  90.   Value value = storageValue();  /* Must be ValueInt */
  91.   codeInt(value.ValueInt.i);
  92. }
  93.  
  94. void codeString(int len, char *str)
  95. {
  96.   if(FirstFreeIns<CODE_SIZECODE) {
  97.     Program[FirstFreeIns].Tag = CodeValue;
  98.     Program[FirstFreeIns].CodeValue.value.Tag = ValueString;
  99.     Program[FirstFreeIns].CodeValue.value.ValueString.len = len;
  100.     Program[FirstFreeIns++].CodeValue.value.ValueString.s = str;
  101.   } else
  102.     error(ErrorSerious,FALSE,"Internal codeString: Overflow.");
  103. }
  104.  
  105. void codeInt(int value)
  106. {
  107.   if(FirstFreeIns<CODE_SIZECODE) {
  108.     Program[FirstFreeIns].Tag = CodeValue;
  109.     Program[FirstFreeIns].CodeValue.value.Tag = ValueInt;
  110.     Program[FirstFreeIns++].CodeValue.value.ValueInt.i = value;
  111.   } else
  112.     error(ErrorSerious,FALSE,"Internal codeInt: Overflow.");
  113. }
  114.  
  115. void codeFloat(FLOAT value)
  116. {
  117.   if(FirstFreeIns<CODE_SIZECODE) {
  118.     Program[FirstFreeIns].Tag = CodeValue;
  119.     Program[FirstFreeIns].CodeValue.value.Tag = ValueFloat;
  120.     Program[FirstFreeIns++].CodeValue.value.ValueFloat.f = value;
  121.   } else
  122.     error(ErrorSerious,FALSE,"Internal codeFloat: Overflow.");
  123. }
  124.  
  125.  
  126. int Sp;  /* Used by codeEvalLow and codeEvalLowest */
  127.  
  128. static BOOL codeEvalLowest(int size, Code *program)  /* True if codeEvalLowest succeded */
  129. {
  130.   int Pp;
  131.   for(Pp=0; Pp<size; Pp++) {
  132.     switch(program[Pp].Tag) {
  133.     case CodeOperator:
  134.       if(program[Pp].CodeOperator.op == Op_neg ||
  135.          program[Pp].CodeOperator.op == Op_not ||
  136.          program[Pp].CodeOperator.op == Op_lnot) {
  137.         if(!evalUnop(program[Pp].CodeOperator.op,&Stack[Sp]))
  138.           return FALSE;
  139.       } else {
  140.         if(!evalBinop(program[Pp].CodeOperator.op,&Stack[Sp-1],&Stack[Sp]))
  141.           return FALSE;
  142.         Sp--;
  143.       }
  144.       break;
  145.     case CodeValue:
  146.       Stack[++Sp] = program[Pp].CodeValue.value;
  147.       break;
  148.     case CodeSymbol:
  149.       if (program[Pp].CodeSymbol.symbol->type & SYMBOL_DEFINED &&
  150.           !(program[Pp].CodeSymbol.symbol->type & SYMBOL_AREA)) { /* This can happen in the relocation phase. */
  151.         switch(program[Pp].CodeSymbol.symbol->value.Tag) {
  152.           case ValueInt:    case ValueFloat:
  153.           case ValueString: case ValueBool:
  154.             Stack[++Sp] = program[Pp].CodeSymbol.symbol->value;
  155.             break;
  156.           case ValueCode:
  157.             if(!codeEvalLowest(program[Pp].CodeSymbol.symbol->value.ValueCode.len,
  158.                                program[Pp].CodeSymbol.symbol->value.ValueCode.c))
  159.               return FALSE;
  160.             break;
  161.           default:
  162.             error(ErrorSerious,FALSE,
  163.                    "Internal codeEvalLow: Illegal value for symbol %s.",
  164.                    program[Pp].CodeSymbol.symbol->str);
  165.         }
  166.       } else {  /* Undefined or area or late register */
  167.         Stack[++Sp].Tag = ValueLateLabel;
  168.         Stack[  Sp].ValueLate.i = 0;
  169.         Stack[  Sp].ValueLate.late = codeNewLateInfo(program[Pp].CodeSymbol.symbol);
  170.       }
  171.       break;
  172.     default:
  173.       error(ErrorSerious,FALSE,"Internal codeEvalLow: Illegal expression.");
  174.     }
  175.   }
  176.   return TRUE;
  177. }
  178.  
  179. Value codeEval(ValueTag legal)
  180. {
  181.   return codeEvalLow(legal,FirstFreeIns,Program);
  182. }
  183.  
  184. Value codeEvalLow(ValueTag legal, int size, Code *program)
  185. {
  186.   Value Result;
  187.   Sp = -1;
  188.   if(!codeEvalLowest(size,program)) {
  189.     Result.Tag = ValueCode;
  190.     Result.ValueCode.len = size;
  191.     Result.ValueCode.c = program;
  192.   } else if(Sp == 0) {
  193.     Result = Stack[0];
  194.   } else {
  195.     Result.Tag = ValueIllegal;
  196.   }
  197.   if(!(Result.Tag & legal)) {
  198.     extern int pedantic,autocast;
  199.     if(autocast && legal & ValueFloat && Result.Tag == ValueInt) {
  200.       FLOAT f = Result.ValueInt.i;
  201.       if(pedantic) 
  202.         error(ErrorInfo,TRUE,"Changing integer %d to float %1.1f.",Result.ValueInt.i,f);
  203.       Result.Tag = ValueFloat;
  204.       Result.ValueFloat.f = f;
  205.     } else {
  206.       Result.Tag = ValueIllegal;
  207.     }
  208.   }
  209.   return Result;    
  210. }
  211.  
  212. Code *codeCopy(int len, Code *code)
  213. {
  214.   int i;
  215.   Code *new = malloc(len*sizeof(Code));
  216.   if(new) {
  217.     for(i=0; i<len; i++) {
  218.       switch(new[i].Tag = code[i].Tag) {
  219.         case CodeOperator:
  220.           new[i].CodeOperator.op = code[i].CodeOperator.op;
  221.           break;
  222.         case CodeValue:
  223.           new[i].CodeValue.value = valueCopy(code[i].CodeValue.value);
  224.           break;
  225.         case CodeSymbol:
  226.           new[i].CodeSymbol.symbol = code[i].CodeSymbol.symbol;
  227.           break;
  228.       }
  229.     }
  230.   } else
  231.     error(ErrorSerious,FALSE,"Internal codeCopy: Out of memory.");
  232.   return new;
  233. }
  234.  
  235. int codeEqual(int len, Code *a,Code *b)
  236. {
  237.   int i;
  238.   for(i=0; i<len; i++) {
  239.     if(a[i].Tag != b[i].Tag)
  240.       return FALSE;
  241.     switch(a[i].Tag) {
  242.       case CodeOperator:
  243.         if(a[i].CodeOperator.op != b[i].CodeOperator.op)
  244.           return FALSE;
  245.         break;
  246.       case CodeValue:
  247.         if(!valueEqual(&a[i].CodeValue.value,&b[i].CodeValue.value))
  248.           return FALSE;
  249.         break;
  250.       case CodeSymbol:
  251.         if(a[i].CodeSymbol.symbol != b[i].CodeSymbol.symbol)
  252.           return FALSE;
  253.         break;
  254.     }
  255.   }
  256.   return TRUE;
  257. }
  258.