Exemplo n.º 1
0
 public override ExpressionTarget ParseExpression(
     HlCompilation compilation,
     HlUnaryOp expr,
     ExpressionTarget outputTarget)
 {
     return(Emit(compilation, compilation.Parse(expr.Left), outputTarget));
 }
Exemplo n.º 2
0
 protected override ExpressionTarget ComputeStatic(
     HlCompilation compilation,
     ExpressionTarget left,
     ExpressionTarget right)
 {
     return(new ExpressionTarget($"{left.StaticParse() * right.StaticParse()}", false, left.TypeDefinition));
 }
        public static ExpressionTarget ParseFunctionInvocation(
            HlCompilation compilation,
            HlInvocationOp expr,
            int targetLength,
            string functionName,
            string jumpInstruction)
        {
            if (expr.ParameterList.Length != targetLength)
            {
                if (!(expr.MemberDefinition != null &&
                      (expr.MemberDefinition == expr.InstanceType.StaticConstructor ||
                       expr.MemberDefinition == expr.InstanceType.DynamicConstructor ||
                       expr.Instance == null)))
                {
                    EventManager <ErrorEvent> .SendEvent(
                        new FunctionArgumentMismatchEvent(
                            $"{functionName}: Invalid parameter Count. Expected {targetLength} got {expr.ParameterList.Length}"
                            )
                        );
                }
            }

            if (expr.Instance != null)
            {
                compilation.EmitterResult.Emit(
                    $"PUSH",
                    expr.Instance
                    );
            }

            foreach (HlExpression parameter in expr.ParameterList)
            {
                ExpressionTarget argVal = compilation.Parse(
                    parameter
                    );
                ExpressionTarget arg = argVal.MakeAddress(compilation);

                compilation.EmitterResult.Emit(
                    $"PUSH",
                    arg.ResultAddress
                    );

                compilation.ReleaseTempVar(arg.ResultAddress);

                compilation.ReleaseTempVar(argVal.ResultAddress);
            }

            compilation.EmitterResult.Emit(jumpInstruction, functionName);

            ExpressionTarget tempReturn = new ExpressionTarget(
                compilation.GetTempVarPop(),
                true,
                compilation.TypeSystem.GetType(
                    compilation.Root,
                    HLBaseTypeNames.s_UintTypeName
                    )
                );

            return(tempReturn);
        }
Exemplo n.º 4
0
        public override ExpressionTarget ParseExpression(
            HlCompilation compilation,
            HlArrayAccessorOp expr,
            ExpressionTarget outputTarget)
        {
            ExpressionTarget tempPtrVar = compilation.Parse(expr.Left);

            ExpressionTarget tempPtr = new ExpressionTarget(
                SettingsManager.GetSettings <HlCompilerSettings>().OmitTempVarInit
                                                                ? compilation.GetTempVar()
                                                                : compilation.GetTempVar(0),
                true,
                tempPtrVar.TypeDefinition,
                true
                );

            ExpressionTarget pnVal = compilation.Parse(
                expr.ParameterList[0]
                );
            ExpressionTarget pn = pnVal.MakeAddress(compilation);

            if (tempPtrVar.TypeDefinition is ArrayTypeDefintion adef)
            {
                string tmpSName = compilation.GetTempVar(adef.ElementType.GetSize());
                compilation.EmitterResult.Emit($"MUL", pn.ResultAddress, tmpSName);
                compilation.ReleaseTempVar(tmpSName);
                compilation.EmitterResult.Emit($"LOAD", tempPtr.ResultAddress, tempPtrVar.ResultAddress);
            }
            else
            {
                string tmpSName = compilation.GetTempVar(tempPtrVar.TypeDefinition.GetSize());
                compilation.EmitterResult.Emit($"MUL", pn.ResultAddress, tmpSName);
                compilation.ReleaseTempVar(tmpSName);
                compilation.EmitterResult.Emit($"COPY", tempPtrVar.ResultAddress, tempPtr.ResultAddress);
            }

            compilation.EmitterResult.Emit($"ADD", tempPtr.ResultAddress, pn.ResultAddress);

            if (outputTarget.ResultAddress != null)
            {
                compilation.EmitterResult.Emit(
                    $"DREF",
                    tempPtr.ResultAddress,
                    outputTarget.ResultAddress
                    );

                compilation.ReleaseTempVar(tempPtr.ResultAddress);
                compilation.ReleaseTempVar(tempPtrVar.ResultAddress);
                compilation.ReleaseTempVar(pn.ResultAddress);
                compilation.ReleaseTempVar(pnVal.ResultAddress);

                return(outputTarget);
            }

            compilation.ReleaseTempVar(tempPtrVar.ResultAddress);
            compilation.ReleaseTempVar(pn.ResultAddress);
            compilation.ReleaseTempVar(pnVal.ResultAddress);

            return(tempPtr);
        }
