public static void SetFilename(string filename) { _filename = filename; if (_filename == null || _filename == "") { _filename = "ICode.pxi"; } _filename = _filename.Split('.')[0]; _filename += ".iCode"; foreach (Symbol s in SymbolTable.GetSymbolsInScope("g")) { if (s.symid[0] == 'H') { if (s.symid.Length == 1) { OutputGlobal(s.symid, CHAR_TYPE, " "); } else { OutputGlobal(s.symid, CHAR_TYPE, s.symid.Substring(1, (s.symid.Length - 1))); } } else if (s.symid[0] == 'N' || s.symid[0] == 'B') { OutputGlobal(s.symid, INT_TYPE, s.value); } } FRAME("MAIN", "NULL"); CALL("MAIN"); JMP("END");//after globals are declared, jump to main }
public static void Start(ref List <string> iCode, string filename) { int labelOffset = 0; string operand1 = ""; string operand2 = ""; string operand3 = ""; string instruction; string[] line; string[] comments; string[] data = new string[2]; data[0] = "returnType:int"; data[1] = "accessMod:public"; string[] dataChar = new string[2]; dataChar[0] = "returnType:char"; dataChar[1] = "accessMod:public"; SymbolTable.Add(new Symbol("g", TRUE, "1", "ilit", data)); SymbolTable.Add(new Symbol("g", FALSE, "0", "ilit", data)); SymbolTable.Add(new Symbol("g", "N4", "4", "ilit", data)); SymbolTable.Add(new Symbol("g", "N-1", "-1", "ilit", data)); SymbolTable.Add(new Symbol("g", "H!", "!", "c**t", dataChar)); SymbolTable.Add(new Symbol("g", "FREE", "0", "ilit", data)); filename = filename.Split('.')[0] + ".asm"; sw = new StreamWriter(filename, false); List <Symbol> globalVars = SymbolTable.GetSymbolsInScope("g"); Symbol var; pc = 0; for (int i = 0; i < globalVars.Count; ++i)//print all global variables at top of assembly file { var = globalVars[i]; if (var.symid[0] == 'H') { if (var.symid.Length == 1) { sw.WriteLine(var.symid + " .BYT "); } else { sw.WriteLine(var.symid + " .BYT " + var.symid.Substring(1, (var.symid.Length - 1))); } ++pc; } else if (var.symid[0] == 'N' || var.symid[0] == 'B' || var.symid == "null") { sw.WriteLine(var.symid + " .INT " + var.value); pc += 4; } } sw.WriteLine(FREE + " .INT 0");//address of available heap pc += 4; sw.WriteLine(";------------------------END OF DATA SEGMENT-----------------------"); LDR(registers[(int)Register.True], TRUE); LDR(registers[(int)Register.False], FALSE); LDA(registers[(int)Register.OP1], END); //load address of final instruction in code segment ADI(registers[(int)Register.OP1], (3 * INSTRUCT_SIZE).ToString()); //get address of first free heap location STR(registers[(int)Register.OP1], FREE); //update free heap location MOV(registers[(int)Register.OP1], registers[(int)Register.FP]); ADI(registers[(int)Register.OP1], (-1 * VAR_SIZE).ToString()); STR(registers[(int)Register.FP], registers[(int)Register.OP1]);//set fp to pfp (bottom of stack) _iCode = iCode; foreach (string s in _iCode) { bufferedLine = ""; labelOffset = 0; operand1 = ""; operand2 = ""; operand3 = ""; comments = s.Split(';'); line = comments[0].Trim().Split(' '); comment = COMMENT_FORMAT + comments[0]; for (int i = 1; i < comments.Length; ++i) { comment += comments[i]; } if (!_instructions.Contains <string>(line[0])) { //label labelOffset = 1; instruction = line[1]; bufferedLine = line[0] + " "; } else { labelOffset = 0; instruction = line[0]; } if (line.Length > labelOffset + 1)//contains 1 or more operands { operand1 = line[labelOffset + 1]; } if (instruction == "FUNC") { operand2 = operand1; } else { if (line.Length > labelOffset + 2)//contains 2 or more operands { operand2 = line[labelOffset + 2]; } if (line.Length > labelOffset + 3)//contains 2 or more operands { operand3 = line[labelOffset + 3]; } } InstructionCall(instruction, operand1, operand2, operand3); } sw.WriteLine(OVERFLOW + " LDB R3 H!"); pc += 12; sw.WriteLine("TRP 3"); pc += 12; sw.WriteLine(UNDERFLOW + " LDB R3 H!"); pc += 12; sw.WriteLine("TRP 3"); pc += 12; sw.Write(END + " TRP 0"); sw.Flush(); sw.Close(); }