public void SetValue(Value value) { string[] small_vals = Address.Split('?'); //get parts of address Value parent = null; //it`s parent value for (int i = 0; i < small_vals.Length; i++) { bool end = false; string val = small_vals[i]; if (i == small_vals.Length - 1) { end = true; } if (val.StartsWith("@")) //example of syntax - plus : @a, @b ; { val = val.Remove(0, 1); if (parent != null) { if (parent.CheckType("Type")) { if (!end) { parent = ((wolType)parent.type).value.GetStaticField(val); } else { ((wolType)parent.type).value.static_fields[val] = value; } } else { if (!end) { parent = parent.GetField(val); } else { parent.type.fields[val] = value; } } } else { try { if (!end) { parent = VirtualMachine.mainstack.values[val]; } else { VirtualMachine.mainstack.values[val] = value; } } catch (KeyNotFoundException) { VirtualMachine.ThrowVMException($"Variable by name '{val}' not found in main stack", VirtualMachine.position, ExceptionType.NotFoundException); } } } else if (val.StartsWith("&")) //example of syntax - set : &this, <null:void> ; { val = val.Remove(0, 1); if (parent != null) { if (parent.CheckType("Type")) { if (!end) { parent = ((wolType)parent.type).value.GetStaticField(val); } else { ((wolType)parent.type).value.static_fields[val] = value; } } else { if (!end) { parent = parent.GetField(val); } else { parent.type.fields[val] = value; } } } else { if (!end) { parent = VirtualMachine.mainstack.values[val]; } else { VirtualMachine.mainstack.values[val] = value; } } } else if (val.StartsWith("#")) //example of syntax - set : &this, #sum ; { val = val.Remove(0, 1); //remove '#' if (parent != null) { if (parent.CheckType("Type")) { ((wolType)parent.type).value.static_fields[val] = value; } else { parent.type.methods[val] = ((wolFunc)value.type).value; //return not static method of ParentValue by name } } else { VirtualMachine.mainstack.functions[val] = ((wolFunc)value.type).value; } } else if (val.StartsWith("$")) //example of syntax - equals : $void, (typeof : <null:void>) ; { if (parent != null) { VirtualMachine.ThrowVMException("Class (Type) cannot have parent value", VirtualMachine.position, ExceptionType.ValueException); } if (!end) { parent = new Value(new wolType(val.Remove(0, 1))); } else { VirtualMachine.mainstack.classes[val.Remove(0, 1)] = ((wolType)value.type).value; } } else if (val.StartsWith("%")) //example of syntax - if : ( equals : $void, (typeof : <null:void>) ), %if_block1 ; { if (parent != null) { VirtualMachine.ThrowVMException("Block cannot have parent value", VirtualMachine.position, ExceptionType.ValueException); } val = val.Remove(0, 1); if (!end) { parent = VirtualMachine.FindBlock(val); } else { if (!VirtualMachine.mainstack.values[val].CheckType("Block")) { VirtualMachine.ThrowVMException($"Variable by name {val} not found", VirtualMachine.position, ExceptionType.NotFoundException); } else { VirtualMachine.mainstack.values[val] = value; } } } else { VirtualMachine.ThrowVMException("Invalid syntax of linked value", VirtualMachine.position, ExceptionType.BLDSyntaxException); } } }
public bool CheckType(string name) => name == type.strtype ? true : false; //thanks C# for one-string functions)) public static Value GetSmallValue(string val, Value parent = null) { //Console.WriteLine("Value is " + val); Value value = VoidValue; val = val.Trim(); if (val.StartsWith("<") && val.EndsWith(">")) //example of syntax - _loads : <wolSystem:string> ; { if (parent != null) { VirtualMachine.ThrowVMException("Default value cannot have parent value", VirtualMachine.position, ExceptionType.ValueException); } val = val.Remove(0, 1).Remove(val.Length - 2); //remove '<' and '>' string[] vals = val.Split(':'); if (vals.Length == 2) { string type_word = vals[1].Trim(), val_word = vals[0].Trim(); if (type_word == "double") { wolDouble type = new wolDouble(); type.ParseDouble(val_word); value = new Value(type); } else if (type_word == "int") { wolInt type = new wolInt(); type.ParseInt(val_word); value = new Value(type); } else if (type_word == "string") { wolString type = new wolString(); type.value = Regex.Unescape(vals[0]); value = new Value(type); } else if (type_word == "long") { wolLong type = new wolLong(); type.ParseLong(val_word); value = new Value(type); } else if (type_word == "bool") { wolBool type = new wolBool(); type.ParseBool(val_word); value = new Value(type); } else if (type_word == "void") { value = VoidValue; } else if (type_word == "short") { wolShort type = new wolShort(); type.ParseShort(val_word); value = new Value(type); } else if (type_word == "float") { wolFloat type = new wolFloat(); type.ParseFloat(val_word); value = new Value(type); } else if (type_word == "byte") { wolByte type = new wolByte(); type.ParseByte(val_word); value = new Value(type); } else if (type_word == "char") { wolChar type = new wolChar(); type.ParseChar(val_word); value = new Value(type); } else { value = new Value(VirtualMachine.GetWolClass(type_word)); foreach (string f in vals[0].Split(',')) { string[] fs = f.Split('='); try { value.type.fields[fs[0].Trim()] = GetValue(fs[1]); } catch (KeyNotFoundException) { VirtualMachine.ThrowVMException($"Field by name {fs[0]} not found", VirtualMachine.position, ExceptionType.NotFoundException); } } } return(value); } else { VirtualMachine.ThrowVMException("Value and his type not found in this string", VirtualMachine.position, ExceptionType.BLDSyntaxException); return(null); } } else if (val.StartsWith("@")) //example of syntax - plus : @a, @b ; { //Console.WriteLine(val); val = val.Remove(0, 1); //skip '@' if (parent != null) { if (parent.CheckType("Type")) { return(((wolType)parent.type).value.GetStaticField(val)); } else { return(parent.GetField(val)); } } else { try { value = VirtualMachine.mainstack.values[val]; } catch (KeyNotFoundException) { VirtualMachine.ThrowVMException($"Variable by name '{val}' not found in main stack", VirtualMachine.position, ExceptionType.NotFoundException); } return(value); } } else if (val.StartsWith("&")) //example of syntax - set : &@this, <null:void> ; { val = val.Remove(0, 1); //remove '&' if (parent != null) { VirtualMachine.ThrowVMException("Link cannot haven`t ParentValue. He can have only valid address", VirtualMachine.position, ExceptionType.ValueException); return(new Value(new wolLink())); } else { return(new Value(new wolLink(val))); } } else if (val.StartsWith("#")) //example of syntax - set : &@this, #sum ; { val = val.Remove(0, 1); //remove '#' if (parent != null) { if (parent.CheckType("Type")) { return(new Value(new wolFunc(((wolType)parent.type).value.GetStaticMethod(val)))); //one string or how make code unreadable } else { if (val == "set") { return(new Value(new wolFunc(parent.setter))); } else if (val == "get") { return(new Value(new wolFunc(parent.getter))); } else { return(new Value(new wolFunc(parent.GetMethod(val)))); //return not static method of ParentValue by name } } } else { return(VirtualMachine.FindFunc(val)); //one string) } } else if (val.StartsWith("$")) //example of syntax - equals : $void, (typeof : <null:void>) ; { if (parent != null) { VirtualMachine.ThrowVMException("Class (Type) cannot have parent value", VirtualMachine.position, ExceptionType.ValueException); } return(new Value(new wolType(val.Remove(0, 1)))); //let`s write in one string!!! } else if (val.StartsWith("%")) //example of syntax - if : ( equals : $void, (typeof : <null:void>) ), %if_block1 ; { if (parent != null) { VirtualMachine.ThrowVMException("Block cannot have parent value", VirtualMachine.position, ExceptionType.ValueException); } return(VirtualMachine.FindBlock(val.Remove(0, 1))); //one string again! } else if (val.StartsWith("(")) //example of syntax - return (typeof : @this ) ; { if (parent != null) { VirtualMachine.ThrowVMException("Expression cannot have parent value", VirtualMachine.position - val.Length, ExceptionType.ValueException); } StringBuilder buffer = new StringBuilder(); char current = val[1]; //skip '(' int pos = 1; //skip '(' byte priority = 0; while (true) //add body of expression { if (current == '(') { priority++; } else if (current == ')') { if (priority == 0) { break; } else { priority--; } } try { buffer.Append(current); current = val[++pos]; } catch (IndexOutOfRangeException) { VirtualMachine.ThrowVMException($"End of string expression ('{val}') not found", VirtualMachine.position - val.Length + pos, ExceptionType.BLDSyntaxException); } } return(Script.ParseExpression(buffer.ToString())); } else { VirtualMachine.ThrowVMException($"Value {val} cannot find", VirtualMachine.position - val.Length, ExceptionType.BLDSyntaxException); return(null); } }
/// <summary> /// Parsing script code with imported stack /// </summary> /// <param name="script_code">Code who will parsing to script</param> /// <param name="_stack">Stack who will import to script</param> public static Value Parse(string script_code, Dictionary <string, Value> args) { string[] string_expressions = script_code.Split(new char[1] { ';' }, StringSplitOptions.RemoveEmptyEntries); //split to lines for (int i = 0; i < string_expressions.Length; i++) { string string_expression = string_expressions[i].Trim(); if (string_expression == string.Empty) { if (i == string_expressions.Length - 1) { break; } else { continue; } } string[] tokens = string_expression.Split(new char[4] { ' ', '\t', '\n', '\r' }, StringSplitOptions.RemoveEmptyEntries); switch (tokens[0]) { case "push-local": args.Add(tokens[1], Value.GetValue(string.Join(' ', tokens.TakeLast(tokens.Length - 2)))); break; case "delete": if (tokens[1] == "local") { args.Remove(tokens[2]); } else if (tokens[1] == "class") { VirtualMachine.mainstack.classes.Remove(tokens[2]); } else if (tokens[1] == "func") { VirtualMachine.mainstack.functions.Remove(tokens[2]); } else { VirtualMachine.mainstack.values.Remove(tokens[1]); } break; case "while": while (((wolBool)Value.GetValue(string.Join(' ', tokens.TakeLast(tokens.Length - 2))).type).value) { ((wolBlock)VirtualMachine.FindBlock(tokens[1]).type).Run(); } break; case "return": return(Value.GetValue(tokens[1])); case "block": string body = ""; for (int j = ++i; j < string_expressions.Length; j++) { i = j; if (string_expressions[j].Trim() == "end") { break; } body += string_expressions[j] + ';'; } VirtualMachine.mainstack.values.Add(tokens[1], new Value(new wolBlock(body))); if (VirtualMachine.test) { Console.WriteLine("Body of " + tokens[1] + '\n' + body); } break; default: ParseExpression(string_expression, args); break; } } return(Value.VoidValue); }