Exemplo n.º 5
0
        public override ExpressionTarget ParseExpression(
            HlCompilation compilation,
            HlUnaryOp expr,
            ExpressionTarget outputTarget)
        {
            ExpressionTarget targetVal = compilation.Parse(
                expr.Left
                );
            ExpressionTarget target = targetVal.MakeAddress(compilation);

            if (target.TypeDefinition.Name != HLBaseTypeNames.s_FloatTypeName)
            {
                EventManager <WarningEvent> .SendEvent(
                    new UnaryMinusExpressionInvalidEvent(
                        "Unary inversion is only possible with signed types and floats, performing this instruction on other types may yield undefined results."
                        )
                    );
            }

            if (outputTarget.ResultAddress == target.ResultAddress)
            {
                compilation.EmitterResult.Emit("INV.F", outputTarget.ResultAddress);

                return(outputTarget);
            }
            else
            {
                compilation.EmitterResult.Emit("INV.F", target.ResultAddress, outputTarget.ResultAddress);
                ExpressionTarget ret = target.CopyIfNotNull(compilation, outputTarget);
                compilation.ReleaseTempVar(target.ResultAddress);
                return(ret);
            }
        }
Exemplo n.º 6
0
        public override ExpressionTarget ParseExpression(
            HlCompilation compilation,
            HlUnaryOp expr,
            ExpressionTarget outputTarget)
        {
            ExpressionTarget targetVal = compilation.Parse(
                expr.Left
                );
            ExpressionTarget target = targetVal.
                                      MakeAddress(compilation);

            //BNE target rTarget if_b0_fail
            //LOAD possibleTarget 0x1; True Value
            //.if_b0_fail
            string label = HlCompilation.GetUniqueName("bexpr_not");

            compilation.EmitterResult.Emit($"LOAD", outputTarget.ResultAddress, "1");
            compilation.EmitterResult.Emit($"BEZ", target.ResultAddress, label);
            compilation.EmitterResult.Emit($"LOAD", outputTarget.ResultAddress, "0");
            compilation.EmitterResult.Store($".{label} linker:hide");
            compilation.ReleaseTempVar(target.ResultAddress);
            compilation.ReleaseTempVar(targetVal.ResultAddress);

            return(outputTarget);
        }
        /// <summary>
        /// Registers the expression in the target container
        /// </summary>
        /// <param name="targetContainer">The target container in which the registration will be made.</param>
        /// <param name="expression">The expression to be registered.</param>
        /// <param name="declaredType">Optional.  The <see cref="ITarget.DeclaredType"/> of the target to be created,
        /// if different from the <see cref="Expression.Type"/> of the <paramref name="expression"/> (or its
        /// <see cref="LambdaExpression.Body"/> if the expression is a <see cref="LambdaExpression"/>).
        ///
        /// Will also override the type against which the expression will be registered if provided.</param>
        /// <param name="scopeBehaviour">Optional.  Controls how the object generated from the compiled expression will be
        /// tracked if the target is executed within an <see cref="ContainerScope" />.  The default is <see cref="ScopeBehaviour.Implicit" />.</param>
        /// <param name="scopePreference">Optional.  If <paramref name="scopeBehaviour"/> is not <see cref="ScopeBehaviour.None"/>, then this controls the
        /// type of scope in which the instance should be tracked.  Defaults to <see cref="ScopePreference.Current"/>.  <see cref="ScopePreference.Root"/>
        /// should be used if the result of the delegate is effectively a singleton.</param>
        public static void RegisterExpression(
            this ITargetContainer targetContainer,
            Expression expression,
            Type declaredType               = null,
            ScopeBehaviour scopeBehaviour   = ScopeBehaviour.Implicit,
            ScopePreference scopePreference = ScopePreference.Current)
        {
            if (targetContainer == null)
            {
                throw new ArgumentNullException(nameof(targetContainer));
            }

            if (expression == null)
            {
                throw new ArgumentNullException(nameof(expression));
            }

            ITarget toRegister = new ExpressionTarget(expression, declaredType);

            if (scopeBehaviour == ScopeBehaviour.Explicit)
            {
                toRegister = toRegister.Scoped();
            }
            else if (scopeBehaviour == ScopeBehaviour.None)
            {
                toRegister = toRegister.Unscoped();
            }

            targetContainer.Register(toRegister);
        }
