Esempio n. 1
0
        public MetadataFile Clone(AinFile ainFile)
        {
            var clone = new MetadataFile(ainFile);

            foreach (var pair in this.EnumerationTypes)
            {
                clone.EnumerationTypes.Add(pair.Key, pair.Value.Clone());
            }

            foreach (var pair in this.Metadata)
            {
                var variable = pair.Key.Canonicalize(ainFile);
                if (variable != null)
                {
                    var metaData = pair.Value.Clone();
                    if (metaData.FuncTypeIndex != -1)
                    {
                        var funcType = this.ainFile.GetFuncType(metaData.FuncTypeIndex);
                        if (funcType != null)
                        {
                            var otherFuncType    = ainFile.GetFuncType(funcType.Name);
                            int newFuncTypeIndex = otherFuncType.Index;
                            metaData.FuncTypeIndex = newFuncTypeIndex;
                        }
                    }
                    clone.Metadata.Add(variable, metaData);
                }
            }
            return(clone);
        }
        /// <summary>
        /// Checks if a variable object is a reference to a variable registered in the AinFile, and returns the original variable from the AinFile if it exists, otherwise returns null.
        /// </summary>
        /// <param name="variable">The variable to find</param>
        /// <param name="ainFile">The AinFile to find the variable in.</param>
        /// <returns>returns the original variable from the AinFile if it exists, otherwise returns null</returns>
        public static IVariable Canonicalize(this IVariable variable, AinFile ainFile)
        {
            int index       = variable.Index;
            int parentIndex = -1;

            if (variable == null || ainFile == null)
            {
                return(null);
            }
            var root = variable.Root;

            var parent = variable.Parent;

            if (parent != null)
            {
                parentIndex = parent.Index;
            }

            if (root == ainFile || root == null)
            {
                if (parent is Function)
                {
                    if (parent.Name.StartsWith("system."))
                    {
                        return(AinFile.GetSystemCallParameter(parentIndex, index));
                    }
                    return(ainFile.GetFunctionParameter(parentIndex, index));
                }
                if (parent is Struct)
                {
                    return(ainFile.GetStructMember(parentIndex, index));
                }
                if (variable is Global)
                {
                    return(ainFile.GetGlobal(index));
                }
                if (parent is FunctionType)
                {
                    return(ainFile.GetFuncTypeParameter(parentIndex, index));
                }
                if (parent is HllFunction)
                {
                    if (parent.Parent != null)
                    {
                        return(ainFile.GetLibraryFunctionParameter(parent.Parent.Index, parentIndex, index));
                    }
                    else
                    {
                        return(null);
                    }
                }
                if (variable is Function)
                {
                    if (variable.Name.StartsWith("system."))
                    {
                        return(AinFile.GetSystemCall(index));
                    }
                    return(ainFile.GetFunction(index));
                }
                if (variable is Struct)
                {
                    return(ainFile.GetStruct(index));
                }
                if (variable is HllFunction)
                {
                    return(ainFile.GetLibraryFunction(parentIndex, index));
                }
                if (variable is FunctionType)
                {
                    return(ainFile.GetFuncType(index));
                }
            }
            else
            {
                if (parent is Function)
                {
                    if (parent.Name.StartsWith("system."))
                    {
                        return(AinFile.GetSystemCallParameter(parentIndex, index));
                    }
                    return(ainFile.GetFunctionParameter(parent.Name, variable.Name));
                }
                if (variable is Global)
                {
                    return(ainFile.GetGlobal(variable.Name));
                }
                if (parent is Struct)
                {
                    return(ainFile.GetStructMember(parent.Name, variable.Name));
                }
                if (parent is FunctionType)
                {
                    return(ainFile.GetFuncTypeParameter(parent.Name, variable.Index));
                }
                if (parent is HllFunction)
                {
                    if (parent.Parent != null)
                    {
                        return(ainFile.GetLibraryFunctionParameter(parent.Parent.Name, parent.Name, index));
                    }
                    else
                    {
                        return(null);
                    }
                }
                if (variable is Function)
                {
                    if (variable.Name.StartsWith("system."))
                    {
                        return(AinFile.GetSystemCall(index));
                    }
                    return(ainFile.GetFunction(variable.Name));
                }
                if (variable is Struct)
                {
                    return(ainFile.GetStruct(variable.Name));
                }
                if (variable is HllFunction)
                {
                    return(ainFile.GetLibraryFunction(parent.Name, variable.Name));
                }
                if (variable is FunctionType)
                {
                    return(ainFile.GetFuncType(variable.Name));
                }
            }
            return(null);
        }
        private void ReadMetadata()
        {
            //quit if we're not attached to anything
            if (variable == null || ainFile == null)
            {
                return;
            }

            //display variable name declaration
            this.VariableTextBox.ReadOnly        = false;
            this.VariableTextBox.Text            = variable.ToString();
            this.VariableTextBox.SelectionStart  = 0;
            this.VariableTextBox.SelectionLength = 0;
            this.VariableTextBox.ScrollToCaret();
            this.VariableTextBox.ReadOnly = true;

            //get metadata or use a blank variable
            Metadata metaData;

            if (ainFile.MetadataFile.Metadata.ContainsKey(variable))
            {
                metaData = ainFile.MetadataFile.Metadata[variable];
            }
            else
            {
                metaData = new Metadata();
            }

            //set alternative name - either the default for what is specified
            string defaultAlternativeName = ainFile.AlternativeNames.GetOrNull(variable.Name);

            AlternativeNameTextBox.Text = metaData.ReplacementName ?? defaultAlternativeName;

            //is this a function parameter?  Allow a default value
            if (variable.Parent is Function && variable.Index < variable.Parent.ParameterCount)
            {
                this.currentDefaultValue = metaData.DefaultValue;
            }
            else if (variable is Global)
            {
                //if it's a global, display the initial value specified in the AIN file, and don't allow editing
                this.currentDefaultValue = ainFile.GlobalInitialValues.Where(i => i.GlobalVariable == variable).FirstOrDefault();
            }
            else
            {
                //DefaultValueTextBox.ReadOnly = true;
                findDefaultValueButton.Enabled = false;
            }
            if (this.currentDefaultValue != null)
            {
                string defaultValueString = this.currentDefaultValue.GetValue();
                DefaultValueTextBox.Text = defaultValueString;
                if (variable is Global)
                {
                    //DefaultValueTextBox.ReadOnly = true;
                    findDefaultValueButton.Enabled = false;
                }
            }

            //get enumeration type
            EnumerationType enumerationType = null;

            if (variable.DataType.GetTypeOfArrayElement().IsInteger())
            {
                enumerationType = metaData.EnumerationType;
                if (enumerationType != null)
                {
                    EnumerationTypeComboBox.Text = enumerationType.Name;
                }
            }
            else if (variable.DataType.IsFunction())
            {
                EditEnumerationTypeButton.Visible   = false;
                spreadEnumerationTypeButton.Visible = false;
                if (variable.DataType.IsFuncType())
                {
                    int structType = variable.StructType;
                    if (metaData.FuncTypeIndex != -1)
                    {
                        structType = metaData.FuncTypeIndex;
                    }
                    var functionType = ainFile.GetFuncType(structType);
                    if (functionType != null)
                    {
                        EnumerationTypeComboBox.Text = functionType.ToString();
                    }
                }
                else  //it's a delegate
                {
                    int structType = variable.StructType;
                    if (metaData.FuncTypeIndex != -1)
                    {
                        structType = metaData.FuncTypeIndex;
                    }
                    var delegateType = ainFile.Delegates.GetOrNull(structType);
                    if (delegateType != null)
                    {
                        EnumerationTypeComboBox.Text = delegateType.ToString();
                    }
                }
            }
            else
            {
                EnumerationTypeComboBox.Enabled     = false;
                EditEnumerationTypeButton.Enabled   = false;
                spreadEnumerationTypeButton.Enabled = false;
            }

            //get description
            DescriptionTextBox.Text = metaData.Description ?? "";
        }
        private bool FindFunctionTypeForVariable(IVariable variable, Expression code, bool MakeNewStuffUp)
        {
            bool variableIsFunction = variable as Function != null;
            bool variableIsFuncType = variable.DataType.IsFuncType();
            bool variableIsDelegate = variable.DataType.IsDelegate();

            foreach (var e in code.GetChildExpressions())
            {
                Expression otherExpression = null;
                IVariable  expVariable     = null;
                if (e.ExpressionType == Instruction.CALLFUNC2 && variableIsFuncType)
                {
                    bool isVoid = e.IsVoidContext();
                    if (!isVoid)
                    {
                        otherExpression = e.GetOtherSideOfBinaryExpression();
                    }
                    IVariable otherExpressionVariable = null;
                    if (otherExpression != null)
                    {
                        otherExpressionVariable = otherExpression.Variable;
                    }

                    DataType otherExpressionDataType   = DataType.Void;
                    int      otherExpressionStructType = -1;
                    if (otherExpressionVariable != null)
                    {
                        otherExpressionDataType   = otherExpressionVariable.DataType;
                        otherExpressionStructType = otherExpressionVariable.StructType;
                    }
                    else
                    {
                        if (isVoid)
                        {
                            otherExpressionDataType = DataType.Void;
                        }
                        else
                        {
                            otherExpressionDataType = DataType.AnyNonVoidType;
                        }
                    }

                    var argExpressions    = (e.Arg3 ?? Expression.Empty).FlattenContainerExpression(Instruction.Comma).ToArray();
                    var variables         = GetVariablesFromExpressions(argExpressions);
                    var matchingFuncTypes = ainFile.MatchingFunctionTypes(otherExpressionDataType, otherExpressionStructType, variables, variables.Length).Distinct().ToArray();

                    var firstMatchingFuncType = matchingFuncTypes.FirstOrDefault();
                    if (firstMatchingFuncType != null)
                    {
                        if (MakeNewStuffUp || matchingFuncTypes.Skip(1).FirstOrDefault() == null)
                        {
                            variable.StructType = firstMatchingFuncType.Index;
                        }
                    }
                }
                if (variableIsFunction && e.ExpressionType == Instruction.RETURN)
                {
                    otherExpression = e.Arg1;
                    expVariable     = variable;
                }
                else
                {
                    expVariable = e.Variable;
                    if (variable == expVariable)
                    {
                        otherExpression = e.GetOtherSideOfBinaryExpression();
                    }
                }

                if (otherExpression != null)
                {
                    Function otherFunction = null;
                    if (otherExpression.ExpressionType == Instruction.PUSH)
                    {
                        otherFunction = ainFile.GetFunction(otherExpression.Value);
                    }
                    else if (otherExpression.ExpressionType == Instruction.S_PUSH)
                    {
                        otherFunction = ainFile.GetFunction(ainFile.GetString(otherExpression.Value));
                    }
                    else
                    {
                        var otherVariable = otherExpression.Variable;
                        if (otherVariable != null && !variableIsDelegate && otherVariable.DataType.IsFuncType() && otherVariable.StructType != -1)
                        {
                            variable.StructType = otherVariable.StructType;
                            return(true);
                        }
                        if (otherVariable != null && variableIsDelegate && otherVariable.DataType.IsDelegate() && otherVariable.StructType != -1)
                        {
                            variable.StructType = otherVariable.StructType;
                            return(true);
                        }
                    }
                    if (otherFunction != null)
                    {
                        FunctionType matchingFuncType = null;
                        if (!variableIsDelegate)
                        {
                            if (!MakeNewStuffUp)
                            {
                                matchingFuncType = ainFile.GetFuncTypeUnique(otherFunction);
                            }
                            else
                            {
                                matchingFuncType = ainFile.GetFuncType(otherFunction);
                            }
                            if (matchingFuncType != null)
                            {
                                variable.StructType = matchingFuncType.Index;
                                return(true);
                            }
                        }
                        else
                        {
                            if (!MakeNewStuffUp)
                            {
                                matchingFuncType = ainFile.GetDelegateUnique(otherFunction);
                            }
                            else
                            {
                                matchingFuncType = ainFile.GetDelegateType(otherFunction);
                            }
                            if (matchingFuncType != null)
                            {
                                variable.StructType = matchingFuncType.Index;
                                return(true);
                            }
                        }
                    }
                }
                else
                {
                    var functionParameter = e.GetFunctionCallParameter();
                    if (functionParameter != null)
                    {
                        if (functionParameter != null && !variableIsDelegate && functionParameter.DataType.IsFuncType() && functionParameter.StructType != -1)
                        {
                            variable.StructType = functionParameter.StructType;
                            return(true);
                        }
                        if (functionParameter != null && variableIsDelegate && functionParameter.DataType.IsDelegate() && functionParameter.StructType != -1)
                        {
                            variable.StructType = functionParameter.StructType;
                            return(true);
                        }
                    }
                    else if (variable.DataType.IsArray())
                    {
                        var parent = e.Parent;
                        if (parent != null && (parent.ExpressionType == Instruction.A_PUSHBACK || parent.ExpressionType == Instruction.A_INSERT))
                        {
                            var       arg2 = parent.Arg2;
                            IVariable var2 = null;
                            if (arg2 != null)
                            {
                                var2 = arg2.Variable;
                            }
                            if (var2 != null)
                            {
                                if (!variableIsDelegate && var2.DataType.IsFuncType() && var2.StructType != -1)
                                {
                                    variable.StructType = var2.StructType;
                                    return(true);
                                }
                                if (variableIsDelegate && var2.DataType.IsDelegate() && var2.StructType != -1)
                                {
                                    variable.StructType = var2.StructType;
                                    return(true);
                                }
                            }
                        }
                    }
                    else if (e.ExpressionType == Instruction.CALLFUNC2)
                    {
                    }
                }
            }
            return(false);
        }