示例#1
0
        public void BuildTypeMatchingTable(TypeDescriptionTable table, ClosureEntities closure, StringBuilder featureBuilder)
        {
            var sb = new StringBuilder();


            sb.AppendLine("System_Void buildTypesTable() {");
            if (TypesToCast.Count > 0)
            {
                AddAllTypes(sb, table, closure);
            }
            sb.AppendLine("}");
            sb.AppendLine(@"
bool IsInstanceOf(int typeSource, int typeImplementation); 
System_Void buildTypesTable();
std::map<int, std::vector<int> > GlobalMappingType;

bool IsInstanceOf(int typeSource, int typeImplementation) {
    auto typeVector = GlobalMappingType[typeSource];
	auto begin = typeVector.begin();
	auto end = typeVector.end();
	return std::find(begin, end, typeImplementation)!= end;

}
");
            featureBuilder.AppendLine(sb.ToString());
        }
        private static void WriteClosureBodies(List <MethodInterpreter> closure, StringBuilder sb,
                                               TypeDescriptionTable typeTable, CrRuntimeLibrary crRuntime)
        {
            sb.AppendLine("///--- PInvoke code --- ");
            foreach (var interpreter in closure)
            {
                if (interpreter.Kind != MethodKind.PlatformInvoke)
                {
                    continue;
                }
                sb.AppendLine(MethodInterpreterCodeWriter.WritePInvokeMethodCode(interpreter));
            }

            sb.AppendLine("///---Begin closure code --- ");
            foreach (var interpreter in closure)
            {
                if (interpreter.Kind != MethodKind.Default)
                {
                    continue;
                }

                if (interpreter.Method.IsAbstract)
                {
                    continue;
                }
                sb.AppendLine(MethodInterpreterCodeWriter.WriteMethodCode(interpreter, typeTable, crRuntime));
            }
            sb.AppendLine("///---End closure code --- ");
        }
示例#3
0
        private static void HandleNewObject(LocalOperation operation, StringBuilder bodySb,
                                            MidRepresentationVariables vars,
                                            TypeDescriptionTable typeTable, MethodInterpreter interpreter)
        {
            var value      = (Assignment)operation.Value;
            var rightValue = (NewConstructedObject)value.Right;
            var localValue = rightValue.Info;

            var declaringType = localValue.DeclaringType;
            var cppName       = declaringType.ToDeclaredVariableType(true, EscapingMode.Stack);
            var assignedData  = interpreter.AnalyzeProperties.GetVariableData(value.AssignedTo);
            var isStack       = assignedData == EscapingMode.Stack;

            if (isStack)
            {
                bodySb
                .AppendFormat("{1} {0};", value.AssignedTo.Name, cppName);
            }
            else
            {
                bodySb.AppendFormat("{0} = std::make_shared<{1}>();", value.AssignedTo.Name, cppName);
            }
            bodySb.AppendLine();
            typeTable.SetIdOfInstance(bodySb, value.AssignedTo, declaringType, isStack);
        }
示例#4
0
        public ProgramClosure(MethodInfo entryMethod, CrRuntimeLibrary crRuntime)
        {
            var optimizationsTable = BuildProgramWideOptimizationsTable();

            Runtime          = crRuntime;
            Runtime.Closure  = this;
            EntryInterpreter = entryMethod.Register();

            ResultingInFunctionOptimizationPass.Runtime = Runtime;
            ResultingGlobalOptimizationPass.Runtime     = Runtime;
            BuildMethodClosure();
            MetaLinkerOptimizer.ApplyOptimizations(MethodClosure.Values.ToList());
            if (optimizationsTable.Optimize(this))
            {
                MetaLinkerOptimizer.ApplyOptimizations(MethodClosure.Values.ToList());
            }

            //BuildMethodClosure();
            AddAlwaysUsedType(typeof(object));
            TypesClosureLinker.SortTypeClosure(UsedTypes, crRuntime);

            var typeTable = new TypeDescriptionTable(UsedTypes);

            _typeDictionary = typeTable.ExtractInformation();

            BuildVirtualMethodTable(typeTable, MethodClosure);
        }
示例#5
0
        private static void HandleAssign(StringBuilder sb, LocalOperation operation, MidRepresentationVariables vars,
                                         TypeDescriptionTable typeTable, MethodInterpreter interpreter)
        {
            var assignment = (Assignment)operation.Value;

            if (assignment.Right is NewConstructedObject)
            {
                HandleNewObject(operation, sb, vars, typeTable, interpreter);
                return;
            }
            var assignedTo    = assignment.AssignedTo;
            var localVariable = assignment.Right as LocalVariable;

            if (localVariable != null)
            {
                var leftVarType  = assignment.AssignedTo.ComputedType();
                var rightVarType = assignment.Right.ComputedType();
                if (leftVarType != rightVarType)
                {
                    if (rightVarType.ClrType.IsPointer)
                    {
                        sb.AppendFormat("{0} = *{1};", assignedTo, localVariable.Name);
                        return;
                    }
                }
                var assignedToData    = interpreter.AnalyzeProperties.GetVariableData(assignedTo);
                var localVariableData = interpreter.AnalyzeProperties.GetVariableData(localVariable);
                var rightVar          = localVariable;
                var description       = assignedTo.ComputedType();
                if (description.ClrTypeCode != TypeCode.Object ||
                    assignedToData == localVariableData)
                {
                    sb.AppendFormat("{0} = {1};", assignedTo.Name, rightVar.Name);
                    return;
                }
                switch (assignedToData)
                {
                case EscapingMode.Pointer:
                    switch (localVariableData)
                    {
                    case EscapingMode.Stack:
                        sb.AppendFormat("{0} = &{1};", assignedTo.Name, rightVar.Name);
                        return;

                    case EscapingMode.Smart:
                        sb.AppendFormat("{0} = ({1}).get();", assignedTo.Name, rightVar.Name);
                        return;
                    }
                    break;

                case EscapingMode.Smart:
                    throw new InvalidDataException("Case not possible!");
                }
                throw new InvalidDataException("Case not handled");
            }
            else
            {
                sb.AppendFormat("{0} = {1};", assignedTo.Name, assignment.Right.ComputedValue());
            }
        }
        static void WriteClosureBodies(List <MethodInterpreter> closure, CodeOutput sb,
                                       TypeDescriptionTable typeTable, ClosureEntities closureEntities)
        {
            sb.Append("///--- PInvoke code ---\n");
            foreach (var interpreter in closure)
            {
                if (interpreter.Kind != MethodKind.PlatformInvoke)
                {
                    continue;
                }
                sb.Append(MethodInterpreterCodeWriter.WritePInvokeMethodCode((PlatformInvokeMethod)interpreter,
                                                                             closureEntities));
            }

            sb.Append("///---Begin closure code ---\n");
            foreach (var interpreter in closure)
            {
                if (interpreter.Kind != MethodKind.CilInstructions)
                {
                    continue;
                }

                if (interpreter.Method.IsAbstract)
                {
                    continue;
                }
                sb.Append(MethodInterpreterCodeWriter.WriteMethodCode((CilMethodInterpreter)interpreter, typeTable,
                                                                      closureEntities));
            }
            sb.Append("///---End closure code ---\n");
        }
        private void AddAllTypes(StringBuilder sb, TypeDescriptionTable table, ClosureEntities closure)
        {
            foreach (var type in TypesToCast)
            {
                sb.AppendFormat("// Type of {0}", type.FullName)
                .AppendLine();

                var typeIdBase = table.GetTypeId(type);

                sb.AppendFormat("std::vector<int> typeTable{0};", typeIdBase)
                .AppendLine();
                var implementingTypes = type.ImplementorsOfT(closure);
                foreach (var implementingType in implementingTypes)
                {
                    sb.AppendFormat("//Implementor {0}", implementingType.FullName)
                    .AppendLine();

                    var typeIdImpl = table.GetTypeId(implementingType);

                    sb
                    .AppendFormat("typeTable{0}.push_back({1});", typeIdBase, typeIdImpl)
                    .AppendLine();
                }

                sb.AppendFormat("GlobalMappingType[{0}] = typeTable{0};", typeIdBase)
                .AppendLine();
            }
        }
        static void WriteStructWithFields(CodeOutput codeOutput, ClosureEntities crRuntime, Type type)
        {
            if (DelegateManager.IsTypeDelegate(type))
                return;

            var mappedType = type.GetMappedType(crRuntime);
            type = mappedType.GetReversedMappedType(crRuntime);

            if (!type.IsValueType && type.BaseType != null)
            {
                //Not Necessary
                // codeOutput.AppendFormat("struct {0} : public {1} {2} {{", type.ToCppMangling(), type.BaseType.ToCppMangling(),type.GetInterfaces().Any()? " ,"+type.GetInterfaces().Select(j=>j.ToCppMangling()).Aggregate((a,b)=>a + " , " + b):"");
                codeOutput.AppendFormat(
                    "struct {0} : public {1}",
                    type.ToCppMangling(),
                    type.BaseType.ToCppMangling())
                    .BracketOpen();
            }
            else if (!type.IsValueType && type.IsInterface)
            {
                codeOutput.AppendFormat("struct {0} : public {1}",
                    type.ToCppMangling(),
                    typeof(object).ToCppMangling())
                    .BracketOpen();
            }
            else
            {
                codeOutput.AppendFormat("struct {0}", type.ToCppMangling())
                    .BracketOpen();
            }

            if (type == typeof(object))
            {
                codeOutput.Append("int _typeId;\n");
            }

            //String Support
            if (type == typeof(string))
            {
                crRuntime.AddType(typeof(string));
                var usedTypes = crRuntime.MappedTypes.Values.ToList();
                var typeTable = new TypeDescriptionTable(usedTypes, crRuntime);

                codeOutput.Append("System_String()")
                    .BracketOpen()
                    .AppendFormat("_typeId = {0};\n", typeTable.GetTypeId(typeof(string)))
                    .BracketClose()
                    .BlankLine();
            }

            WriteClassFieldsBody(codeOutput, mappedType, crRuntime);
            codeOutput.BracketClose(true)
                .Append(";\n")
                .BlankLine();

            var typedesc = UsedTypeList.Set(type, crRuntime);
            typedesc.WriteStaticFieldInitialization(codeOutput);
        }
示例#9
0
        public StringBuilder BuildFullSourceCode()
        {
            var         entryInterpreter = ResolveMethod(EntryPoint);
            List <Type> usedTypes        = MappedTypes.Values.ToList();
            var         typeTable        = new TypeDescriptionTable(usedTypes, this);

            return(CppCodeGenerator.GenerateSourceStringBuilder(entryInterpreter, typeTable,
                                                                MethodImplementations.Values.ToList(), this));
        }
        private static void HandleBox(Boxing boxing, StringBuilder bodySb, TypeDescriptionTable typeTable, ClosureEntities closureEntities)
        {
            TypeDescription typeDescription = boxing.Right.ComputedType();

            bodySb
            .AppendFormat("{0} = box_value<{2}>({1}, {3});",
                          boxing.AssignedTo.Name,
                          boxing.Right.Name,
                          typeDescription.GetClrType(closureEntities).ToDeclaredVariableType(EscapingMode.Stack),
                          typeTable.GetTypeId(typeDescription.GetClrType(closureEntities)));
        }
示例#11
0
 private void BuildVirtualMethodTable(TypeDescriptionTable typeTable,
                                      Dictionary <MethodInterpreterKey, MethodInterpreter> methodClosure)
 {
     _virtualMethodTable = new VirtualMethodTable(typeTable);
     foreach (var type in _typeDictionary.Keys)
     {
         var methods = type.GetMethods();
         foreach (var method in methods)
         {
             _virtualMethodTable.RegisterMethod(method, methodClosure);
         }
     }
 }
示例#12
0
        public CodeOutput GenerateSourceCodeOutput(
            MethodInterpreter interpreter,
            TypeDescriptionTable table,
            List <MethodInterpreter> closure,
            ClosureEntities closureEntities)
        {
            var headerSb = _createCodeOutput();

            headerSb.Append("#include \"sloth.h\"")
            .BlankLine();
            if (!string.IsNullOrEmpty(TypeNamerUtils.SmartPtrHeader))
            {
                headerSb
                .AppendFormat("#include {0}", TypeNamerUtils.SmartPtrHeader)
                .BlankLine();
            }

            var initializersCodeOutput = _createCodeOutput();

            TypeBodiesCodeGenerator.WriteClosureStructBodies(initializersCodeOutput, closureEntities);
            WriteClosureDelegateBodies(closure, initializersCodeOutput);
            WriteClosureHeaders(closure, initializersCodeOutput, closureEntities);

            initializersCodeOutput.BlankLine();
            initializersCodeOutput.Append("#include \"runtime_base.hpp\"");
            initializersCodeOutput.BlankLine();

            var bodySb = _createCodeOutput();

            bodySb.Append(VirtualMethodTableCodeWriter.GenerateTypeTableCode(table, closureEntities));
            // We need to use this type table to generate missing jumps for subclasses  that dont override a base method
            WriteCppMethods(closure, bodySb, closureEntities);
            WriteClosureMethods(closure, bodySb, table, closureEntities);

            WriteMainBody(interpreter, bodySb, closureEntities);
            bodySb.Append(PlatformInvokeCodeWriter.LoadDllMethods());
            bodySb.Append(ConstByteArrayList.BuildConstantTable());

            LinkingData.Instance.IsInstTable.BuildTypeMatchingTable(table, closureEntities, initializersCodeOutput.StringBuilderOutput);
            bodySb.Append(LinkingData.Instance.Strings.BuildStringTable());


            return(headerSb
                   .Append(initializersCodeOutput.ToString())
                   .Append(bodySb.ToString()));
        }
示例#13
0
        public void GenerateInstructionCode(IsInstance isInstance, CodeOutput sb, ClosureEntities crRuntime)
        {
            AddToRuntime(crRuntime);
            //Needs improvement, how do i get the correct typeid at this point ? we cant just use zero :P
            //This is a stupid hack as usedtypes can probably change as closure is computed

            crRuntime.AddType(isInstance.CastTo);
            var usedTypes = crRuntime.MappedTypes.Values.ToList();
            var typeTable = new TypeDescriptionTable(usedTypes, crRuntime);

            TypesToCast.Add(isInstance.CastTo);
            sb
            .AppendFormat("{0} = IsInstanceOf({1}, {2});",
                          isInstance.AssignedTo.Name,
                          typeTable.GetTypeId(isInstance.CastTo),
                          isInstance.Right.Name + "->_typeId"
                          );
        }
        public static string WriteCode(MethodInterpreter interpreter, TypeDescriptionTable typeTable,
                                       CrRuntimeLibrary crRuntime)
        {
            var operations = interpreter.MidRepresentation.LocalOperations;
            var headerSb   = new StringBuilder();
            var sb         = CppWriteSignature.WriteSignature(interpreter, crRuntime);

            headerSb.AppendLine(sb.ToString());
            headerSb.Append("{");
            var bodySb      = ComputeBodySb(operations, interpreter.MidRepresentation.Vars, typeTable, interpreter, crRuntime);
            var variablesSb = ComputeVariableSb(interpreter.MidRepresentation, interpreter);
            var finalSb     = new StringBuilder();

            finalSb.AppendLine(headerSb.ToString());
            finalSb.AppendLine(variablesSb.ToString());
            finalSb.AppendLine(bodySb.ToString());
            return(finalSb.ToString());
        }
        private static void WriteStructWithFields(StringBuilder sb, ClosureEntities crRuntime, Type type)
        {
            if (DelegateManager.IsTypeDelegate(type))
            {
                return;
            }
            var mappedType = type.GetMappedType(crRuntime);

            type = mappedType.GetReversedMappedType(crRuntime);

            if (!type.IsValueType && type.BaseType != null)
            {
                //Not Necessary
                // sb.AppendFormat("struct {0} : public {1} {2} {{", type.ToCppMangling(), type.BaseType.ToCppMangling(),type.GetInterfaces().Any()? " ,"+type.GetInterfaces().Select(j=>j.ToCppMangling()).Aggregate((a,b)=>a + " , " + b):"");
                sb.AppendFormat("struct {0} : public {1} {{", type.ToCppMangling(), type.BaseType.ToCppMangling());
            }
            else if (!type.IsValueType && type.IsInterface)
            {
                sb.AppendFormat("struct {0} : public {1} {{", type.ToCppMangling(), typeof(object).ToCppMangling());
            }
            else
            {
                sb.AppendFormat("struct {0} {{", type.ToCppMangling());
            }
            sb.AppendLine();
            if (type == typeof(object))
            {
                sb.AppendLine("int _typeId;");
            }
            //String Support
            if (type == typeof(string))
            {
                crRuntime.AddType(typeof(string));
                List <Type> usedTypes = crRuntime.MappedTypes.Values.ToList();
                var         typeTable = new TypeDescriptionTable(usedTypes, crRuntime);
                sb.AppendLine(String.Format("System_String() {{_typeId = {0}; }}", typeTable.GetTypeId(typeof(string))));
            }
            WriteClassFieldsBody(sb, mappedType, crRuntime);
            sb.AppendFormat("}};").AppendLine();

            var typedesc = UsedTypeList.Set(type, crRuntime);

            typedesc.WriteStaticFieldInitialization(sb);
        }
        public static bool HandleCastRelatedOperations(TypeDescriptionTable typeTable, ClosureEntities crRuntime,
                                                       LocalOperation operation, CodeOutput bodySb, OperationKind opKind)
        {
            switch (opKind)
            {
            case OperationKind.Box:
                if (!Boxing.IsUsed)
                {
                    Boxing.IsUsed = true;
                    bodySb.Append(BoxingTemplate);
                }
                HandleBox((Boxing)operation, bodySb, typeTable, crRuntime);
                break;

            case OperationKind.CastClass:
                HandleCastClass((ClassCasting)operation, bodySb, crRuntime);
                break;

            case OperationKind.Unbox:
                HandleUnbox((Unboxing)operation, bodySb, crRuntime);
                break;

            case OperationKind.IsInstance:
            {
                var declarations = new List <string>
                {
                    "bool IsInstanceOf(int typeSource, int typeImplementation);",
                    "System_Void buildTypesTable();",
                    "std::map<int, std::vector<int> > GlobalMappingType;"
                };

                bodySb.Append(Join(Environment.NewLine, declarations));

                HandleIsInstance((IsInstance)operation, bodySb, crRuntime);
            }
            break;

            default:
                return(false);
            }
            return(true);
        }
示例#17
0
        public static string WriteCode(CilMethodInterpreter interpreter, TypeDescriptionTable typeTable,
                                       ClosureEntities crRuntime)
        {
            var operations = interpreter.MidRepresentation.LocalOperations;
            var headerSb   = new CodeOutput();

            CppWriteSignature.WriteSignature(headerSb, interpreter, crRuntime);

            var bodySb      = ComputeBodySb(operations, interpreter.MidRepresentation.Vars, typeTable, interpreter, crRuntime);
            var variablesSb = ComputeVariableSb(interpreter.MidRepresentation, interpreter, crRuntime);
            var finalSb     = new CodeOutput();

            finalSb.Append(headerSb.ToString())
            .BracketOpen()
            .Append(variablesSb.ToString())
            .Append(bodySb.ToString())
            .BracketClose();

            return(finalSb.ToString());
        }
        static void HandleNewObject(LocalOperation operation, CodeOutput bodySb, TypeDescriptionTable typeTable,
                                    MethodInterpreter interpreter, ClosureEntities crRuntime)
        {
            var value      = (NewConstructedObject)operation;
            var rightValue = value;
            var localValue = rightValue.Info;

            var declaringType = localValue.DeclaringType;
            var targetType    = declaringType.GetMappedType(crRuntime);
            var cppName       = declaringType.ToDeclaredVariableType(EscapingMode.Stack);
            var assignedData  = interpreter.AnalyzeProperties.GetVariableData(value.AssignedTo);
            var isStack       = assignedData == EscapingMode.Stack;

            if (isStack)
            {
                bodySb
                .AppendFormat("{1} {0};", value.AssignedTo.Name, cppName);
            }
            else
            {
                bodySb.AppendFormat("{0} = std::make_shared<{1}>();", value.AssignedTo.Name, cppName);
            }
            typeTable.SetIdOfInstance(bodySb, value.AssignedTo, targetType, isStack);
        }
 public static string WriteMethodCode(MethodInterpreter interpreter, TypeDescriptionTable typeTable,
                                      CrRuntimeLibrary crRuntime)
 {
     return(CppMethodCodeWriter.WriteCode(interpreter, typeTable, crRuntime));
 }
示例#20
0
 private static void WriteClosureMethods(List <MethodInterpreter> closure, StringBuilder sb, TypeDescriptionTable typeTable, ClosureEntities closureEntities)
 {
     WriteClosureBodies(closure, sb, typeTable, closureEntities);
 }
示例#21
0
        public static StringBuilder GenerateSourceStringBuilder(MethodInterpreter interpreter, TypeDescriptionTable table, List <MethodInterpreter> closure, ClosureEntities closureEntities)
        {
            var headerSb = new StringBuilder();

            headerSb.AppendLine("#include \"sloth.h\"");
            headerSb.AppendLine("#include <functional>");


            var initializersSb = new StringBuilder();

            TypeBodiesCodeGenerator.WriteClosureStructBodies(initializersSb, closureEntities);
            WriteClosureDelegateBodies(closure, initializersSb);
            WriteClosureHeaders(closure, initializersSb, closureEntities);

            initializersSb.AppendLine("#include \"runtime_base.hpp\"");


            var bodySb = new StringBuilder();

            bodySb.AppendLine(VirtualMethodTableCodeWriter.GenerateTypeTableCode(table, closureEntities)); // We need to use this type table to generate missing jumps for subclasses  that dont override a base method
            WriteCppMethods(closure, bodySb, closureEntities);
            WriteClosureMethods(closure, bodySb, table, closureEntities);

            WriteMainBody(interpreter, bodySb, closureEntities);
            bodySb.AppendLine(PlatformInvokeCodeWriter.LoadDllMethods());
            bodySb.AppendLine(ConstByteArrayList.BuildConstantTable());

            LinkingData.Instance.IsInstTable.BuildTypeMatchingTable(table, closureEntities);
            bodySb.AppendLine(LinkingData.Instance.Strings.BuildStringTable());

            //Add Logic to Automatically include std class features that are needed ...
            if (closureEntities.Features.Count > 0)
            {
                foreach (var runtimeFeature in closureEntities.Features)
                {
                    if (runtimeFeature.IsUsed)
                    {
                        if (runtimeFeature.Headers.Count > 0)
                        {
                            headerSb.AppendLine("//Headers For Feature: " + runtimeFeature.Name + "\n" +
                                                runtimeFeature.Headers.Select(g => "#include<" + g + ">").Aggregate((a, b) => a + "\n" + b) + "\n//End Of Headers For Feature: " + runtimeFeature.Name + "\n");
                        }
                        if (runtimeFeature.Declarations.Count > 0)
                        {
                            initializersSb.AppendLine("//Initializers For: " + runtimeFeature.Name + "\n" + runtimeFeature.Declarations.Aggregate((a, b) => a + "\n" + b) + "\n//End OF Initializers For: " + runtimeFeature.Name + "\n");
                        }
                        if (!String.IsNullOrEmpty(runtimeFeature.Functions))
                        {
                            bodySb.AppendLine("//Functions For Feature: " + runtimeFeature.Name + "\n" + runtimeFeature.Functions + "\n//End Of Functions For Feature: " + runtimeFeature.Name + "\n");
                        }
                    }
                }
            }

            return(headerSb.Append(initializersSb).Append(bodySb));
        }
        private static StringBuilder ComputeBodySb(List <LocalOperation> operations, MidRepresentationVariables vars,
                                                   TypeDescriptionTable typeTable, MethodInterpreter interpreter, ClosureEntities crRuntime)
        {
            var bodySb = new StringBuilder();

            foreach (var operation in operations)
            {
                if (CppHandleOperators.HandleAssignmentOperations(bodySb, operation, operation.Kind, typeTable,
                                                                  interpreter, crRuntime))
                {
                    bodySb.AppendLine();
                    continue;
                }
                switch (operation.Kind)
                {
                case OperationKind.Label:
                    WriteLabel(bodySb, ((Label)operation).JumpTo);
                    break;

                case OperationKind.AlwaysBranch:
                    HandleAlwaysBranchOperator(operation, bodySb);
                    break;

                case OperationKind.BranchOperator:
                    CppHandleBranches.HandleBranchOperator(operation, bodySb);
                    break;

                case OperationKind.Call:
                    CppHandleCalls.HandleCall(operation, bodySb, vars, interpreter, crRuntime);
                    break;

                case OperationKind.CallInterface:
                    CppHandleCalls.HandleCallInterface(operation, bodySb, vars, interpreter, crRuntime);
                    break;

                case OperationKind.CallVirtual:
                    CppHandleCalls.HandleCallVirtual(operation, bodySb, interpreter, crRuntime);
                    break;

                case OperationKind.CallRuntime:
                    CppHandleCalls.HandleCallRuntime(operation, bodySb, crRuntime);
                    break;

                case OperationKind.Return:
                    CppHandleCalls.HandleReturn(operation, bodySb, interpreter);
                    break;

                case OperationKind.CopyArrayInitializer:
                    HandleCopyArrayInitializer(operation, bodySb);
                    break;

                case OperationKind.Switch:
                    HandleSwitch(operation, bodySb);
                    break;

                case OperationKind.Comment:
                    HandleComment(operation.ToString(), bodySb);
                    break;

                case OperationKind.Box:
                    var boxing = crRuntime.FindFeature("Boxing");
                    if (!boxing.IsUsed)
                    {
                        boxing.IsUsed = true;
                        boxing.Declarations.Add(@"template<class T>
struct BoxedT : public System_Object
{
	T Data;
};

template<class T>
std::shared_ptr<System_Object> box_value(T value, int typeId){
	auto result = std::make_shared<BoxedT< T > >();
	result->_typeId = typeId;
	result->Data = value;
	return result;
}

template<class T>
T unbox_value(std::shared_ptr<System_Object> value){
	auto resultObject = value.get();
	auto castedUnboxing = (BoxedT<T>*)resultObject;
	return castedUnboxing->Data;
}");
                    }
                    HandleBox((Boxing)operation, bodySb, typeTable, crRuntime);
                    break;

                case OperationKind.CastClass:
                    HandleCastClass((ClassCasting)operation, bodySb, crRuntime);
                    break;

                case OperationKind.Unbox:
                    HandleUnbox((Unboxing)operation, bodySb, crRuntime);
                    break;

                case OperationKind.IsInstance:

                    HandleIsInstance((IsInstance)operation, bodySb, crRuntime);
                    break;

                default:
                    throw new InvalidOperationException(
                              string.Format(
                                  "Invalid operation '{0}' is introduced in intermediary representation\nValue: {1}",
                                  operation.Kind,
                                  operation));
                }
                bodySb.AppendLine();
            }
            bodySb.AppendLine("}");
            return(bodySb);
        }
示例#23
0
        public static string GenerateTypeTableCode(TypeDescriptionTable table, ClosureEntities crRuntime)
        {
            var sb = new StringBuilder();

            sb.AppendLine("// --- Begin definition of virtual implementingMethod tables ---");
            sb.AppendLine("System_Void setupTypeTable();")
            .AppendLine();


            var vcalls = crRuntime.AbstractMethods;

            WriteForwardVcalls(crRuntime, vcalls, sb);



            foreach (var virtualMethod in vcalls)
            {
                var methodName       = virtualMethod.ClangMethodSignature(crRuntime);
                var parametersString = GetParametersString(virtualMethod, crRuntime);

                sb.Append(virtualMethod.ReturnType.ToCppName(EscapingMode.Smart));
                sb.Append(" ");
                sb.Append(methodName);
                sb.Append("_vcall(");
                sb.AppendFormat(parametersString);
                sb.AppendLine(") {");

                sb.AppendLine("switch (_this->_typeId)").AppendLine("{");

                var declaringType = virtualMethod.DeclaringType;

                var implementingTypes = declaringType.ImplementorsOfT(crRuntime);//.MappedTypes.Values);
                foreach (var implementingType in implementingTypes)
                {
                    if (implementingType.GetReversedMappedType(crRuntime) != implementingType)
                    {
                        continue;
                    }
                    var implementingMethod = AddVirtualMethodImplementations.GetImplementingMethod(implementingType, virtualMethod);
//                    if (implementingMethod == null) //We should call the next implementingMethod in line ... not ignore this object
//                        continue;
                    if (implementingMethod != null)
                    {
                        if (implementingMethod.GetMethodBody() == null)
                        {
                            continue;
                        }
                        var declaringTypeImplementation =
                            implementingMethod.DeclaringType.GetReversedMappedType(crRuntime);

                        var typeId = table.GetTypeId(declaringTypeImplementation);

                        sb.AppendFormat("case {0}:", typeId).AppendLine();



                        var isVoid = virtualMethod.ReturnType == typeof(void);
                        if (!isVoid)
                        {
                            sb.Append("return ");
                        }



                        var methodImpl           = implementingMethod.ClangMethodSignature(crRuntime);
                        var parametersCallString = GetCall(virtualMethod, implementingMethod, crRuntime);

                        sb
                        .AppendFormat("{0}(", methodImpl)
                        .AppendFormat("{0});", parametersCallString)
                        .AppendLine();
                        if (isVoid)
                        {
                            sb.Append("return;").AppendLine();
                        }
                    }
                    else
                    {
                        var typeId = table.GetTypeId(implementingType.GetReversedMappedType(crRuntime));

                        sb.AppendFormat("case {0}:", typeId).AppendLine();

                        var isVoid = virtualMethod.ReturnType == typeof(void);
                        if (!isVoid)
                        {
                            sb.Append("return ");
                        }



                        var method = implementingType.GetMethod(virtualMethod.Name, virtualMethod.GetParameters().Select(j => j.ParameterType).ToArray());

                        var methodImpl           = method.ClangMethodSignature(crRuntime);
                        var parametersCallString = GetCall(virtualMethod, method, crRuntime);
                        sb
                        .AppendFormat("{0}(", methodImpl)
                        .AppendFormat("{0});", parametersCallString)
                        .AppendLine();
                        if (isVoid)
                        {
                            sb.Append("return;").AppendLine();
                        }
                    }
                }

                sb.AppendLine("} //switch");
                sb.AppendLine("}");
            }

            return(sb.ToString());
        }
示例#24
0
 public static string WriteMethodCode(CilMethodInterpreter interpreter, TypeDescriptionTable typeTable, ClosureEntities closureEntities)
 {
     return(CppMethodCodeWriter.WriteCode(interpreter, typeTable, closureEntities));
 }
示例#25
0
 private static void WriteClosureMethods(List <MethodInterpreter> closure, StringBuilder sb,
                                         TypeDescriptionTable typeTable, CrRuntimeLibrary crRuntime)
 {
     WriteClosureBodies(closure, sb, typeTable, crRuntime);
 }
示例#26
0
 static void WriteClosureMethods(List <MethodInterpreter> closure, CodeOutput sb,
                                 TypeDescriptionTable typeTable, ClosureEntities closureEntities)
 {
     WriteClosureBodies(closure, sb, typeTable, closureEntities);
 }
        public static bool HandleAssignmentOperations(StringBuilder bodySb, LocalOperation operation, OperationKind kind, TypeDescriptionTable typeTable, MethodInterpreter interpreter, ClosureEntities crRuntime)
        {
            switch (kind)
            {
            case OperationKind.Assignment:
                HandleAssign(bodySb, operation, interpreter, crRuntime);
                break;

            case OperationKind.BinaryOperator:
                HandleOperator(operation, bodySb, crRuntime);
                break;

            case OperationKind.UnaryOperator:
                HandleUnaryOperator((UnaryOperator)operation, bodySb);
                break;

            case OperationKind.SetField:
                HandleSetField(operation, bodySb, crRuntime);
                break;

            case OperationKind.GetField:
                HandleGetField(operation, bodySb, interpreter);
                break;

            case OperationKind.SetStaticField:
                HandleSetStaticField(operation, bodySb);
                break;

            case OperationKind.GetStaticField:
                HandleLoadStaticField(operation, bodySb, crRuntime);
                break;

            case OperationKind.GetArrayItem:
                HandleReadArrayItem(operation, bodySb, interpreter, crRuntime);
                break;

            case OperationKind.SetArrayItem:
                HandleSetArrayValue(operation, bodySb, interpreter);
                break;

            case OperationKind.NewObject:
                HandleNewObject(operation, bodySb, typeTable, interpreter, crRuntime);
                break;

            case OperationKind.NewArray:
                HandleNewArray(operation, bodySb, interpreter);
                break;

            case OperationKind.AddressOfArrayItem:
                HandleGetAddressOfArrayItem(operation, bodySb);
                break;

            case OperationKind.RefAssignment:
                HandleRefAssignment(operation, bodySb);
                break;

            case OperationKind.DerefAssignment:
                HandleDerefAssignment(operation, bodySb);
                break;

            case OperationKind.FieldRefAssignment:
                HandleFieldRefAssignment(operation, bodySb);
                break;

            case OperationKind.LoadFunction:
                HandleLoadFunction(operation, bodySb, crRuntime);
                break;

            case OperationKind.SizeOf:
                HandleSizeOf(operation, bodySb);
                break;

            default:
                return(false);
            }
            return(true);
        }
        private static StringBuilder ComputeBodySb(List <LocalOperation> operations, MidRepresentationVariables vars,
                                                   TypeDescriptionTable typeTable, MethodInterpreter interpreter, CrRuntimeLibrary crRuntime)
        {
            var bodySb = new StringBuilder();

            foreach (var operation in operations)
            {
                if (CppHandleOperators.HandleAssignmentOperations(vars, bodySb, operation, operation.Kind, typeTable,
                                                                  interpreter))
                {
                    bodySb.AppendLine();
                    continue;
                }
                switch (operation.Kind)
                {
                case OperationKind.Label:
                    WriteLabel(bodySb, (int)operation.Value);
                    break;

                case OperationKind.AlwaysBranch:
                    HandleAlwaysBranchOperator(operation, bodySb);
                    break;

                case OperationKind.BranchOperator:
                    CppHandleBranches.HandleBranchOperator(operation, bodySb);
                    break;

                case OperationKind.Call:
                    CppHandleCalls.HandleCall(operation, bodySb, vars, interpreter, crRuntime);
                    break;

                case OperationKind.CallInterface:
                    CppHandleCalls.HandleCallInterface(operation, bodySb, vars, interpreter, crRuntime);
                    break;

                case OperationKind.CallVirtual:
                    CppHandleCalls.HandleCallVirtual(operation, bodySb, vars, interpreter, crRuntime);
                    break;

                case OperationKind.CallRuntime:
                    CppHandleCalls.HandleCallRuntime(operation, bodySb);
                    break;

                case OperationKind.Return:
                    CppHandleCalls.HandleReturn(operation, bodySb);
                    break;

                case OperationKind.CopyArrayInitializer:
                    HandleCopyArrayInitializer(operation, bodySb);
                    break;

                case OperationKind.Switch:
                    HandleSwitch(operation, bodySb);
                    break;

                case OperationKind.Comment:
                    HandleComment(operation.Value.ToString(), bodySb);
                    break;

                default:
                    throw new InvalidOperationException(
                              string.Format(
                                  "Invalid operation '{0}' is introduced in intermediary representation\nValue: {1}",
                                  operation.Kind,
                                  operation.Value));
                }
                bodySb.AppendLine();
            }
            bodySb.AppendLine("}");
            return(bodySb);
        }
示例#29
0
        static CodeOutput ComputeBodySb(List <LocalOperation> operations, MidRepresentationVariables vars,
                                        TypeDescriptionTable typeTable, MethodInterpreter interpreter, ClosureEntities crRuntime)
        {
            var bodySb = new CodeOutput();

            foreach (var operation in operations)
            {
                bodySb.Append("\n");
                if (CppHandleOperators.HandleAssignmentOperations(bodySb, operation, operation.Kind, typeTable,
                                                                  interpreter, crRuntime))
                {
                    continue;
                }
                if (CppCastRelatedOperations.HandleCastRelatedOperations(typeTable, crRuntime, operation, bodySb,
                                                                         operation.Kind))
                {
                    continue;
                }
                if (HandleCallOperations(vars, interpreter, crRuntime, operation, bodySb))
                {
                    continue;
                }

                switch (operation.Kind)
                {
                case OperationKind.Label:
                    WriteLabel(bodySb, ((Label)operation).JumpTo);
                    break;

                case OperationKind.AlwaysBranch:
                    HandleAlwaysBranchOperator(operation, bodySb);
                    break;

                case OperationKind.BranchOperator:
                    CppHandleBranches.HandleBranchOperator(operation, bodySb);
                    break;

                case OperationKind.Return:
                    CppHandleCalls.HandleReturn(operation, bodySb, interpreter);
                    break;

                case OperationKind.CopyArrayInitializer:
                    HandleCopyArrayInitializer(operation, bodySb);
                    break;

                case OperationKind.Switch:
                    HandleSwitch(operation, bodySb);
                    break;

                case OperationKind.Comment:
                    HandleComment(operation.ToString(), bodySb);
                    break;


                default:
                    throw new InvalidOperationException(
                              $"Invalid operation '{operation.Kind}' is introduced in intermediary representation\nValue: {operation}");
                }
            }

            return(bodySb);
        }