Exemplo n.º 8
0
        public override ExpressionTarget ParseExpression(HlCompilation compilation, HlReturnOp expr)
        {
            if (expr.Right != null)
            {
                ExpressionTarget ptVal = compilation.Parse(
                    expr.Right
                    );
                ExpressionTarget pt = ptVal.
                                      MakeAddress(compilation);

                compilation.EmitterResult.Emit($"PUSH", pt.ResultAddress);

                compilation.ReleaseTempVar(pt.ResultAddress);
                compilation.ReleaseTempVar(ptVal.ResultAddress);
            }
            else
            {
                string v = SettingsManager.GetSettings <HlCompilerSettings>().OmitTempVarInit
                               ? compilation.GetTempVar()
                               : compilation.GetTempVar(0);
                compilation.EmitterResult.Emit($"PUSH", v);
                compilation.ReleaseTempVar(v);
            }

            compilation.EmitterResult.Emit("RET");

            return(new ExpressionTarget());
        }
Exemplo n.º 9
0
        public override ExpressionTarget ParseExpression(HlCompilation compilation, HlUnaryOp expr)
        {
            ExpressionTarget target = compilation.Parse(expr.Left);

            HlTypeDefinition tDef = target.TypeDefinition ??
                                    compilation.TypeSystem.GetType(compilation.Root, HLBaseTypeNames.s_UintTypeName);


            string funcName = tDef.GetFinalStaticFunction(expr.OperationType.ToString());

            return(InvocationExpressionCompiler.ParseFunctionInvocation(
                       compilation,
                       new HlInvocationOp(
                           new HlValueOperand(
                               new HlTextToken(
                                   HlTokenType.OpWord,
                                   funcName,
                                   0
                                   )
                               ),
                           new[] { expr.Left }
                           ),
                       1,
                       funcName,
                       "JSR"
                       ));
        }
Exemplo n.º 10
0
        public override ExpressionTarget ParseExpression(
            HlCompilation compilation,
            HlBinaryOp expr)
        {
            ExpressionTarget target = compilation.Parse(expr.Left);

            ExpressionTarget rTargetVal = compilation.Parse(
                expr.Right
                );
            ExpressionTarget rTarget = rTargetVal.MakeAddress(compilation);

            string instrKey =
                target.TypeDefinition.Name == HLBaseTypeNames.s_FloatTypeName ||
                rTarget.TypeDefinition.Name == HLBaseTypeNames.s_FloatTypeName
                    ? InstructionKey + ".F"
                    : InstructionKey;

            compilation.EmitterResult.Emit(
                instrKey,
                target.ResultAddress,
                rTarget.ResultAddress
                );

            compilation.ReleaseTempVar(rTarget.ResultAddress);
            compilation.ReleaseTempVar(rTargetVal.ResultAddress);

            return(target);
        }
        public void DeclaredTypeShouldBeInheritedFromLambdaExpression()
        {
            Expression <Func <ResolveContext, string> > expr = c => "hello world";

            var result2 = new ExpressionTarget(expr);

            Assert.Same(typeof(string), result2.DeclaredType);
        }
        public void DeclaredTypeShouldBeInheritedFromConstantExpression()
        {
            //use two expressions: a lambda and a standard expression
            var expr = Expression.Constant("hello world");

            var result1 = new ExpressionTarget(expr);

            Assert.Same(typeof(string), result1.DeclaredType);
        }
Exemplo n.º 13
0
        private bool IsReducable(ExpressionTarget target)
        {
            if (!target.IsAddress)
            {
                uint v = target.StaticParse();

                return(v != 0 && (v & (v - 1)) == 0);    //Is Power of 2?
            }

            return(false);
        }
Exemplo n.º 14
0
        private void ParseBody(HlCompilation compilation, HlWhileOp expr, string start, string end)
        {
            foreach (HlExpression hlExpression in expr.Block)
            {
                ExpressionTarget e = compilation.Parse(hlExpression);
                compilation.ReleaseTempVar(e.ResultAddress);
            }

            compilation.EmitterResult.Emit($"JMP", start);
            compilation.EmitterResult.Store($".{end} linker:hide");
        }
        public void ShouldSetExpressionOrFactory()
        {
            var expr = Expression.Constant("hello world");

            Assert.Same(expr, new ExpressionTarget(expr).Expression);
            Func <ICompileContext, Expression> factory = c => expr;
            var factoryTarget = new ExpressionTarget(factory, typeof(string));

            //we test DeclaredType for straight Expressions next
            Assert.Same(factory, factoryTarget.ExpressionFactory);
            Assert.Equal(typeof(string), factoryTarget.DeclaredType);
        }
