示例#1
0
void CodeGenVisitor::JIT(Expression* e) {
	StatementList* sl = new StatementList();
	sl->addStatement(new ReturnStatement(e));
	FunctionDefinition* fd = new FunctionDefinition(Type::INT, "", new ParameterList(), sl);

	value_ = 0;
	fd->accept(this);

	if (!value_) {
		delete fd;
		throw "error evaluating expression";
	}

	llvm::Function* f = dynamic_cast<llvm::Function*>(value_);

	void* fPtr = ee_->getPointerToFunction(f);

	// some casting ... because we like magic
	int (*fP)() = (int (*)())(intptr_t)fPtr;

	std::cout << "Evaluated to: " << fP() << std::endl;

	// throw it away
	f->eraseFromParent();
}
示例#2
0
void Compiler::appendBaseConstructor(FunctionDefinition const& _constructor)
{
	CompilerContext::LocationSetter locationSetter(m_context, _constructor);
	FunctionType constructorType(_constructor);
	if (!constructorType.getParameterTypes().empty())
	{
		solAssert(m_baseArguments.count(&_constructor), "");
		std::vector<ASTPointer<Expression>> const* arguments = m_baseArguments[&_constructor];
		solAssert(arguments, "");
		for (unsigned i = 0; i < arguments->size(); ++i)
			compileExpression(*(arguments->at(i)), constructorType.getParameterTypes()[i]);
	}
	_constructor.accept(*this);
}
示例#3
0
void Compiler::appendConstructor(FunctionDefinition const& _constructor)
{
	CompilerContext::LocationSetter locationSetter(m_context, _constructor);
	// copy constructor arguments from code to memory and then to stack, they are supplied after the actual program
	if (!_constructor.getParameters().empty())
	{
		unsigned argumentSize = 0;
		for (ASTPointer<VariableDeclaration> const& var: _constructor.getParameters())
			if (var->getType()->isDynamicallySized())
			{
				argumentSize = 0;
				break;
			}
			else
				argumentSize += var->getType()->getCalldataEncodedSize();

		CompilerUtils(m_context).fetchFreeMemoryPointer();
		if (argumentSize == 0)
		{
			// argument size is dynamic, use CODESIZE to determine it
			m_context.appendProgramSize(); // program itself
			// CODESIZE is program plus manually added arguments
			m_context << eth::Instruction::CODESIZE << eth::Instruction::SUB;
		}
		else
			m_context << u256(argumentSize);
		// stack: <memptr> <argument size>
		m_context << eth::Instruction::DUP1;
		m_context.appendProgramSize();
		m_context << eth::Instruction::DUP4 << eth::Instruction::CODECOPY;
		m_context << eth::Instruction::ADD;
		CompilerUtils(m_context).storeFreeMemoryPointer();
		appendCalldataUnpacker(
			FunctionType(_constructor).getParameterTypes(),
			true,
			CompilerUtils::freeMemoryPointer + 0x20
		);
	}
	_constructor.accept(*this);
}