Beispiel #1
0
        public override LLVMValueRef Emit(EmittingContext pContext)
        {
            pContext.EmitDebugLocation(this);

            var variable = pContext.AllocateVariable("string_temp", this);

            var literal = EscapeString();
            //Save length
            var length = pContext.GetArrayLength(variable);

            LLVM.BuildStore(pContext.Builder, pContext.GetInt(literal.Length), length);

            //Allocate space for our string
            LLVMValueRef dataArray;

            using (var b = new VariableDeclarationBuilder(pContext))
            {
                var charArray = LLVMTypeRef.ArrayType(SmallTypeCache.GetLLVMType(SmallTypeCache.Char, pContext), (uint)(literal.Length + 1)); //Need to allocate 1 more space for the /0
                dataArray = LLVM.BuildAlloca(b.Builder, charArray, "");
            }

            //Store the string constant in the allocated array
            var data = pContext.GetString(literal);

            LLVM.BuildStore(pContext.Builder, data, dataArray);

            //Store the allocated array in the string variable
            var dataAccess   = LLVM.BuildInBoundsGEP(pContext.Builder, dataArray, new LLVMValueRef[] { pContext.GetInt(0), pContext.GetInt(0) }, "");
            var variableData = LLVM.BuildInBoundsGEP(pContext.Builder, variable, new LLVMValueRef[] { pContext.GetInt(0), pContext.GetInt(1) }, "");

            LLVM.BuildStore(pContext.Builder, dataAccess, variableData);

            return(variable);
        }
Beispiel #2
0
        public override LLVMValueRef Emit(EmittingContext pContext)
        {
            pContext.EmitDebugLocation(this);

            var variable = pContext.AllocateVariable("array_temp", this);

            var size   = Size.Emit(pContext);
            var length = pContext.GetArrayLength(variable);

            LLVM.BuildStore(pContext.Builder, size, length);

            var data         = pContext.AllocateArrayLiteral(Type.GetElementType(), size);
            var variableData = LLVM.BuildInBoundsGEP(pContext.Builder, variable, new LLVMValueRef[] { pContext.GetInt(0), pContext.GetInt(1) }, "");

            LLVM.BuildStore(pContext.Builder, data, variableData);

            return(variable);
        }
        public override LLVMValueRef Emit(EmittingContext pContext)
        {
            pContext.EmitDebugLocation(this);

            LLVMValueRef value;

            switch (Operator)
            {
            case UnaryExpressionOperator.Not:
                value = Value.Emit(pContext);
                Utils.LlvmHelper.LoadIfPointer(ref value, pContext);
                return(LLVM.BuildNot(pContext.Builder, value, ""));

            case UnaryExpressionOperator.Negative:
                value = Value.Emit(pContext);
                Utils.LlvmHelper.LoadIfPointer(ref value, pContext);
                return(LLVM.BuildNeg(pContext.Builder, value, ""));

            case UnaryExpressionOperator.Length:
                var arr = Value.Emit(pContext);
                return(LLVM.BuildLoad(pContext.Builder, pContext.GetArrayLength(arr), ""));

            case UnaryExpressionOperator.PreIncrement:
            case UnaryExpressionOperator.PreDecrement:
            case UnaryExpressionOperator.PostIncrement:
            case UnaryExpressionOperator.PostDecrement:
                var variable = (IdentifierSyntax)Value;
                variable.DoNotLoad = true;
                LLVMValueRef v = variable.Emit(pContext);

                BinaryExpressionOperator op = BinaryExpressionOperator.Equals;
                switch (Operator)
                {
                case UnaryExpressionOperator.PostDecrement:
                case UnaryExpressionOperator.PreDecrement:
                    op = BinaryExpressionOperator.Subtraction;
                    break;

                case UnaryExpressionOperator.PostIncrement:
                case UnaryExpressionOperator.PreIncrement:
                    op = BinaryExpressionOperator.Addition;
                    break;
                }

                value = BinaryExpressionSyntax.EmitOperator(v, op, pContext.GetInt(1), pContext);

                //Post unary we want to return the original variable value
                if (Operator == UnaryExpressionOperator.PostIncrement || Operator == UnaryExpressionOperator.PostDecrement)
                {
                    //Save the old value to a temp variable that we will return
                    var          temp      = pContext.AllocateVariable("<temp_unary>", Value);
                    LLVMValueRef tempValue = Utils.LlvmHelper.IsPointer(v) ? LLVM.BuildLoad(pContext.Builder, v, "") : v;
                    LLVM.BuildStore(pContext.Builder, tempValue, temp);

                    //Increment the variable
                    Utils.LlvmHelper.LoadIfPointer(ref value, pContext);
                    if (Value.SyntaxType == SyntaxType.Identifier || Value.SyntaxType == SyntaxType.MemberAccess)
                    {
                        LLVM.BuildStore(pContext.Builder, value, v);
                    }

                    return(temp);
                }

                //If it isn't a variable we cane save we need to return the addition
                if (Value.SyntaxType == SyntaxType.Identifier || Value.SyntaxType == SyntaxType.MemberAccess)
                {
                    LLVM.BuildStore(pContext.Builder, value, v);
                }
                return(value);

            default:
                throw new NotSupportedException();
            }
        }