Exemplo n.º 16
0
        public override ExpressionTarget ParseExpression(HlCompilation compilation, HlForOp expr)
        {
            string startLabel = HlCompilation.GetUniqueName("for_start");
            string condLabel  = HlCompilation.GetUniqueName("for_eval_condition");
            string endLabel   = HlCompilation.GetUniqueName("for_end");

            HlCompilation subFor = new HlCompilation(compilation, HlCompilation.GetUniqueName("for"));

            subFor.EmitterResult.Store(
                $".{startLabel} linker:hide"
                );                       //Unused, makes clear where the for compiler started emitting code.

            ExpressionTarget targetVal = subFor.Parse(expr.VDecl);
            ExpressionTarget target    = targetVal.MakeAddress(subFor); //Declare Variable(left)

            subFor.EmitterResult.Store($".{condLabel} linker:hide");    //Label to jumpto

            ExpressionTarget condVal = subFor.Parse(expr.Condition);    //Check Condition
            ExpressionTarget cond    = condVal.MakeAddress(subFor);     //Check Condition

            subFor.EmitterResult.Emit(
                $"BEZ",
                cond.ResultAddress,
                endLabel
                );                      //Check if Expression "Equal to Zero" => jump to end if it is

            foreach (HlExpression hlExpression in expr.ExprBody)
            {
                subFor.ReleaseTempVar(
                    subFor.Parse(hlExpression).
                    ResultAddress
                    );                  //Parse block and clean up any temp variables that were emitted.
            }

            subFor.ReleaseTempVar(subFor.Parse(expr.VInc).ResultAddress); //Compute Increment Expression

            subFor.EmitterResult.Emit($"JMP", condLabel);                 //Jump back up if we executed the body.

            subFor.EmitterResult.Store(
                $".{endLabel} linker:hide"
                );                       //End label that we jump to if we exit the loop

            subFor.ReleaseTempVar(target.ResultAddress);
            subFor.ReleaseTempVar(targetVal.ResultAddress);
            subFor.ReleaseTempVar(cond.ResultAddress);
            subFor.ReleaseTempVar(condVal.ResultAddress);

            compilation.EmitterResult.Store(subFor.EmitVariables(false));
            compilation.EmitterResult.Store(subFor.EmitterResult.Get());

            return(new ExpressionTarget());
        }
Exemplo n.º 17
0
        public static ExpressionTarget Emit(
            HlCompilation compilation,
            ExpressionTarget target,
            ExpressionTarget outputTarget)
        {
            compilation.EmitterResult.Emit(
                $"LOAD",
                outputTarget.ResultAddress,
                target.ResultAddress
                );

            return(outputTarget.Cast(target.TypeDefinition));
        }
Exemplo n.º 18
0
        public override ExpressionTarget ParseExpression(
            HlCompilation compilation,
            HlBinaryOp expr)
        {
            ExpressionTarget target = compilation.Parse(expr.Left);

            ExpressionTarget rTarget = compilation.Parse(
                expr.Right
                );

            if (SettingsManager.GetSettings <HlCompilerSettings>().OptimizeReduceExpressions&&
                IsReducable(rTarget))
            {
                uint   amount = GetPowLevel(rTarget.StaticParse());
                string tmp    = compilation.GetTempVarLoad(amount.ToString());

                ExpressionTarget taddr = target.MakeAddress(compilation);
                compilation.EmitterResult.Emit(
                    "SHR",
                    taddr.ResultAddress,
                    tmp
                    );

                compilation.ReleaseTempVar(tmp);
                compilation.ReleaseTempVar(taddr.ResultAddress);

                return(target);
            }

            string rtOrig = rTarget.ResultAddress;

            rTarget = rTarget.MakeAddress(compilation);

            string instrKey =
                target.TypeDefinition.Name == HLBaseTypeNames.s_FloatTypeName ||
                rTarget.TypeDefinition.Name == HLBaseTypeNames.s_FloatTypeName
                    ? InstructionKey + ".F"
                    : InstructionKey;

            compilation.EmitterResult.Emit(
                instrKey,
                target.ResultAddress,
                rTarget.ResultAddress
                );

            compilation.ReleaseTempVar(rTarget.ResultAddress);

            compilation.ReleaseTempVar(rtOrig);

            return(target);
        }
