/// <summary> /// Creates instance of NativeObjectsAnalyzerHelper /// </summary> /// <param name="method">Method name</param> /// <param name="objectName">Class name</param> public NativeObjectsAnalyzerHelper(NativeMethod method, QualifiedName objectName) { Method = method; ObjectName = objectName; }
/// <summary> /// Creates a new instance of NativeObjectAnalyzer. It parses the xml with information about the objects. /// </summary> /// <param name="outSet">FlowOutputSet</param> private NativeObjectAnalyzer(FlowOutputSet outSet) { using (MemoryStream stream = new MemoryStream(Encoding.UTF8.GetBytes(Resources.php_classes))) using (XmlReader reader = XmlReader.Create(stream)) { nativeObjects = new Dictionary <QualifiedName, ClassDecl>(); NativeObjectsAnalyzerHelper.mutableNativeObjects = new Dictionary <QualifiedName, ClassDeclBuilder>(); Visibility methodVisibility = Visibility.PUBLIC; ClassDeclBuilder currentClass = null; NativeMethod currentMethod = null; while (reader.Read()) { switch (reader.NodeType) { case XmlNodeType.Element: switch (reader.Name) { case "class": case "interface": currentClass = new ClassDeclBuilder(); var classFinal = reader.GetAttribute("isFinal"); if (classFinal == "true") { currentClass.IsFinal = true; } else { currentClass.IsFinal = false; } currentClass.QualifiedName = new QualifiedName(new Name(reader.GetAttribute("name"))); if (reader.GetAttribute("baseClass") != null) { currentClass.BaseClasses = new List <QualifiedName>(); currentClass.BaseClasses.Add(new QualifiedName(new Name(reader.GetAttribute("baseClass")))); } else { currentClass.BaseClasses = null; } NativeObjectsAnalyzerHelper.mutableNativeObjects[currentClass.QualifiedName] = currentClass; if (reader.Name == "class") { currentClass.IsInterface = false; } else { currentClass.IsInterface = true; } break; case "field": string fieldName = reader.GetAttribute("name"); string fieldVisibility = reader.GetAttribute("visibility"); string fieldIsStatic = reader.GetAttribute("isStatic"); string fieldIsConst = reader.GetAttribute("isConst"); string fieldType = reader.GetAttribute("type"); fieldTypes.Add(fieldType); Visibility visibility; switch (fieldVisibility) { case "public": visibility = Visibility.PUBLIC; break; case "protectd": visibility = Visibility.PROTECTED; break; case "private": visibility = Visibility.PRIVATE; break; default: visibility = Visibility.PUBLIC; break; } if (fieldIsConst == "false") { Value initValue = outSet.UndefinedValue; string stringValue = reader.GetAttribute("value"); int intValue; bool boolValue; long longValue; double doubleValue; if (stringValue == null) { initValue = outSet.UndefinedValue; } else if (bool.TryParse(stringValue, out boolValue)) { initValue = outSet.CreateBool(boolValue); } else if (int.TryParse(stringValue, out intValue)) { initValue = outSet.CreateInt(intValue); } else if (long.TryParse(stringValue, out longValue)) { initValue = outSet.CreateLong(longValue); } else if (double.TryParse(stringValue, out doubleValue)) { initValue = outSet.CreateDouble(doubleValue); } else { initValue = outSet.CreateString(stringValue); } currentClass.Fields[new FieldIdentifier(currentClass.QualifiedName, new VariableName(fieldName))] = new FieldInfo(new VariableName(fieldName), currentClass.QualifiedName, fieldType, visibility, new MemoryEntry(initValue), bool.Parse(fieldIsStatic)); } else { string value = reader.GetAttribute("value"); //resolve constant VariableName constantName = new VariableName(fieldName); var constIdentifier = new FieldIdentifier(currentClass.QualifiedName, constantName); switch (fieldType) { case "int": case "integer": try { currentClass.Constants[constIdentifier] = new ConstantInfo(constantName, currentClass.QualifiedName, visibility, new MemoryEntry(outSet.CreateInt(int.Parse(value)))); } catch (Exception) { currentClass.Constants[constIdentifier] = new ConstantInfo(constantName, currentClass.QualifiedName, visibility, new MemoryEntry(outSet.CreateDouble(double.Parse(value)))); } break; case "string": currentClass.Constants[constIdentifier] = new ConstantInfo(constantName, currentClass.QualifiedName, visibility, new MemoryEntry(outSet.CreateString(value))); break; case "boolean": currentClass.Constants[constIdentifier] = new ConstantInfo(constantName, currentClass.QualifiedName, visibility, new MemoryEntry(outSet.CreateBool(bool.Parse(value)))); break; case "float": currentClass.Constants[constIdentifier] = new ConstantInfo(constantName, currentClass.QualifiedName, visibility, new MemoryEntry(outSet.CreateDouble(double.Parse(value)))); break; case "NULL": currentClass.Constants[constIdentifier] = new ConstantInfo(constantName, currentClass.QualifiedName, visibility, new MemoryEntry(outSet.UndefinedValue)); break; default: break; } } break; case "method": currentMethod = new NativeMethod(new QualifiedName(new Name(reader.GetAttribute("name"))), reader.GetAttribute("returnType"), new List <NativeFunctionArgument>()); currentMethod.IsFinal = bool.Parse(reader.GetAttribute("final")); currentMethod.IsStatic = bool.Parse(reader.GetAttribute("static")); returnTypes.Add(reader.GetAttribute("returnType")); if (currentMethod.Name == new QualifiedName(new Name("getLastErrors"))) { } methodVisibility = Visibility.PUBLIC; if (reader.GetAttribute("visibility") == "private") { methodVisibility = Visibility.PRIVATE; } else if (reader.GetAttribute("visibility") == "protected") { methodVisibility = Visibility.PROTECTED; } else { methodVisibility = Visibility.PUBLIC; } if (reader.IsEmptyElement) { NativeAnalyzerMethod analyzer; if (currentMethod.Name.Name.Equals(new Name("__construct"))) { analyzer = new NativeObjectsAnalyzerHelper(currentMethod, currentClass.QualifiedName).Construct; } else { analyzer = new NativeObjectsAnalyzerHelper(currentMethod, currentClass.QualifiedName).Analyze; } MethodInfo methodInfo = new MethodInfo(currentMethod.Name.Name, currentClass.QualifiedName, methodVisibility, analyzer, currentMethod.ConvertArguments(), currentMethod.IsFinal, currentMethod.IsStatic, currentMethod.IsAbstract); currentClass.ModeledMethods[new MethodIdentifier(currentClass.QualifiedName, methodInfo.Name)] = methodInfo; } break; case "arg": currentMethod.Arguments.Add(new NativeFunctionArgument(reader.GetAttribute("type"), bool.Parse(reader.GetAttribute("optional")), bool.Parse(reader.GetAttribute("byReference")), bool.Parse(reader.GetAttribute("dots")))); methodTypes.Add(reader.GetAttribute("type")); break; } break; case XmlNodeType.Text: break; case XmlNodeType.XmlDeclaration: case XmlNodeType.ProcessingInstruction: break; case XmlNodeType.Comment: break; case XmlNodeType.EndElement: switch (reader.Name) { case "method": NativeAnalyzerMethod analyzer; if (currentMethod.Name.Name.Equals(new Name("__construct"))) { analyzer = new NativeObjectsAnalyzerHelper(currentMethod, currentClass.QualifiedName).Construct; } else { analyzer = new NativeObjectsAnalyzerHelper(currentMethod, currentClass.QualifiedName).Analyze; } MethodInfo methodInfo = new MethodInfo(currentMethod.Name.Name, currentClass.QualifiedName, methodVisibility, analyzer, currentMethod.ConvertArguments(), currentMethod.IsFinal, currentMethod.IsStatic, currentMethod.IsAbstract); currentClass.ModeledMethods[new MethodIdentifier(currentClass.QualifiedName, methodInfo.Name)] = methodInfo; break; } break; } } } /* * check if every ancestor exist */ foreach (var nativeObject in NativeObjectsAnalyzerHelper.mutableNativeObjects.Values) { if (nativeObject.QualifiedName != null) { if (!NativeObjectsAnalyzerHelper.mutableNativeObjects.ContainsKey(nativeObject.QualifiedName)) { throw new Exception(); } } } //generate result foreach (var nativeObject in NativeObjectsAnalyzerHelper.mutableNativeObjects.Values) { List <QualifiedName> newBaseClasses = new List <QualifiedName>(); if (nativeObject.BaseClasses != null) { QualifiedName baseClassName = nativeObject.BaseClasses.Last(); while (true) { newBaseClasses.Add(baseClassName); var baseClass = NativeObjectsAnalyzerHelper.mutableNativeObjects[baseClassName]; foreach (var constant in baseClass.Constants) { nativeObject.Constants[constant.Key] = constant.Value; } foreach (var field in baseClass.Fields) { nativeObject.Fields[field.Key] = field.Value; } foreach (var method in baseClass.ModeledMethods) { nativeObject.ModeledMethods[method.Key] = method.Value; } if (baseClass.BaseClasses != null && baseClass.BaseClasses.Count > 0) { baseClassName = baseClass.BaseClasses.Last(); } else { break; } } } newBaseClasses.Reverse(); nativeObject.BaseClasses = newBaseClasses; nativeObjects[nativeObject.QualifiedName] = nativeObject.Build(); } initReportingFunctions(); initCleaningFunctions(); }