/// <summary> /// Constructs a single intrinsic definition. /// </summary> /// <param name="count">Indicates how many arguments the function takes</param> /// <param name="types">Bitmask representing the valid argument types</param> /// <param name="requiredType">Type to which the argument must be cast</param> /// <param name="returnType">Symbol representing the return type</param> public IntrDefinition(ArgCount count, int types, SymType requiredType, SymType returnType) { Count = count; Types = types; RequiredType = requiredType; ReturnType = returnType; }
public void PushBack(SymType previoustype, String previouscontent) { pushbackbuffer_type.Push(nexttype); pushbackbuffer_content.Push(nextcontent); nexttype = previoustype; nextcontent = previouscontent; }
// Lexical scanner private void Scan() { int k; while (Cradle.Look == Cradle.CR) { Cradle.Fin(); } if (Cradle.IsAlpha(Cradle.Look)) { GetName(); } else if (Cradle.IsDigit(Cradle.Look)) { GetNum(); } else if (IsOp(Cradle.Look)) { GetOp(); } else { Value = Cradle.Look.ToString(); Token = SymType.Operator; Cradle.GetChar(); } Cradle.SkipWhite(); }
public override UInt32 GetGlobalRVA(String symbolName, SymType symType) { DiaSymbol sy = df.GlobalSymbol.FindSymbol(symbolName); if (sy == null && symType == SymType.GlobalFunction) { // Try looking for the symbol in public symbols, // as assembly routines do not have normal // global symbol table entries. We don't know // how many parameters to use, so just guess // at a few sizes. for (int i = 0; i <= 16; i += 4) { // Non-fastcall. sy = GetValidPublicSymbolEntry("_" + symbolName + "@" + i); if (sy != null) { break; } // Fastcall. sy = GetValidPublicSymbolEntry("@" + symbolName + "@" + i); if (sy != null) { break; } } } return(GetSymbolRva(sy, symbolName, "Symbol")); }
/// <summary> /// Emit this code to load a null value to the stack. /// </summary> /// <param name="cg">A CodeGenerator object</param> /// <param name="returnType">The type required by the caller</param> /// <returns>The symbol type of the value generated</returns> public override SymType Generate(CodeGenerator cg, SymType returnType) { if (cg == null) { throw new ArgumentNullException("cg"); } cg.Emitter.LoadNull(); return Type; }
public bool Accept(SymType symtype) { if ((_sym != null) && _sym.Type == symtype) { getsym(); return(true); } return(false); }
/// <summary> /// Adds a parameter to the definition of this external function with the given /// name, type and linkage. Parameters must be added in the exact order in which /// they are defined in the external function. /// </summary> /// <param name="name">The parameter name.</param> /// <param name="type">A SymType representing the parameter type.</param> /// <param name="linkage">A SymLinkage representing the parameter linkage.</param> /// <param name="include">Specifies whether this parameter should be included in ParametersNode.</param> public void Add(string name, SymType type, SymLinkage linkage, bool include = true) { FunctionDefinition definition = new FunctionDefinition(); definition.Name = name; definition.Symbol = new Symbol(name, new SymFullType(type), SymClass.VAR, null, 0); definition.Symbol.Linkage = linkage; definition.Include = include; _definitions.Add(definition); _paramList.Add(name); }
public Symbol(string ident, SymType typ, bool verbose) : this() { _ident = ident; _type = typ; if (verbose) { Console.WriteLine("New symbol: '" + ident + "' (" + _type + ")"); } }
internal void StartFromBegin() { nexttype = SymType.EOF; nextcontent = ""; linenumber = 0; columnnumber = 0; line = lines[0]; pushbackbuffer_type = new Stack <SymType>(); pushbackbuffer_content = new Stack <string>(); }
public bool Expect(SymType symtype) { Symbol current = _sym; if (Accept(symtype)) { return(true); } throw new UnexpectedTokenException(_lineNumber, current.Spelling); }
public void ThrowExpectedSymbol(SymType type, String content) { if (content != null) { ThrowParseError("Expected " + content); } else { ThrowParseError("Expected " + type); } }
public Scanner(Stream source) { reader = new StreamReader(source, System.Text.Encoding.UTF8); nexttype = SymType.EOF; nextcontent = ""; line = reader.ReadLine(); linenumber = 0; columnnumber = 0; pushbackbuffer_type = new Stack <SymType>(); pushbackbuffer_content = new Stack <String>(); }
internal void ThrowExpectedSymbol(SymType type, string content) { if (content != null) { ThrowParseError("Expected " + content); } else { //ThrowParseError("Expected " + type, 1, 1); ThrowParseError("Expected " + type); } }
public void AddSymbol(string sym, string val, SymType type, int reqParams = 0, List <SymType> paramTypes = null) { Symbol smb = new Symbol(val, type, reqParams); if (Symbols.ContainsKey(sym)) { Symbols[sym] = smb; } else { Symbols.Add(sym, smb); } }
// Get a number private void GetNum() { Value = ""; if (!Cradle.IsDigit(Cradle.Look)) { Cradle.Expected("Integer"); } while (Cradle.IsDigit(Cradle.Look)) { Value += Cradle.Look; Cradle.GetChar(); } Token = SymType.Number; }
// Get an operator private void GetOp() { Value = ""; if (!IsOp(Cradle.Look)) { Cradle.Expected("Operator"); } while (IsOp(Cradle.Look)) { Value += Cradle.Look; Cradle.GetChar(); } Token = SymType.Operator; }
/// <summary> /// Emit the code to create an array of variable arguments and evaluate /// and store each argument in the array. On exit, the address of the /// array is left on the top of the stack. /// </summary> /// <param name="cg">A CodeGenerator object</param> /// <param name="returnType">The type required by the caller</param> /// <returns>The symbol type of the value generated</returns> public override SymType Generate(CodeGenerator cg, SymType returnType) { if (cg == null) { throw new ArgumentNullException("cg"); } int argCount = Nodes.Count; cg.Emitter.CreateSimpleArray(argCount, typeof(Object)); for (int c = 0; c < argCount; ++c) { cg.Emitter.Dup(); cg.Emitter.LoadInteger(c); cg.Emitter.StoreElementReference(cg.GenerateExpression(SymType.NONE, Nodes[c])); } return SymType.VARARG; }
public static SymBase GetInstance(string symType) { SymType aTyp = (SymType)Enum.Parse(typeof(SymType), symType); switch (aTyp) { case SymType.TripleDES: return(new TripleDES()); case SymType.RijndaelManaged: return(new RijndaelManaged()); case SymType.RC2: return(new RC2()); case SymType.DES: return(new DES()); } return(null); }
public Symbol(string val, SymType type, int reqParams = 0, List <SymType> paramTypes = null) { Value = val; Type = type; if (reqParams == 0) { InfParams = true; } else { ReqParams = reqParams; } if (paramTypes == null) { ParamTypes = new List <SymType>(); } else { ParamTypes = paramTypes; } }
public SymPointerType SymTypeToSymPointerType(SymType symType) { switch (symType) { case SymAliasType symAliasType: return(SymTypeToSymPointerType(symAliasType.Alias)); case SymArrayType symArrayType: return(new SymPointerType(symArrayType)); case SymBoolType symBoolType: return(SymBoolPtr); case SymCharType symCharType: return(SymCharPtr); case SymConformatArrayType symConformatArrayType: return(new SymPointerType(symConformatArrayType)); case SymFloatType symFloatType: return(SymFloatPtr); case SymIntegerType symIntegerType: return(SymIntPtr); case SymNilConst symNilConst: return(SymNilPtr); case SymPointerType symPointerType: return(new SymPointerType(symPointerType)); case SymRecordType symRecordType: return(new SymPointerType(symRecordType)); case SymStringType symStringType: return(SymStringPtr); } return(null); }
// Get an identifier private void GetName() { int k; Value = ""; if (!Cradle.IsAlpha(Cradle.Look)) { Cradle.Expected("Name"); } while (Cradle.IsAlNum(Cradle.Look)) { Value += char.ToUpper(Cradle.Look); Cradle.GetChar(); } k = Lookup(Value); if (k == -1) { Token = SymType.Ident; } else { Token = (SymType)k; } }
public abstract UInt32 GetGlobalRVA(String symbolName, SymType symType);
/// <summary> /// Returns whether the given symbol type is valid as an argument for /// this intrinsic. Note that this does not handle type coercion. /// </summary> /// <param name="type">The symbol type to check</param> /// <returns>True if the type is valid, false otherwise</returns> public bool IsValidArgType(SymType type) { switch (type) { case SymType.CHAR: return (Types & S) != 0; case SymType.FIXEDCHAR: return (Types & S) != 0; case SymType.INTEGER: return (Types & I) != 0; case SymType.FLOAT: return (Types & R) != 0; case SymType.DOUBLE: return (Types & D) != 0; case SymType.BOOLEAN: return (Types & L) != 0; case SymType.COMPLEX: return (Types & C) != 0; } return false; }
/// <summary> /// Emit the code to subtract values of the specified type. /// </summary> /// <param name="type">Type of the arguments</param> public void Sub(SymType type) { switch (type) { case SymType.COMPLEX: Emit0(OpCodes.Call, typeof(Complex).GetMethod("op_Subtraction", new [] { typeof(Complex), typeof(Complex) } )); break; default: Emit0(OpCodes.Sub); break; } }
public void AddType(string identifier, SymType type) { _stack.Peek().AddType(identifier, type); }
// Verify that the type on the right hand side of an assignment can be // assigned to the left hand side. bool ValidateAssignmentTypes(SymType toType, SymType fromType) { bool valid = false; switch (toType) { case SymType.CHAR: case SymType.FIXEDCHAR: valid = Symbol.IsCharType(fromType); break; case SymType.DOUBLE: case SymType.INTEGER: case SymType.FLOAT: case SymType.COMPLEX: if (toType == SymType.COMPLEX) { valid = (fromType == SymType.COMPLEX); } else { valid = Symbol.IsNumberType(fromType); } break; case SymType.BOOLEAN: valid = Symbol.IsLogicalType(fromType); break; } return valid; }
public override UInt32 GetGlobalRVA(String symbolName, SymType symType) { DiaSymbol sy = df.GlobalSymbol.FindSymbol(symbolName); if (sy == null && symType == SymType.GlobalFunction) { // Try looking for the symbol in public symbols, // as assembly routines do not have normal // global symbol table entries. We don't know // how many parameters to use, so just guess // at a few sizes. for (int i = 0; i <= 16; i += 4) { // Non-fastcall. sy = GetValidPublicSymbolEntry("_" + symbolName + "@" + i); if (sy != null) { break; } // Fastcall. sy = GetValidPublicSymbolEntry("@" + symbolName + "@" + i); if (sy != null) { break; } } } return GetSymbolRva(sy, symbolName, "Symbol"); }
/// <summary> /// Emit the code to load a value of the specified type onto the stack. /// </summary> /// <param name="type">The type wanted</param> /// <param name="value">A variant value</param> public void LoadValue(SymType type, Variant value) { if (value == null) { throw new ArgumentNullException("value"); } switch (type) { case SymType.INTEGER: LoadInteger(value.IntValue); break; case SymType.FLOAT: LoadFloat(value.RealValue); break; case SymType.DOUBLE: LoadDouble(value.DoubleValue); break; default: Debug.Assert(false, string.Format("LoadValue: Unsupported type {0}", type)); break; } }
/// <summary> /// Emit the code to divide values of the specified type. /// </summary> /// <param name="type">Type of the arguments</param> public void Div(SymType type) { switch (type) { case SymType.COMPLEX: Emit0(OpCodes.Call, typeof(Complex).GetMethod("op_Division", new [] { typeof(Complex), typeof(Complex) } )); break; default: Emit0(OpCodes.Div); break; } }
/// <summary> /// Create a local variable of the given type and return the index /// of the variable in the local index table. /// </summary> /// <param name="type">SymType of the local</param> /// <returns>The integer index of the new local</returns> public LocalDescriptor CreateLocal(SymType type) { return CreateLocal(Symbol.SymTypeToSystemType(type)); }
/// <summary> /// Checks whether the actual type of the last operation matches the type /// needed and, if not, emits the appropriate conversion to the required type. /// If typeNeeded is NONE then no conversion is performed.. /// </summary> /// <returns>The type that the last operation was converted to</returns> /// <param name="actualType">The actual type of the operation</param> /// <param name="typeNeeded">The type needed.</param> public SymType ConvertType(SymType actualType, SymType typeNeeded) { if (actualType != typeNeeded) { switch (typeNeeded) { case SymType.NONE: typeNeeded = actualType; break; case SymType.LABEL: typeNeeded = actualType; break; case SymType.BOOLEAN: Emit0(OpCodes.Conv_I1); break; case SymType.DOUBLE: Emit0(OpCodes.Conv_R8); break; case SymType.FLOAT: Emit0(OpCodes.Conv_R4); break; case SymType.INTEGER: Emit0(OpCodes.Conv_I4); break; case SymType.CHAR: if (actualType == SymType.FIXEDCHAR) { Emit0(OpCodes.Call, typeof(JComLib.FixedString).GetMethod("ToString", Type.EmptyTypes )); } break; case SymType.FIXEDCHAR: { Type fromType = Symbol.SymTypeToSystemType(actualType); Emit0(OpCodes.Call, typeof(JComLib.FixedString).GetMethod("op_Implicit", new [] { fromType } )); break; } case SymType.COMPLEX: { Type fromType = Symbol.SymTypeToSystemType(actualType); Emit0(OpCodes.Call, typeof(Complex).GetMethod("op_Implicit", new [] { fromType } )); break; } } } return typeNeeded; }
/// <summary> /// Emit the instructions to call a method whose address has been /// pushed to the top of the stack. /// </summary> /// <param name="type">Return type of the method</param> /// <param name="paramTypes">Parameter types</param> public void CallIndirect(SymType type, Type[] paramTypes) { Emit0(OpCodes.Calli, CallingConventions.Standard, Symbol.SymTypeToSystemType(type), paramTypes); }
/// <summary> /// Obtains a new temporary store of the given symbol type. /// </summary> /// <param name="type">The symbol type requested.</param> /// <returns>A LocalDescriptor object for the type</returns> public LocalDescriptor New(SymType type) { return New(Symbol.SymTypeToSystemType(type)); }
/// <summary> /// Emit this code to load the value to the stack. /// </summary> /// <param name="cg">A CodeGenerator object</param> /// <param name="returnType">The type required by the caller</param> /// <returns>The symbol type of the value generated</returns> public override SymType Generate(CodeGenerator cg, SymType returnType) { if (cg == null) { throw new ArgumentNullException("cg"); } cg.GenerateLoad(Value); return Value.Type; }
public override UInt32 GetGlobalRVA(String symbolName, SymType symType) { return(GetRVA(symbolName)); }
/// <summary> /// Emit the code to multiply values of the specified type. /// </summary> /// <param name="type">Type of the arguments</param> public void Mul(SymType type) { switch (type) { case SymType.COMPLEX: Emit0(OpCodes.Call, typeof(Complex).GetMethod("op_Multiply", new [] { typeof(Complex), typeof(Complex) } )); break; default: Emit0(OpCodes.Mul); break; } }
public Symbol() { _type = SymType.Undefined; }
/// <summary> /// Emit the code to negate a value of the specified type. /// </summary> /// <param name="type">Type of the arguments</param> public void Neg(SymType type) { switch (type) { case SymType.COMPLEX: Emit0(OpCodes.Call, typeof(Complex).GetMethod("op_UnaryNegation", new [] { typeof(Complex) } )); break; default: Emit0(OpCodes.Neg); break; } }
public void GetSym() { if (pushbackbuffer_type.Count > 0) { nexttype = pushbackbuffer_type.Pop(); nextcontent = pushbackbuffer_content.Pop(); return; } for (; ;) { if (line == null) { nexttype = SymType.EOF; nextcontent = ""; return; } if (columnnumber >= line.Length) { nexttype = SymType.EOL; nextcontent = ""; line = reader.ReadLine(); linenumber++; columnnumber = 0; return; } if (columnnumber == 0 && line.StartsWith("'PRAGMA ")) { nexttype = SymType.PRAGMA; nextcontent = line.Substring(8).Trim(); line = reader.ReadLine(); linenumber++; columnnumber = 0; return; } switch (line[columnnumber]) { case '\'': // detect begin of comment columnnumber = line.Length; break; case ' ': case '\t': // white spaces will be skipped in normal program context columnnumber++; break; case '0': case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': { // found a number (with optional decimal point, but no '-') int startpos = columnnumber; columnnumber++; while (columnnumber < line.Length && ((line[columnnumber] >= '0' && line[columnnumber] <= '9') || line[columnnumber] == '.')) { columnnumber++; } nexttype = SymType.NUMBER; nextcontent = line.Substring(startpos, columnnumber - startpos); return; } case '"': { // found a string (maybe with missing trailing ") int startpos = columnnumber; columnnumber++; for (; ;) { if (columnnumber >= line.Length) { throw new Exception("Nonterminated string at: " + (linenumber + 1) + ":" + (columnnumber + 1)); } if (line[columnnumber] == '"') { columnnumber++; // an additonal " continues the string if (columnnumber < line.Length && line[columnnumber] == '"') { columnnumber++; } else { break; } } columnnumber++; } nexttype = SymType.STRING; nextcontent = line.Substring(startpos + 1, columnnumber - startpos - 2); // deliver string without " return; } default: { char c = line[columnnumber]; if ((c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || (c == '_')) // found an identifier { int startpos = columnnumber; columnnumber++; while (columnnumber < line.Length) { c = line[columnnumber]; if ((c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || (c == '_') || (c >= '0' && c <= '9')) { columnnumber++; continue; } break; } String w = line.Substring(startpos, columnnumber - startpos).ToUpperInvariant(); nexttype = SymType.ID; nextcontent = w; if (w.Equals("AND") || w.Equals("ELSE") || w.Equals("ELSEIF") || w.Equals("ENDFOR") || w.Equals("ENDIF") || w.Equals("ENDSUB") || w.Equals("ENDWHILE") || w.Equals("FOR") || w.Equals("GOTO") || w.Equals("IF") || w.Equals("OR") || w.Equals("STEP") || w.Equals("SUB") || w.Equals("THEN") || w.Equals("TO") || w.Equals("WHILE") ) { nexttype = SymType.KEYWORD; } return; } else { // other stuff is probably a special character nexttype = SymType.SPECIAL; nextcontent = line.Substring(columnnumber, 1); columnnumber++; // detect two-digit special operators also if (nextcontent.Equals("<") && columnnumber < line.Length && line[columnnumber] == '=') { nextcontent = "<="; columnnumber++; } else if (nextcontent.Equals(">") && columnnumber < line.Length && line[columnnumber] == '=') { nextcontent = ">="; columnnumber++; } else if (nextcontent.Equals("<") && columnnumber < line.Length && line[columnnumber] == '>') { nextcontent = "<>"; columnnumber++; } return; } } } } }
/// <summary> /// Emit the code to store the value on the top of the stack. /// </summary> /// <param name="type">Type to store</param> public void StoreElement(SymType type) { Emit0(OpCodes.Stelem, Symbol.SymTypeToSystemType(type)); }
public void AddType(SymType type) { _stack.Peek().AddType(type); }
public void AddParameter(string modifier, string identifier, SymType type) { _stack.Peek().AddVariable(identifier, new SymParameter(type, modifier)); }
public void AddConstant(bool local, string identifier, SymType type) { _stack.Peek().AddVariable(local, identifier, type); }
public abstract UInt32 GetGlobalRVA(String symbolName, SymType symType);
public void AddAlias(string aliasIdentifier, SymType typeToAias) { _stack.Peek().AddAlias(aliasIdentifier, new SymAliasType(aliasIdentifier, typeToAias)); }
/// <summary> /// Emit the code to store a value indirectly. The stack must contain /// two values: the value to store and then the indirection offset. /// </summary> /// <param name="type">Type of the value to be stored</param> public void StoreIndirect(SymType type) { switch (type) { case SymType.DOUBLE: Emit0(OpCodes.Stind_R8); break; case SymType.FLOAT: Emit0(OpCodes.Stind_R4); break; case SymType.INTEGER: Emit0(OpCodes.Stind_I4); break; case SymType.BOOLEAN: Emit0(OpCodes.Stind_I4); break; default: Debug.Assert(false, string.Format("StoreIndirect: Unsupported type {0}", type)); break; } }
/// <summary> /// Emit this code to load the value to the stack. /// </summary> /// <param name="cg">A CodeGenerator object</param> /// <param name="returnType">The type required by the caller</param> /// <returns>The symbol type of the value generated</returns> public override SymType Generate(CodeGenerator cg, SymType returnType) { if (cg == null) { throw new ArgumentNullException("cg"); } switch (ID) { case ParseID.ADD: return GenerateAdd(cg); case ParseID.EQV: return GenerateEq(cg); case ParseID.NEQV: return GenerateNe(cg); case ParseID.XOR: return GenerateXor(cg); case ParseID.OR: return GenerateOr(cg); case ParseID.AND: return GenerateAnd(cg); case ParseID.GT: return GenerateGt(cg); case ParseID.GE: return GenerateGe(cg); case ParseID.LE: return GenerateLe(cg); case ParseID.EQ: return GenerateEq(cg); case ParseID.NE: return GenerateNe(cg); case ParseID.LT: return GenerateLt(cg); case ParseID.SUB: return GenerateSub(cg); case ParseID.MULT: return GenerateMult(cg); case ParseID.DIVIDE: return GenerateDivide(cg); case ParseID.CONCAT: return GenerateConcat(cg); case ParseID.EXP: return GenerateExp(cg); } Debug.Assert(false, "Unsupported parse ID for BinaryOpParseNode"); return Value.Type; }
/// <summary> /// Generate code for an expression tree. /// </summary> /// <param name="typeNeeded">The type to which the expression should be converted if it /// does not evaluate to that type natively.</param> /// <param name="rootNode">The ParseNode of the root of the expression tree.</param> /// <returns>The type of the generated expression</returns> public SymType GenerateExpression(SymType typeNeeded, ParseNode rootNode) { if (rootNode == null) { throw new ArgumentNullException("rootNode"); } SymType thisType = rootNode.Generate(this, SymType.GENERIC); return _em.ConvertType(thisType, typeNeeded); }
/// <summary> /// Emit this code to load the value to the stack. /// </summary> /// <param name="cg">A CodeGenerator object</param> /// <param name="returnType">The type required by the caller</param> /// <returns>The symbol type of the value generated</returns> public override SymType Generate(CodeGenerator cg, SymType returnType) { if (cg == null) { throw new ArgumentNullException("cg"); } if (ID == ParseID.LABEL) { if (Symbol.IsFixedStatic) { cg.Emitter.LoadString(Symbol.Value.StringValue); return Type; } return cg.LoadLocal(Symbol); } Debug.Assert(false, "Unsupported parse ID for SymbolParseNode"); return Value.Type; }
/// <summary> /// Emit this code to load the value to the stack. /// </summary> /// <param name="cg">A CodeGenerator object</param> /// <param name="returnType">The type required by the caller</param> /// <returns>The symbol type of the value generated</returns> public override SymType Generate(CodeGenerator cg, SymType returnType) { if (cg == null) { throw new ArgumentNullException("cg"); } switch (ID) { case ParseID.MINUS: return GenerateMinus(cg); case ParseID.NOT: return GenerateNot(cg); } Debug.Assert(false, "Unsupported parse ID for UnaryOpParseNode"); return Value.Type; }
/// <summary> /// Implements the base code generator for the node to invoke a /// function implementation with a symbol type. /// </summary> /// <param name="cg">The code generator object</param> /// <param name="returnType">The expected type of the return value</param> /// <returns>The computed type</returns> public virtual SymType Generate(CodeGenerator cg, SymType returnType) { throw new InvalidOperationException("ParseNode does not implement Generate"); }
public void getsym() { if (_symP >= _program.Length) { _sym = null; return; } string c = " "; bool parseNextLine = true; bool changedLine = false; while (parseNextLine) { parseNextLine = false; while (_newLine) { changedLine = true; if (_symP + 6 >= _program.Length) { _sym = null; return; } _lineNumber = _program.Substring(_symP, 6); _symP += 6; _newLine = false; c = _program.Substring(_symP, 1); if (c == "*") { //This line is a comment while (c != "\n") { _symP++; c = _program.Substring(_symP, 1); } _newLine = true; _symP++; } else if (c == "-") { //This line is a continuation of the previous line //TODO: This should never be handled here. //See further down getsym in literal/identifier parsing code. } } c = _program.Substring(_symP, 1); if (!_inQuotes || _sym == null || changedLine /*|| _sym.Type != SymType.Text*/) { while (c == " " || c == "\t") { //Console.WriteLine("skipping space"); _symP++; c = _program.Substring(_symP, 1); } } int start = _symP; int len = 0; string sub = null; _sym = null; int backup = _symP; string subN = ""; SymType typ; while (c != "\n") { len++; _symP++; c = _program.Substring(_symP, 1); sub = _program.Substring(start, _symP - start); //Get the next char and check if it's whitespace if (sub.Length > 0) { subN = sub.Substring(0, 1); } else { subN = ""; } if (ident.IndexOf(subN) == -1) { typ = _symbols.Find(sub); if (typ != SymType.Undefined && (_quoteChar == null || _quoteChar == subN)) { _sym = new Symbol(sub, typ, _verbose); break; } } if (ident.IndexOf(c) == -1) { if ((len <= _symbols.Longest)) { typ = _symbols.Find(sub); if (typ != SymType.Undefined && (_quoteChar == null || _quoteChar == subN)) { _sym = new Symbol(sub, typ, _verbose); break; } if (ident.IndexOf(c) == -1 && ident.IndexOf(subN) == -1) { break; } } else { if (ident.IndexOf(c) == -1) { break; } } } } if (sub == null) { parseNextLine = true; c = _program.Substring(_symP, 1); while (c != "\n") { _symP++; c = _program.Substring(_symP, 1); } _newLine = true; _symP++; } else { if (sub == "") { //I think this is just a blank line and should be ignored. } if (_sym == null) { sub = ""; //Console.WriteLine("rolling back to: "+_program.Substring(backup)); _symP = backup; start = _symP; len = 0; bool endQuoteDetected = false; _symP--; //Parsing a literal or identifier do { _symP++; c = _program.Substring(_symP, 1); if (_inQuotes && c == "\n") { //Newline in string //TODO: This next line possibly makes the string include the quote character //Console.WriteLine("** Adding Sub part: " + _program.Substring(start, _symP - start)); sub += _program.Substring(start, _symP - start); _symP++; changedLine = true; _lineNumber = _program.Substring(_symP, 6); _symP += 6; _newLine = false; c = _program.Substring(_symP, 1); if (c == "-") { //This line is a continuation of the previous line while (_symP < _program.Length && c != _quoteChar) { _symP++; c = _program.Substring(_symP, 1); } if (c == _quoteChar) { start = _symP + 1; c = ""; } else { //TODO: Replace this with the proper COBOL error message throw new Compiler.Exceptions.UnexpectedTokenException(_lineNumber, "'" + c + "'. Quote character expected."); } } else { //TODO: Error? //This should be a line continued form the previous one and therefore have a dash here Console.WriteLine("ERROR: Unexpected newline in string at line " + _lineNumber); } } if (_inQuotes && c == _quoteChar) { endQuoteDetected = true; } } while (ident.IndexOf(c) != -1 || (_inQuotes && _quoteChar != null && !endQuoteDetected)); sub += _program.Substring(start, _symP - start); if (sub == "") { sub = c; _symP++; } if (sub.Substring(sub.Length - 1, 1) == ".") { sub = sub.Substring(0, sub.Length - 1); } SymType t = SymType.Text; int tempInt; if (Int32.TryParse(sub, out tempInt)) { t = SymType.Number; } _sym = new Symbol(sub, t, _verbose); } string dsp = " \t"; int p = _symP; while (dsp.IndexOf(c) != -1) { p++; c = _program.Substring(p, 1); } if (c == "\n") { _newLine = true; _symP = p + 1; } } } if (!_inQuotes) { if (_sym.Type == SymType.SingleQuote) { _quoteChar = "'"; _inQuotes = true; } if (_sym.Type == SymType.DoubleQuote) { _quoteChar = "\""; _inQuotes = true; } } else { if (_sym.Spelling == _quoteChar) { _inQuotes = false; _quoteChar = null; } } }
/// <summary> /// Implements the base code generator for the node to invoke a /// function implementation with a symbol type. /// </summary> /// <param name="cg">The code generator object</param> /// <param name="returnType">The expected type of the return value</param> /// <returns>The computed type</returns> public override SymType Generate(CodeGenerator cg, SymType returnType) { if (cg == null) { throw new ArgumentNullException("cg"); } cg.Emitter.LoadLocal(_local); return Symbol.SystemTypeToSymbolType(_local.Type); }
public SymConstant(string ident, SymType varSymType) : base(ident, varSymType) { }
// Generate the code to write an expression to a substring represented // by an identifier which should be fixed string type. void GenerateSaveSubstring(CodeGenerator cg, SymType charType) { Type baseType = Symbol.SymTypeToSystemType(charType); // Optimise for constant start/end values if (Identifier.SubstringStart.IsConstant) { int startIndex = Identifier.SubstringStart.Value.IntValue - 1; cg.Emitter.LoadInteger(startIndex); } else { cg.GenerateExpression(SymType.INTEGER, Identifier.SubstringStart); cg.Emitter.LoadInteger(1); cg.Emitter.Sub(SymType.INTEGER); } if (Identifier.SubstringEnd == null) { cg.Emitter.LoadInteger(Identifier.Symbol.FullType.Width); } else { if (Identifier.SubstringEnd.IsConstant) { int endIndex = Identifier.SubstringEnd.Value.IntValue - 1; cg.Emitter.LoadInteger(endIndex); } else { cg.GenerateExpression(SymType.INTEGER, Identifier.SubstringEnd); cg.Emitter.LoadInteger(1); cg.Emitter.Sub(SymType.INTEGER); } } cg.Emitter.Call(cg.GetMethodForType(typeof(JComLib.FixedString), "Set", new [] { baseType, typeof(int), typeof(int) })); }
protected SymVar(string ident, SymType varSymType = null) : base(ident) { VarSymType = varSymType; }
public CSymbol(SymbolsGen yyp) : base(yyp.m_lexer) { m_parser = yyp; m_symtype = SymType.unknown; m_prec = null; m_prod = null; m_refSymbol = null; m_first = new SymbolSet(yyp); m_follow = new SymbolSet(yyp); }
public SymParameter(SymType varSymType, string modifier = "") : base("Parameter", varSymType) { Modifier = modifier; }
/// <summary> /// Emit the code to store the value on the top of the stack /// as a reference type. /// </summary> /// <param name="type">Type to store</param> public void StoreElementReference(SymType type) { switch (type) { case SymType.INTEGER: case SymType.BOOLEAN: case SymType.FLOAT: case SymType.DOUBLE: case SymType.COMPLEX: Type sysType = Symbol.SymTypeToSystemType(type); Emit0(OpCodes.Box, sysType); break; } Emit0(OpCodes.Stelem_Ref); }
/// Handle a declaration statement of the specified type. ParseNode KDeclaration(SymType type) { SymFullType fullType = new SymFullType(type); SimpleToken token; if (Symbol.IsCharType(type)) { fullType.Width = ParseTypeWidth(0); } // Could be a function declaration preceded by type? if (_ls.PeekKeyword() == TokenID.KFUNCTION) { _ls.GetToken(); return KSubFunc(SymClass.FUNCTION, null, fullType); } do { Symbol sym = ParseIdentifierDeclaration(fullType); if (sym != null) { if (sym.Defined) { _messages.Error(MessageCode.IDENTIFIERREDEFINITION, String.Format("Identifier {0} already declared", sym.Name)); } if (sym.IsParameter) { if (!sym.IsArray && !sym.IsMethod && sym.IsValueType) { sym.Linkage = SymLinkage.BYREF; } else { sym.Linkage = SymLinkage.BYVAL; } } sym.Defined = true; } token = _ls.GetToken(); } while (token.ID == TokenID.COMMA); _ls.BackToken(); return null; }