Exemplo n.º 19
0
        public override ExpressionTarget ParseExpression(HlCompilation compilation, HlWhileOp expr)
        {
            string startLabel = HlCompilation.GetUniqueName("while_start");
            string endLabel   = HlCompilation.GetUniqueName("while_end");

            HlCompilation whileComp = new HlCompilation(compilation, HlCompilation.GetUniqueName("while"));

            whileComp.EmitterResult.Store($".{startLabel} linker:hide");
            ExpressionTarget targetVal = whileComp.Parse(expr.Condition);

            if (SettingsManager.GetSettings <HlCompilerSettings>().OptimizeWhileConditionExpressions&&
                !targetVal.IsAddress)
            {
                if (targetVal.StaticParse() != 0)

                //If True we parse body without check and directly jump to condition
                //If False we omit the whole loop entirely
                {
                    ParseBody(whileComp, expr, startLabel, endLabel);
                }

                compilation.EmitterResult.Store(whileComp.EmitVariables(false));
                compilation.EmitterResult.Store(whileComp.EmitterResult.Get());

                return(new ExpressionTarget());
            }

            ExpressionTarget target = targetVal.MakeAddress(whileComp);   //Make sure we have an address and not a static value

            whileComp.EmitterResult.Emit($"BEZ", target.ResultAddress, endLabel);

            ParseBody(whileComp, expr, startLabel, endLabel);

            whileComp.ReleaseTempVar(target.ResultAddress);
            whileComp.ReleaseTempVar(targetVal.ResultAddress);

            compilation.EmitterResult.Store(whileComp.EmitVariables(false));
            compilation.EmitterResult.Store(whileComp.EmitterResult.Get());

            //.while_start
            //LOAD tmp_condition_var 0x00
            //<PARSE CONDITION EXPR HERE>
            //BEZ tmp_condition_var while_end
            //<PARSE BLOCK HERE>
            //JMP while_start
            //.while_end
            return(new ExpressionTarget());
        }
Exemplo n.º 20
0
        public override ExpressionTarget ParseExpression(HlCompilation compilation, HlUnaryOp expr)
        {
            ExpressionTarget target = compilation.Parse(expr.Left);

            string instrKey =
                target.TypeDefinition.Name == HLBaseTypeNames.s_FloatTypeName
                    ? "INC.F"
                    : "INC";

            compilation.EmitterResult.Emit(
                instrKey,
                target.ResultAddress
                );

            return(target);
        }
Exemplo n.º 21
0
        public override ExpressionTarget ParseExpression(
            HlCompilation compilation,
            HlBinaryOp expr,
            ExpressionTarget outputTarget)
        {
            ExpressionTarget target = compilation.Parse(expr.Left);

            ExpressionTarget rTargetVal = compilation.Parse(
                expr.Left
                );
            ExpressionTarget rTarget = rTargetVal.
                                       MakeAddress(compilation);


            if (target.ResultAddress == outputTarget.ResultAddress)
            {
                compilation.EmitterResult.Emit(
                    $"XOR",
                    target.ResultAddress,
                    rTarget.ResultAddress
                    );

                compilation.ReleaseTempVar(rTarget.ResultAddress);
                compilation.ReleaseTempVar(rTargetVal.ResultAddress);
            }
            else
            {
                compilation.EmitterResult.Emit(
                    $"XOR",
                    target.ResultAddress,
                    rTarget.ResultAddress,
                    outputTarget.ResultAddress
                    );

                compilation.ReleaseTempVar(rTarget.ResultAddress);
                compilation.ReleaseTempVar(target.ResultAddress);
                compilation.ReleaseTempVar(rTargetVal.ResultAddress);

                return(outputTarget);
            }

            return(target);
        }
Exemplo n.º 22
0
        public override ExpressionTarget ParseExpression(
            HlCompilation compilation,
            HlUnaryOp expr,
            ExpressionTarget outputTarget)
        {
            ExpressionTarget targetVal = compilation.Parse(
                expr.Left
                );
            ExpressionTarget target = targetVal.
                                      MakeAddress(compilation);

            string tmp = compilation.GetTempVar(~( uint )0);

            compilation.EmitterResult.Emit($"XOR", target.ResultAddress, tmp);

            ExpressionTarget ret = target.CopyIfNotNull(compilation, outputTarget);

            compilation.ReleaseTempVar(tmp);
            compilation.ReleaseTempVar(target.ResultAddress);

            return(ret);
        }
