Exemple #1
0
void Value::toLLVMValue(Builder *builder) {
	if (isConstant()) {
		mValue = builder->llvmValue(constant());
		mConstant = ConstantValue();
		mType = tNormalValue;
	}
}
Value NullValueType::generateOperation(Builder *builder, int opType, const Value &operand1, const Value &operand2, OperationFlags &operationFlags) const {
	assert(operand1.valueType() == this);
	switch (opType) {
		case ast::ExpressionNode::opEqual:
			if (operand2.isConstant()) {
				const ConstantValue &val = operand2.constant();
				switch (val.type()) {
					case ConstantValue::Byte:
					case ConstantValue::Short:
					case ConstantValue::Integer:
					case ConstantValue::Boolean:
						return Value(ConstantValue::equal(ConstantValue(0), val, operationFlags), mRuntime);
					case ConstantValue::Float:
						return Value(ConstantValue::equal(ConstantValue(0.0), val, operationFlags), mRuntime);
					case ConstantValue::String:
						return Value(ConstantValue::equal(ConstantValue(""), val, operationFlags), mRuntime);
					case ConstantValue::Null:
						return Value(ConstantValue(true), mRuntime);
					default:
						break;
				}
				break;
			}

			return operand2.valueType()->generateOperation(builder, opType, builder->defaultValue(operand2.valueType()), operand2, operationFlags);
		case ast::ExpressionNode::opNotEqual:
			if (operand2.isConstant()) {
				const ConstantValue &val = operand2.constant();
				switch (val.type()) {
					case ConstantValue::Byte:
					case ConstantValue::Short:
					case ConstantValue::Integer:
					case ConstantValue::Boolean:
						return Value(ConstantValue::notEqual(ConstantValue(0), val, operationFlags), mRuntime);
					case ConstantValue::Float:
						return Value(ConstantValue::notEqual(ConstantValue(0.0), val, operationFlags), mRuntime);
					case ConstantValue::String:
						return Value(ConstantValue::notEqual(ConstantValue(""), val, operationFlags), mRuntime);
					case ConstantValue::Null:
						return Value(ConstantValue(true), mRuntime);
					default:
						break;
				}
				break;
			}

			return operand2.valueType()->generateOperation(builder, opType, builder->defaultValue(operand2.valueType()), operand2, operationFlags);
	}
	operationFlags |= OperationFlag::NoSuchOperation;
	return Value();
}
Exemple #3
0
ScriptContext::ScriptContext() : m_VariableIndex(0) , m_DataIndex(0) {
	m_Functions.push_back(Function("+",OP_ADD,12,2,scriptAddOperation));
	m_Functions.push_back(Function("*",OP_MUL,16,2,scriptMul));
	//m_Functions.push_back(Function("/",OP_DIV,16,2));
	//m_Functions.push_back(Function("-",OP_SUB,12,2));
	//m_Functions.push_back(Function("sin",OP_SIN,17,1));
	//m_Functions.push_back(Function("cos",OP_COS,17,1));
	m_Functions.push_back(Function("=",OP_ASSIGN,1,1,scriptAssign));
	m_Functions.push_back(Function("random",OP_RND,20,2,scriptRandom));
	m_Functions.push_back(Function("print",OP_RND,19,1,scriptPrint));
	m_Functions.push_back(Function("vector2",OP_NEW_VEC2,20,2,scriptNewVec2));

	m_Constants.push_back(ConstantValue("PI",3.14159265359f));

	m_Declarations.push_back(TypeDeclaration("int",DT_INT));
	m_Declarations.push_back(TypeDeclaration("float",DT_FLOAT));
	m_Declarations.push_back(TypeDeclaration("vec2",DT_VEC2));
	m_Declarations.push_back(TypeDeclaration("vec3",DT_VEC3));
	m_Declarations.push_back(TypeDeclaration("color",DT_COLOR));
}
Exemple #4
0
void TypeAnalyzer::analyze(const BinaryOperator *binary) {
    /* Be careful: these pointers become kinda invalid after doing unionSet(). */
    Type *type = types().getType(binary);
    Type *leftType = types().getType(binary->left());
    Type *rightType = types().getType(binary->right());

    const dflow::Value *value = dataflow().getValue(binary->left());
    const dflow::Value *leftValue = dataflow().getValue(binary->left());
    const dflow::Value *rightValue = dataflow().getValue(binary->right());

    switch (binary->operatorKind()) {
    case BinaryOperator::ADD:
        if (leftType->isInteger() && rightType->isInteger()) {
            type->makeInteger();
        }
        if ((leftType->isInteger() && rightType->isPointer()) ||
                (leftType->isPointer() && rightType->isInteger())) {
            type->makePointer();
        }
        if (type->isInteger()) {
            leftType->makeInteger();
            rightType->makeInteger();
        }
        if (type->isPointer()) {
            if (leftType->isInteger()) {
                rightType->makePointer();
            }
            if (rightType->isInteger()) {
                leftType->makePointer();
            }
            if (leftType->isPointer()) {
                rightType->makeInteger();
            }
            if (rightType->isPointer()) {
                leftType->makeInteger();
            }
            if (!leftType->isPointer() && !rightType->isPointer()) {
                if (leftValue->isMultiplication()) {
                    rightType->makePointer();
                } else if (rightValue->isMultiplication()) {
                    leftType->makePointer();
                } else if (leftValue->isConstant()) {
                    if (leftValue->constantValue().value() < 4096) {
                        leftType->makeInteger();
                    } else {
                        leftType->makePointer();
                    }
                } else if (rightValue->isConstant()) {
                    if (rightValue->constantValue().value() < 4096) {
                        rightType->makeInteger();
                    } else {
                        rightType->makePointer();
                    }
                }
            }
        }

        if (leftType->isUnsigned() || rightType->isUnsigned()) {
            type->makeUnsigned();
        }
        if (leftType->isSigned() && rightType->isSigned()) {
            type->makeSigned();
        }
        if (type->isSigned()) {
            leftType->makeSigned();
            rightType->makeSigned();
        }
        if (type->isUnsigned()) {
            if (leftType->isSigned()) {
                rightType->makeUnsigned();
            }
            if (rightType->isSigned()) {
                rightType->makeUnsigned();
            }
        }

        if (rightValue->isConstant()) {
            if (type == leftType) {
                type->updateFactor(rightValue->constantValue().absoluteValue());
            } else {
#ifdef NC_STRUCT_RECOVERY
                if (!value->isStackOffset()) {
                    leftType->addOffset(rightValue->constantValue().signedValue(), type);
                }
#endif
            }
        }
        if (leftValue->isConstant()) {
            if (type == rightType) {
                type->updateFactor(leftValue->constantValue().absoluteValue());
            } else {
#ifdef NC_STRUCT_RECOVERY
                if (!value->isStackOffset()) {
                    rightType->addOffset(leftValue->constantValue().signedValue(), type);
                }
#endif
            }
        }

        if (leftType->isPointer() && rightValue->isMultiplication()) {
            type->makePointer(leftType->pointee());
        }
        if (rightType->isPointer() && leftValue->isMultiplication()) {
            type->makePointer(rightType->pointee());
        }
        break;

    case BinaryOperator::SUB:
        if (leftType->isInteger() && rightType->isInteger()) {
            type->makeInteger();
        }
        if (leftType->isPointer() && rightType->isInteger()) {
            type->makePointer();
        }
        if (type->isPointer()) {
            leftType->makePointer();
            rightType->makeInteger();
        }

        if (leftType->isUnsigned() || rightType->isUnsigned()) {
            type->makeUnsigned();
        }
        if (leftType->isSigned() && rightType->isSigned()) {
            type->makeSigned();
        }
        if (type->isSigned()) {
            leftType->makeSigned();
            rightType->makeSigned();
        }
        if (type->isUnsigned()) {
            if (leftType->isSigned()) {
                rightType->makeUnsigned();
            }
            if (rightType->isSigned()) {
                rightType->makeUnsigned();
            }
        }

        if (rightValue->isConstant()) {
            if (type == leftType) {
                type->updateFactor(rightValue->constantValue().absoluteValue());
            } else {
#ifdef NC_STRUCT_RECOVERY
                if (!value->isStackOffset()) {
                    leftType->addOffset(-rightValue->constantValue().signedValue(), type);
                }
#endif
            }
        }

        if (leftType->isPointer() && rightValue->isMultiplication()) {
            type->makePointer(leftType->pointee());
        }
        break;

    case BinaryOperator::MUL:
        type->makeInteger();
        leftType->makeInteger();
        rightType->makeInteger();

        if (leftType->isUnsigned() || rightType->isUnsigned()) {
            type->makeUnsigned();
        }
        if (leftType->isSigned() && rightType->isSigned()) {
            type->makeSigned();
        }
        if (type->isSigned()) {
            leftType->makeSigned();
            rightType->makeSigned();
        }
        if (type->isUnsigned()) {
            if (leftType->isSigned()) {
                rightType->makeUnsigned();
            }
            if (rightType->isSigned()) {
                rightType->makeUnsigned();
            }
        }

        if (rightValue->isConstant()) {
            type->updateFactor(leftType->factor() * rightValue->constantValue().value());
        }
        if (leftValue->isConstant()) {
            type->updateFactor(rightType->factor() * leftValue->constantValue().value());
        }
        break;

    case BinaryOperator::SIGNED_DIV:
        leftType->makeInteger();
        rightType->makeInteger();
        type->makeInteger();

        leftType->makeSigned();
        rightType->makeSigned();
        type->makeSigned();
        break;

    case BinaryOperator::UNSIGNED_DIV:
        type->makeInteger();
        leftType->makeInteger();
        rightType->makeInteger();

        if (leftType->isSigned()) {
            rightType->makeUnsigned();
        }
        if (rightType->isUnsigned()) {
            leftType->makeSigned();
        }
        type->makeUnsigned();
        break;

    case BinaryOperator::SIGNED_REM:
        leftType->makeInteger();
        rightType->makeInteger();
        type->makeInteger();

        leftType->makeSigned();
        rightType->makeSigned();
        type->makeSigned();
        break;

    case BinaryOperator::UNSIGNED_REM:
        type->makeInteger();
        leftType->makeInteger();
        rightType->makeInteger();

        if (leftType->isSigned()) {
            rightType->makeUnsigned();
        }
        if (rightType->isUnsigned()) {
            leftType->makeSigned();
        }
        type->makeUnsigned();
        break;

    case BinaryOperator::BITWISE_AND: /* FALLTHROUGH */
    case BinaryOperator::LOGICAL_AND: /* FALLTHROUGH */
    case BinaryOperator::BITWISE_OR: /* FALLTHROUGH */
    case BinaryOperator::LOGICAL_OR: /* FALLTHROUGH */
    case BinaryOperator::BITWISE_XOR:
        leftType->makeInteger();
        rightType->makeInteger();
        type->makeInteger();

        leftType->makeUnsigned();
        rightType->makeUnsigned();
        type->makeUnsigned();
        break;

    case BinaryOperator::SHL:
        leftType->makeInteger();
        rightType->makeInteger();
        type->makeInteger();

        rightType->makeUnsigned();
        if (leftType->isSigned()) {
            type->makeSigned();
        }
        if (leftType->isUnsigned()) {
            type->makeUnsigned();
        }
        if (type->isSigned()) {
            leftType->makeSigned();
        }
        if (type->isUnsigned()) {
            leftType->makeUnsigned();
        }

        if (rightValue->isConstant()) {
            type->updateFactor(leftType->factor() * (ConstantValue(1) << rightValue->constantValue().value()));
        }
        break;

    case BinaryOperator::SHR:
        leftType->makeInteger();
        rightType->makeInteger();
        type->makeInteger();

        leftType->makeUnsigned();
        type->makeUnsigned();
        break;

    case BinaryOperator::SAR:
        leftType->makeInteger();
        rightType->makeInteger();
        type->makeInteger();

        leftType->makeSigned();
        type->makeSigned();
        break;

    case BinaryOperator::EQUAL:
        leftType->unionSet(rightType);
        break;

    case BinaryOperator::SIGNED_LESS: /* FALLTHROUGH */
    case BinaryOperator::SIGNED_LESS_OR_EQUAL: /* FALLTHROUGH */
    case BinaryOperator::SIGNED_GREATER: /* FALLTHROUGH */
    case BinaryOperator::SIGNED_GREATER_OR_EQUAL:
        leftType->makeSigned();
        rightType->makeSigned();
        leftType->unionSet(rightType);
        break;

    case BinaryOperator::UNSIGNED_LESS: /* FALLTHROUGH */
    case BinaryOperator::UNSIGNED_LESS_OR_EQUAL: /* FALLTHROUGH */
    case BinaryOperator::UNSIGNED_GREATER: /* FALLTHROUGH */
    case BinaryOperator::UNSIGNED_GREATER_OR_EQUAL:
        if (rightType->isSigned()) {
            leftType->makeUnsigned();
        } else if (leftType->isSigned()) {
            rightType->makeUnsigned();
        } else {
            leftType->makeUnsigned();
            rightType->makeUnsigned();
        }
        leftType->unionSet(rightType);
        break;

    default:
        unreachable();
        break;
    }
}