Exemplo n.º 23
0
        public override ExpressionTarget ParseExpression(
            HlCompilation compilation,
            HlValueOperand expr,
            ExpressionTarget outputTarget)
        {
            string type;
            string value;

            switch (expr.Value.Type)
            {
            case HlTokenType.OpCharLiteral:
                type  = HLBaseTypeNames.s_UintTypeName;
                value = $"'{expr.Value}'";

                break;

            case HlTokenType.OpDecimalNumber:
                type = HLBaseTypeNames.s_FloatTypeName;

                unsafe
                {
                    float val = float.Parse(expr.Value.ToString());
                    value = (*( uint * )&val).ToString();
                }

                break;

            default:
                type  = HLBaseTypeNames.s_UintTypeName;
                value = expr.Value.ToString();

                break;
            }

            compilation.EmitterResult.Emit($"LOAD", outputTarget.ResultAddress, value);

            return(outputTarget.Cast(compilation.TypeSystem.GetType(compilation.Root, type)));
        }
        public ExpressionTarget Compile(HlCompilation compilation, HlInvocationOp expr)
        {
            ExpressionTarget t = compilation.Parse(expr.ParameterList.First());

            ExpressionTarget ret = ReferenceExpressionCompiler.Emit(
                compilation,
                t,
                new ExpressionTarget(
                    SettingsManager.GetSettings <HlCompilerSettings>().OmitTempVarInit
                                                                             ? compilation.GetTempVar()
                                                                             : compilation.GetTempVar(0),
                    true,
                    compilation.TypeSystem.GetType(
                        compilation.Root,
                        HLBaseTypeNames.s_UintTypeName
                        )
                    )
                );

            compilation.ReleaseTempVar(t.ResultAddress);

            return(ret);
        }
        public override ExpressionTarget ParseExpression(HlCompilation compilation, HlUnaryOp expr)
        {
            ExpressionTarget target = compilation.Parse(expr.Left);

            string instrKey =
                target.TypeDefinition.Name == HLBaseTypeNames.s_FloatTypeName
                    ? "DEC.F"
                    : "DEC";

            ExpressionTarget copy = new ExpressionTarget(
                compilation.GetTempVarCopy(target.ResultAddress),
                target.IsAddress,
                target.TypeDefinition,
                target.IsPointer
                );

            compilation.EmitterResult.Emit( //Decrement Original and pass decremented copy
                instrKey,
                target.ResultAddress
                );

            compilation.ReleaseTempVar(target.ResultAddress);
            return(copy);
        }
Exemplo n.º 26
0
        public override ExpressionTarget ParseExpression(HlCompilation compilation, HlValueOperand expr)
        {
            string type;
            string value;

            switch (expr.Value.Type)
            {
            case HlTokenType.OpCharLiteral:
                type  = HLBaseTypeNames.s_UintTypeName;
                value = $"'{expr.Value}'";

                break;

            case HlTokenType.OpDecimalNumber:
                type = HLBaseTypeNames.s_FloatTypeName;

                unsafe
                {
                    float val = float.Parse(expr.Value.ToString());
                    value = (*( uint * )&val).ToString();
                }

                break;

            default:
                type  = HLBaseTypeNames.s_UintTypeName;
                value = expr.Value.ToString();

                break;
            }

            ExpressionTarget tmp =
                new ExpressionTarget(value, false, compilation.TypeSystem.GetType(compilation.Root, type));

            return(tmp);
        }
 public override uint StaticEvaluate(ExpressionTarget a, ExpressionTarget b)
 {
     return(a.StaticParse() > b.StaticParse() ? 1U : 0U);
 }
Exemplo n.º 28
0
        public override ExpressionTarget ParseExpression(
            HlCompilation compilation,
            HlVarOperand expr,
            ExpressionTarget outputTarget)
        {
            if (compilation.ConstValTypes.Contains(expr.Value.ToString()))
            {
                return(new ExpressionTarget(
                           expr.Value.ToString(),
                           true,
                           compilation.TypeSystem.GetType(
                               compilation.Root,
                               HLBaseTypeNames.s_UintTypeName
                               )
                           ).
                       CopyIfNotNull(compilation, outputTarget));
            }

            string varAddr;

            if (compilation.ContainsVariable(expr.Value.ToString()))
            {
                VariableData v = compilation.GetVariable(expr.Value.ToString());
                varAddr = v.GetFinalName();

                return(new ExpressionTarget(
                           varAddr,
                           true,
                           v.TypeDefinition,
                           !v.TypeDefinition.IsValueType ||
                           v.IsPointer
                           ).CopyIfNotNull(compilation, outputTarget));
            }

            if (compilation.FunctionMap.Contains(expr.Value.ToString()))
            {
                varAddr = expr.Value.ToString();

                return(new ExpressionTarget(varAddr, true, null));
            }

            if (compilation.TypeSystem.HasType(compilation.Root, expr.Value.ToString()))
            {
                HlTypeDefinition tdef = compilation.TypeSystem.GetType(compilation.Root, expr.Value.ToString());

                return(new ExpressionTarget("%%TYPE%%", false, tdef, false));
            }

            if (compilation.ExternalSymbols.Any(x => x.GetName() == expr.Value.ToString()))
            {
                return(new ExpressionTarget(
                           compilation.ExternalSymbols.
                           First(x => x.GetName() == expr.Value.ToString()).
                           GetFinalName(),
                           false,
                           compilation.TypeSystem.GetType(
                               compilation.Root,
                               HLBaseTypeNames.s_UintTypeName
                               )
                           ));
            }

            EventManager <ErrorEvent> .SendEvent(new HlVariableNotFoundEvent( expr.Value.ToString(), false ));

            return(new ExpressionTarget());
        }
Exemplo n.º 29
0
        public override ExpressionTarget ParseExpression(
            HlCompilation compilation,
            HlMemberAccessOp expr,
            ExpressionTarget outputTarget)
        {
            string           tmpVar;
            ExpressionTarget lType = compilation.Parse(expr.Left);

            if (lType.ResultAddress == "%%TYPE%%")
            {
                if (expr.MemberName is HlInvocationOp invoc)
                {
                    HlMemberDefinition data = null;
                    bool writeProlog        = invoc.Left.ToString() == "new";

                    if (invoc.Left.ToString() == "new" || invoc.Left.ToString() == "base")
                    {
                        data = lType.TypeDefinition.StaticConstructor;
                    }
                    else
                    {
                        data = lType.TypeDefinition.GetPrivateOrPublicMember(invoc.Left.ToString());
                    }

                    if (lType.TypeDefinition.IsAbstract &&
                        writeProlog &&
                        data == lType.TypeDefinition.StaticConstructor)
                    {
                        EventManager <ErrorEvent> .SendEvent(
                            new AbstractConstructorCallEvent( lType.TypeDefinition )
                            );
                    }

                    if (data != null && !data.IsStatic)
                    {
                        EventManager <WarningEvent> .SendEvent(
                            new StaticInstanceMemberAccessEvent(
                                lType.TypeDefinition,
                                data
                                )
                            );
                    }

                    invoc.Redirect(null, lType.TypeDefinition, data, writeProlog);

                    ExpressionTarget t = compilation.Parse(invoc, outputTarget).
                                         CopyIfNotNull(compilation, outputTarget);

                    return(t);
                }
                else
                {
                    HlMemberDefinition data =
                        lType.TypeDefinition.GetPrivateOrPublicMember(expr.MemberName.ToString());

                    string funcName =
                        lType.TypeDefinition.
                        GetFinalMemberName(data);         //$"FUN_{lType.TypeDefinition.Name}_{expr.MemberName}";

                    if (data.IsStatic && data is HlPropertyDefinition propDef)
                    {
                        funcName = compilation.GetFinalName(funcName);
                    }

                    if (!data.IsStatic)
                    {
                        EventManager <WarningEvent> .SendEvent(
                            new StaticInstanceMemberAccessEvent(
                                lType.TypeDefinition,
                                data
                                )
                            );
                    }

                    if (outputTarget.ResultAddress != null)
                    {
                        compilation.EmitterResult.Emit("LOAD", funcName, outputTarget.ResultAddress);

                        return(outputTarget);
                    }

                    return(new ExpressionTarget(
                               funcName,
                               true,
                               compilation.TypeSystem.GetType(
                                   compilation.Root,
                                   HLBaseTypeNames.s_UintTypeName
                                   ),
                               false
                               ));
                }
            }

            string containerName = expr.MemberName.ToString();

            if (expr.MemberName is HlInvocationOp inv)
            {
                if (lType.TypeDefinition.HasMember(inv.Left.ToString()) &&
                    lType.TypeDefinition.GetPrivateOrPublicMember(inv.Left.ToString()) is HlPropertyDefinition)
                {
                    containerName = inv.Left.ToString();
                }
                else
                {
                    HlMemberDefinition data = lType.TypeDefinition.GetPrivateOrPublicMember(inv.Left.ToString());

                    inv.Redirect(
                        lType.ResultAddress,
                        lType.TypeDefinition,
                        data
                        );

                    ExpressionTarget tVal = compilation.Parse(inv, outputTarget);
                    ExpressionTarget t    = tVal.CopyIfNotNull(compilation, outputTarget);


                    return(t);
                }
            }
            else if (expr.MemberName is HlArrayAccessorOp arr &&
                     lType.TypeDefinition.GetPrivateOrPublicMember(arr.Left.ToString()) is HlPropertyDefinition)
            {
                containerName = arr.Left.ToString();
            }

            uint off = HlTypeDefinition.RecursiveGetOffset(
                lType.TypeDefinition,
                0,
                0,
                containerName.Split('.')
                );

            string tmpOff = compilation.GetTempVar(off);

            if (lType.IsPointer)
            {
                tmpVar = compilation.GetTempVarCopy(lType.ResultAddress);
            }
            else
            {
                tmpVar = compilation.GetTempVarLoad(lType.ResultAddress);
            }

            compilation.EmitterResult.Emit($"ADD", tmpVar, tmpOff);

            compilation.ReleaseTempVar(tmpOff);

            HlMemberDefinition mdef = null;

            if (expr.Left.ToString() == "this")
            {
                mdef = HlTypeDefinition.RecursiveGetPrivateOrPublicMember(
                    lType.TypeDefinition,
                    0,
                    containerName.Split('.')
                    );
            }
            else
            {
                mdef = HlTypeDefinition.RecursiveGetPublicMember(
                    lType.TypeDefinition,
                    0,
                    containerName.Split('.')
                    );
            }

            if (mdef is HlPropertyDefinition pdef)
            {
                if (outputTarget.ResultAddress != null)
                {
                    compilation.EmitterResult.Emit($"DREF", tmpVar, outputTarget.ResultAddress);
                    compilation.ReleaseTempVar(tmpVar);

                    return(outputTarget);
                }

                return(new ExpressionTarget(tmpVar, true, pdef.PropertyType, true));
            }

            if (mdef is HlFunctionDefinition fdef)
            {
                if (outputTarget.ResultAddress != null)
                {
                    compilation.EmitterResult.Emit($"DREF", tmpVar, outputTarget.ResultAddress);
                    compilation.ReleaseTempVar(tmpVar);

                    return(outputTarget);
                }

                return(new ExpressionTarget(tmpVar, true, fdef.ReturnType, true));
            }

            return(new ExpressionTarget());
        }
Exemplo n.º 30
0
        public override ExpressionTarget ParseExpression(
            HlCompilation compilation,
            HlBinaryOp expr,
            ExpressionTarget outputTarget)
        {
            ExpressionTarget targetVal = compilation.Parse(
                expr.Left
                );

            ExpressionTarget rTargetVal = compilation.Parse(
                expr.Right
                );

            if (SettingsManager.GetSettings <HlCompilerSettings>().OptimizeConstExpressions&&
                !targetVal.IsAddress &&
                !rTargetVal.IsAddress)
            {
                return(new ExpressionTarget(
                           StaticEvaluate(targetVal, rTargetVal).ToString(),
                           false,
                           compilation.TypeSystem.GetType(
                               compilation.Root,
                               HLBaseTypeNames.s_UintTypeName
                               )
                           ));
            }

            ExpressionTarget target  = targetVal.MakeAddress(compilation);
            ExpressionTarget rTarget = rTargetVal.MakeAddress(compilation);

            if (target.IsPointer)
            {
                ExpressionTarget tmp = new ExpressionTarget(
                    compilation.GetTempVarDref(target.ResultAddress),
                    true,
                    compilation.TypeSystem.GetType(
                        compilation.Root,
                        HLBaseTypeNames.s_UintTypeName
                        )
                    );

                compilation.ReleaseTempVar(target.ResultAddress);
                compilation.ReleaseTempVar(targetVal.ResultAddress);
                target = tmp;
            }

            if (rTarget.IsPointer)
            {
                ExpressionTarget tmp = new ExpressionTarget(
                    compilation.GetTempVarDref(rTarget.ResultAddress),
                    true,
                    compilation.TypeSystem.GetType(
                        compilation.Root,
                        HLBaseTypeNames.s_UintTypeName
                        )
                    );

                compilation.ReleaseTempVar(rTarget.ResultAddress);
                compilation.ReleaseTempVar(rTargetVal.ResultAddress);
                rTarget = tmp;
            }

            //BNE target rTarget if_b0_fail
            //LOAD possibleTarget 0x1; True Value
            //.if_b0_fail
            string label = HlCompilation.GetUniqueName("rel_expr_comp");

            compilation.EmitterResult.Emit($"LOAD", outputTarget.ResultAddress, "1");

            compilation.EmitterResult.Store(
                $"{InstructionKey} {target.ResultAddress} {rTarget.ResultAddress} {label}"
                );

            compilation.EmitterResult.Emit($"LOAD", outputTarget.ResultAddress, "0");
            compilation.EmitterResult.Store($".{label} linker:hide");
            compilation.ReleaseTempVar(rTarget.ResultAddress);
            compilation.ReleaseTempVar(target.ResultAddress);
            compilation.ReleaseTempVar(targetVal.ResultAddress);
            compilation.ReleaseTempVar(rTargetVal.ResultAddress);

            return(outputTarget);
        }