Merge
This commit is contained in:
commit
1e535a160d
40
src/pim/Exceptions.h
Normal file
40
src/pim/Exceptions.h
Normal file
@ -0,0 +1,40 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <cstring>
|
||||||
|
#include <string>
|
||||||
|
#include "Token.h"
|
||||||
|
|
||||||
|
namespace pim
|
||||||
|
{
|
||||||
|
namespace compiler {
|
||||||
|
class ParserExpectException: public std::exception
|
||||||
|
{
|
||||||
|
char * error;
|
||||||
|
public:
|
||||||
|
ParserExpectException(Token token, int expectingSymbol) {
|
||||||
|
error = strdup(std::string("Expecting " + Token::SymbolNames[expectingSymbol] + " got " + token.Source).c_str());
|
||||||
|
}
|
||||||
|
ParserExpectException(Token token, std::string expectingString) {
|
||||||
|
error = strdup(std::string("Expecting " + expectingString + " got " + token.Source).c_str());
|
||||||
|
}
|
||||||
|
const char * what() const throw()
|
||||||
|
{
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
~ParserExpectException() throw() {};
|
||||||
|
};
|
||||||
|
class TypeException: public std::exception
|
||||||
|
{
|
||||||
|
char * error;
|
||||||
|
public:
|
||||||
|
TypeException(int type, int expectingType) {
|
||||||
|
error = strdup(std::string("Expecting a particular type, got a different type").c_str());
|
||||||
|
}
|
||||||
|
const char * what() const throw()
|
||||||
|
{
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
~TypeException() throw() {};
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
@ -4,11 +4,13 @@
|
|||||||
#include "Format.h"
|
#include "Format.h"
|
||||||
#include "Generator.h"
|
#include "Generator.h"
|
||||||
#include "Opcodes.h"
|
#include "Opcodes.h"
|
||||||
|
#include "Exceptions.h"
|
||||||
namespace pim
|
namespace pim
|
||||||
{
|
{
|
||||||
namespace compiler
|
namespace compiler
|
||||||
{
|
{
|
||||||
Generator::Generator() :
|
Generator::Generator() :
|
||||||
|
typeStack(),
|
||||||
output(std::cout),
|
output(std::cout),
|
||||||
labelCounter(0),
|
labelCounter(0),
|
||||||
programCounter(0)
|
programCounter(0)
|
||||||
@ -16,6 +18,10 @@ namespace pim
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Generator::~Generator()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
void Generator::defineLabel(std::string label)
|
void Generator::defineLabel(std::string label)
|
||||||
{
|
{
|
||||||
Label newLabel;
|
Label newLabel;
|
||||||
@ -313,6 +319,47 @@ namespace pim
|
|||||||
variableType = type;
|
variableType = type;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Generator::PushType(int type)
|
||||||
|
{
|
||||||
|
typeStack.push(type);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Generator::pushType(int type)
|
||||||
|
{
|
||||||
|
typeStack.push(type);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Generator::popType(int count)
|
||||||
|
{
|
||||||
|
while(count--)
|
||||||
|
{
|
||||||
|
typeStack.pop();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Generator::AssureType(int type)
|
||||||
|
{
|
||||||
|
int otherType = typeStack.top();
|
||||||
|
|
||||||
|
if(otherType != type)
|
||||||
|
{
|
||||||
|
if(otherType == DataType::Integer && type == DataType::Float)
|
||||||
|
{
|
||||||
|
ToFloat();
|
||||||
|
}
|
||||||
|
else if(otherType == DataType::Float && type == DataType::Integer)
|
||||||
|
{
|
||||||
|
ToInteger();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Generator::ForceType(int type)
|
||||||
|
{
|
||||||
|
if(typeStack.top() != type)
|
||||||
|
throw new TypeException(typeStack.top(), type);
|
||||||
|
}
|
||||||
|
|
||||||
void Generator::ScopeVariable(std::string label)
|
void Generator::ScopeVariable(std::string label)
|
||||||
{
|
{
|
||||||
currentScope->Definitions.push_back(Definition(label, variableType, currentScope->LocalFrameSize, currentScope));
|
currentScope->Definitions.push_back(Definition(label, variableType, currentScope->LocalFrameSize, currentScope));
|
||||||
@ -329,8 +376,11 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::LoadVariable(std::string label)
|
void Generator::LoadVariable(std::string label)
|
||||||
{
|
{
|
||||||
writeOpcode(Opcode::Load);
|
|
||||||
Definition d = currentScope->GetDefinition(label);
|
Definition d = currentScope->GetDefinition(label);
|
||||||
|
|
||||||
|
pushType(d.Type);
|
||||||
|
writeOpcode(Opcode::Load);
|
||||||
|
|
||||||
writeConstant(d.StackPosition+(currentScope->FrameSize-d.MyScope->FrameSize));
|
writeConstant(d.StackPosition+(currentScope->FrameSize-d.MyScope->FrameSize));
|
||||||
|
|
||||||
output << "load " << label << std::endl;
|
output << "load " << label << std::endl;
|
||||||
@ -338,8 +388,12 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::StoreVariable(std::string label)
|
void Generator::StoreVariable(std::string label)
|
||||||
{
|
{
|
||||||
writeOpcode(Opcode::Store);
|
|
||||||
Definition d = currentScope->GetDefinition(label);
|
Definition d = currentScope->GetDefinition(label);
|
||||||
|
AssureType(d.Type);
|
||||||
|
popType(1);
|
||||||
|
|
||||||
|
writeOpcode(Opcode::Store);
|
||||||
|
|
||||||
writeConstant(d.StackPosition+(currentScope->FrameSize-d.MyScope->FrameSize));
|
writeConstant(d.StackPosition+(currentScope->FrameSize-d.MyScope->FrameSize));
|
||||||
//writeConstantPlaceholderOffset(currentScope->GetDefinition(label).StackPosition, &(currentScope->OldFrameSize));
|
//writeConstantPlaceholderOffset(currentScope->GetDefinition(label).StackPosition, &(currentScope->OldFrameSize));
|
||||||
//writeConstant(currentScope->GetDefinition(label).StackPosition);
|
//writeConstant(currentScope->GetDefinition(label).StackPosition);
|
||||||
@ -349,6 +403,7 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::RTConstant(std::string name)
|
void Generator::RTConstant(std::string name)
|
||||||
{
|
{
|
||||||
|
pushType(DataType::Integer);
|
||||||
writeOpcode(Opcode::Constant);
|
writeOpcode(Opcode::Constant);
|
||||||
writeConstantMacroPlaceholder(name);
|
writeConstantMacroPlaceholder(name);
|
||||||
|
|
||||||
@ -357,6 +412,7 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::Constant(std::string constant)
|
void Generator::Constant(std::string constant)
|
||||||
{
|
{
|
||||||
|
pushType(DataType::Integer);
|
||||||
writeOpcode(Opcode::Constant);
|
writeOpcode(Opcode::Constant);
|
||||||
writeConstant(constant);
|
writeConstant(constant);
|
||||||
|
|
||||||
@ -374,6 +430,7 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::Discard()
|
void Generator::Discard()
|
||||||
{
|
{
|
||||||
|
popType(1);
|
||||||
writeOpcode(Opcode::Discard);
|
writeOpcode(Opcode::Discard);
|
||||||
|
|
||||||
output << "discard" << std::endl;
|
output << "discard" << std::endl;
|
||||||
@ -381,6 +438,7 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::Duplicate()
|
void Generator::Duplicate()
|
||||||
{
|
{
|
||||||
|
pushType(typeStack.top());
|
||||||
writeOpcode(Opcode::Duplicate);
|
writeOpcode(Opcode::Duplicate);
|
||||||
|
|
||||||
output << "duplicate" << std::endl;
|
output << "duplicate" << std::endl;
|
||||||
@ -388,6 +446,8 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::Add()
|
void Generator::Add()
|
||||||
{
|
{
|
||||||
|
popType(2);
|
||||||
|
pushType(DataType::Integer);
|
||||||
writeOpcode(Opcode::Add);
|
writeOpcode(Opcode::Add);
|
||||||
|
|
||||||
output << "add" << std::endl;
|
output << "add" << std::endl;
|
||||||
@ -395,6 +455,8 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::Subtract()
|
void Generator::Subtract()
|
||||||
{
|
{
|
||||||
|
popType(2);
|
||||||
|
pushType(DataType::Integer);
|
||||||
writeOpcode(Opcode::Subtract);
|
writeOpcode(Opcode::Subtract);
|
||||||
|
|
||||||
output << "sub" << std::endl;
|
output << "sub" << std::endl;
|
||||||
@ -402,13 +464,36 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::Multiply()
|
void Generator::Multiply()
|
||||||
{
|
{
|
||||||
|
popType(2);
|
||||||
|
pushType(DataType::Integer);
|
||||||
writeOpcode(Opcode::Multiply);
|
writeOpcode(Opcode::Multiply);
|
||||||
|
|
||||||
|
|
||||||
output << "mul" << std::endl;
|
output << "mul" << std::endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Generator::ToInteger()
|
||||||
|
{
|
||||||
|
popType(1);
|
||||||
|
pushType(DataType::Integer);
|
||||||
|
writeOpcode(Opcode::ToInteger);
|
||||||
|
|
||||||
|
output << "ftoi" << std::endl;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Generator::ToFloat()
|
||||||
|
{
|
||||||
|
popType(1);
|
||||||
|
pushType(DataType::Float);
|
||||||
|
writeOpcode(Opcode::ToFloat);
|
||||||
|
|
||||||
|
output << "itof" << std::endl;
|
||||||
|
}
|
||||||
|
|
||||||
void Generator::Divide()
|
void Generator::Divide()
|
||||||
{
|
{
|
||||||
|
popType(2);
|
||||||
|
pushType(DataType::Integer);
|
||||||
writeOpcode(Opcode::Divide);
|
writeOpcode(Opcode::Divide);
|
||||||
|
|
||||||
output << "div" << std::endl;
|
output << "div" << std::endl;
|
||||||
@ -416,6 +501,8 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::Modulus()
|
void Generator::Modulus()
|
||||||
{
|
{
|
||||||
|
popType(2);
|
||||||
|
pushType(DataType::Integer);
|
||||||
writeOpcode(Opcode::Modulus);
|
writeOpcode(Opcode::Modulus);
|
||||||
|
|
||||||
output << "add" << std::endl;
|
output << "add" << std::endl;
|
||||||
@ -444,6 +531,8 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::GetParticle()
|
void Generator::GetParticle()
|
||||||
{
|
{
|
||||||
|
popType(2);
|
||||||
|
pushType(DataType::Integer);
|
||||||
writeOpcode(Opcode::Get);
|
writeOpcode(Opcode::Get);
|
||||||
|
|
||||||
output << "getpart" << std::endl;
|
output << "getpart" << std::endl;
|
||||||
@ -451,6 +540,9 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::GetPosition()
|
void Generator::GetPosition()
|
||||||
{
|
{
|
||||||
|
popType(1);
|
||||||
|
pushType(DataType::Integer);
|
||||||
|
pushType(DataType::Integer);
|
||||||
writeOpcode(Opcode::Position);
|
writeOpcode(Opcode::Position);
|
||||||
|
|
||||||
output << "getpos" << std::endl;
|
output << "getpos" << std::endl;
|
||||||
@ -458,6 +550,7 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::KillParticle()
|
void Generator::KillParticle()
|
||||||
{
|
{
|
||||||
|
popType(1);
|
||||||
writeOpcode(Opcode::Kill);
|
writeOpcode(Opcode::Kill);
|
||||||
|
|
||||||
output << "kill" << std::endl;
|
output << "kill" << std::endl;
|
||||||
@ -465,6 +558,8 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::LoadProperty(std::string property)
|
void Generator::LoadProperty(std::string property)
|
||||||
{
|
{
|
||||||
|
popType(1);
|
||||||
|
pushType(DataType::Integer);
|
||||||
writeOpcode(Opcode::LoadProperty);
|
writeOpcode(Opcode::LoadProperty);
|
||||||
writeConstantPropertyPlaceholder(property);
|
writeConstantPropertyPlaceholder(property);
|
||||||
|
|
||||||
@ -473,25 +568,19 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::StoreProperty(std::string property)
|
void Generator::StoreProperty(std::string property)
|
||||||
{
|
{
|
||||||
|
ForceType(DataType::Integer); //Ensure particle ID is an integer
|
||||||
|
popType(1); //Use particle ID
|
||||||
|
popType(1);
|
||||||
|
|
||||||
writeOpcode(Opcode::StoreProperty);
|
writeOpcode(Opcode::StoreProperty);
|
||||||
writeConstantPropertyPlaceholder(property);
|
writeConstantPropertyPlaceholder(property);
|
||||||
|
|
||||||
output << "storeprop " << property << std::endl;
|
output << "storeprop " << property << std::endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Generator::IntegerToDecimal()
|
|
||||||
{
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
void Generator::DecimalToInteger()
|
|
||||||
{
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void Generator::JumpEqual(std::string label)
|
void Generator::JumpEqual(std::string label)
|
||||||
{
|
{
|
||||||
|
popType(2);
|
||||||
writeOpcode(Opcode::JumpEqual);
|
writeOpcode(Opcode::JumpEqual);
|
||||||
writeConstantPlaceholder(label);
|
writeConstantPlaceholder(label);
|
||||||
|
|
||||||
@ -500,6 +589,7 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::JumpNotEqual(std::string label)
|
void Generator::JumpNotEqual(std::string label)
|
||||||
{
|
{
|
||||||
|
popType(2);
|
||||||
writeOpcode(Opcode::JumpNotEqual);
|
writeOpcode(Opcode::JumpNotEqual);
|
||||||
writeConstantPlaceholder(label);
|
writeConstantPlaceholder(label);
|
||||||
|
|
||||||
@ -508,6 +598,7 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::JumpGreater(std::string label)
|
void Generator::JumpGreater(std::string label)
|
||||||
{
|
{
|
||||||
|
popType(2);
|
||||||
writeOpcode(Opcode::JumpGreater);
|
writeOpcode(Opcode::JumpGreater);
|
||||||
writeConstantPlaceholder(label);
|
writeConstantPlaceholder(label);
|
||||||
|
|
||||||
@ -516,6 +607,7 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::JumpGreaterEqual(std::string label)
|
void Generator::JumpGreaterEqual(std::string label)
|
||||||
{
|
{
|
||||||
|
popType(2);
|
||||||
writeOpcode(Opcode::JumpGreaterEqual);
|
writeOpcode(Opcode::JumpGreaterEqual);
|
||||||
writeConstantPlaceholder(label);
|
writeConstantPlaceholder(label);
|
||||||
|
|
||||||
@ -524,6 +616,7 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::JumpLess(std::string label)
|
void Generator::JumpLess(std::string label)
|
||||||
{
|
{
|
||||||
|
popType(2);
|
||||||
writeOpcode(Opcode::JumpLess);
|
writeOpcode(Opcode::JumpLess);
|
||||||
writeConstantPlaceholder(label);
|
writeConstantPlaceholder(label);
|
||||||
|
|
||||||
@ -532,6 +625,7 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::JumpLessEqual(std::string label)
|
void Generator::JumpLessEqual(std::string label)
|
||||||
{
|
{
|
||||||
|
popType(2);
|
||||||
writeOpcode(Opcode::JumpLessEqual);
|
writeOpcode(Opcode::JumpLessEqual);
|
||||||
writeConstantPlaceholder(label);
|
writeConstantPlaceholder(label);
|
||||||
|
|
||||||
@ -540,6 +634,7 @@ namespace pim
|
|||||||
|
|
||||||
void Generator::Jump(std::string label)
|
void Generator::Jump(std::string label)
|
||||||
{
|
{
|
||||||
|
popType(2);
|
||||||
writeOpcode(Opcode::Jump);
|
writeOpcode(Opcode::Jump);
|
||||||
writeConstantPlaceholder(label);
|
writeConstantPlaceholder(label);
|
||||||
|
|
||||||
|
@ -5,6 +5,7 @@
|
|||||||
#include <stack>
|
#include <stack>
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include "Token.h"
|
#include "Token.h"
|
||||||
|
#include "Types.h"
|
||||||
namespace pim
|
namespace pim
|
||||||
{
|
{
|
||||||
namespace compiler
|
namespace compiler
|
||||||
@ -36,10 +37,6 @@ namespace pim
|
|||||||
}
|
}
|
||||||
~SymbolNotFoundException() throw() {};
|
~SymbolNotFoundException() throw() {};
|
||||||
};
|
};
|
||||||
class Type
|
|
||||||
{
|
|
||||||
enum { Integer = Token::IntegerSymbol, Decimal = Token::DecimalSymbol };
|
|
||||||
};
|
|
||||||
class Scope;
|
class Scope;
|
||||||
class Definition
|
class Definition
|
||||||
{
|
{
|
||||||
@ -93,6 +90,7 @@ namespace pim
|
|||||||
class Generator
|
class Generator
|
||||||
{
|
{
|
||||||
int variableType;
|
int variableType;
|
||||||
|
std::stack<int> typeStack;
|
||||||
std::stack<Scope*> scopes;
|
std::stack<Scope*> scopes;
|
||||||
Scope * currentScope;
|
Scope * currentScope;
|
||||||
std::ostream & output;
|
std::ostream & output;
|
||||||
@ -118,6 +116,9 @@ namespace pim
|
|||||||
|
|
||||||
std::vector<unsigned char> program;
|
std::vector<unsigned char> program;
|
||||||
|
|
||||||
|
void pushType(int type);
|
||||||
|
void popType(int count);
|
||||||
|
|
||||||
void defineLabel(std::string label);
|
void defineLabel(std::string label);
|
||||||
void writeOpcode(int opcode);
|
void writeOpcode(int opcode);
|
||||||
void writeConstant(std::string constant);
|
void writeConstant(std::string constant);
|
||||||
@ -130,11 +131,15 @@ namespace pim
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
Generator();
|
Generator();
|
||||||
|
virtual ~Generator();
|
||||||
|
|
||||||
std::vector<unsigned char> Finish();
|
std::vector<unsigned char> Finish();
|
||||||
|
|
||||||
std::string UniqueLabel(std::string prefix);
|
std::string UniqueLabel(std::string prefix);
|
||||||
|
|
||||||
|
void AssureType(int type);
|
||||||
|
void ForceType(int type);
|
||||||
|
|
||||||
void PushScope(std::string label);
|
void PushScope(std::string label);
|
||||||
void PushLocalScope(std::string label);
|
void PushLocalScope(std::string label);
|
||||||
void LocalEnter();
|
void LocalEnter();
|
||||||
@ -145,6 +150,7 @@ namespace pim
|
|||||||
void ScopeVariableType(int type);
|
void ScopeVariableType(int type);
|
||||||
void ScopeVariable(std::string label);
|
void ScopeVariable(std::string label);
|
||||||
|
|
||||||
|
void PushType(int type);
|
||||||
void PushVariableAddress(std::string label);
|
void PushVariableAddress(std::string label);
|
||||||
// void Store();
|
// void Store();
|
||||||
void LoadVariable(std::string label);
|
void LoadVariable(std::string label);
|
||||||
@ -161,6 +167,8 @@ namespace pim
|
|||||||
void Divide();
|
void Divide();
|
||||||
void Modulus();
|
void Modulus();
|
||||||
void Negate();
|
void Negate();
|
||||||
|
void ToInteger();
|
||||||
|
void ToFloat();
|
||||||
|
|
||||||
void TransformParticle();
|
void TransformParticle();
|
||||||
void CreateParticle();
|
void CreateParticle();
|
||||||
@ -170,9 +178,6 @@ namespace pim
|
|||||||
void LoadProperty(std::string property);
|
void LoadProperty(std::string property);
|
||||||
void StoreProperty(std::string property);
|
void StoreProperty(std::string property);
|
||||||
|
|
||||||
void IntegerToDecimal();
|
|
||||||
void DecimalToInteger();
|
|
||||||
|
|
||||||
void JumpEqual(std::string label);
|
void JumpEqual(std::string label);
|
||||||
void JumpNotEqual(std::string label);
|
void JumpNotEqual(std::string label);
|
||||||
void JumpGreater(std::string label);
|
void JumpGreater(std::string label);
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
#include <fstream>
|
#include <fstream>
|
||||||
#include "Machine.h"
|
#include "Machine.h"
|
||||||
#include "Opcodes.h"
|
#include "Opcodes.h"
|
||||||
|
#include "Types.h"
|
||||||
#include "simulation/Simulation.h"
|
#include "simulation/Simulation.h"
|
||||||
#include "X86Native.h"
|
#include "X86Native.h"
|
||||||
namespace pim
|
namespace pim
|
||||||
@ -269,6 +270,8 @@ namespace pim
|
|||||||
case Opcode::Get:
|
case Opcode::Get:
|
||||||
case Opcode::Position:
|
case Opcode::Position:
|
||||||
case Opcode::Kill:
|
case Opcode::Kill:
|
||||||
|
case Opcode::ToFloat:
|
||||||
|
case Opcode::ToInteger:
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -2,6 +2,7 @@ namespace pim
|
|||||||
{
|
{
|
||||||
struct Opcode
|
struct Opcode
|
||||||
{
|
{
|
||||||
|
public:
|
||||||
enum
|
enum
|
||||||
{
|
{
|
||||||
#define OPDEF(name) name,
|
#define OPDEF(name) name,
|
||||||
|
@ -1,4 +1,6 @@
|
|||||||
OPDEF(Load)
|
OPDEF(Load)
|
||||||
|
OPDEF(ToFloat)
|
||||||
|
OPDEF(ToInteger)
|
||||||
OPDEF(Store)
|
OPDEF(Store)
|
||||||
OPDEF(Constant)
|
OPDEF(Constant)
|
||||||
OPDEF(Increment)
|
OPDEF(Increment)
|
||||||
|
@ -1,6 +1,10 @@
|
|||||||
//Syntax analyser
|
//Syntax analyser
|
||||||
#include "Parser.h"
|
#include "Parser.h"
|
||||||
#include "Format.h"
|
#include "Format.h"
|
||||||
|
#include "Types.h"
|
||||||
|
#include "Exceptions.h"
|
||||||
|
#include "simulation/Particle.h"
|
||||||
|
#include "simulation/StructProperty.h"
|
||||||
namespace pim
|
namespace pim
|
||||||
{
|
{
|
||||||
namespace compiler
|
namespace compiler
|
||||||
@ -106,7 +110,18 @@ namespace pim
|
|||||||
*/
|
*/
|
||||||
void Parser::argument()
|
void Parser::argument()
|
||||||
{
|
{
|
||||||
generator->ScopeVariableType(token.Symbol);
|
int type;
|
||||||
|
switch(token.Symbol)
|
||||||
|
{
|
||||||
|
case Token::DecimalConstant:
|
||||||
|
type = DataType::Float;
|
||||||
|
break;
|
||||||
|
case Token::IntegerConstant:
|
||||||
|
case Token::ParticleConstant:
|
||||||
|
type = DataType::Integer;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
generator->ScopeVariableType(type);
|
||||||
if(!accept(Token::IntegerSymbol))
|
if(!accept(Token::IntegerSymbol))
|
||||||
if(!accept(Token::DecimalSymbol))
|
if(!accept(Token::DecimalSymbol))
|
||||||
if(!accept(Token::ParticleSymbol))
|
if(!accept(Token::ParticleSymbol))
|
||||||
@ -130,7 +145,18 @@ namespace pim
|
|||||||
*/
|
*/
|
||||||
void Parser::declaration()
|
void Parser::declaration()
|
||||||
{
|
{
|
||||||
generator->ScopeVariableType(token.Symbol);
|
int type;
|
||||||
|
switch(token.Symbol)
|
||||||
|
{
|
||||||
|
case Token::DecimalConstant:
|
||||||
|
type = DataType::Float;
|
||||||
|
break;
|
||||||
|
case Token::IntegerConstant:
|
||||||
|
case Token::ParticleConstant:
|
||||||
|
type = DataType::Integer;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
generator->ScopeVariableType(type);
|
||||||
if(!accept(Token::IntegerSymbol))
|
if(!accept(Token::IntegerSymbol))
|
||||||
if(!accept(Token::DecimalSymbol))
|
if(!accept(Token::DecimalSymbol))
|
||||||
if(!accept(Token::ParticleSymbol))
|
if(!accept(Token::ParticleSymbol))
|
||||||
@ -296,7 +322,7 @@ namespace pim
|
|||||||
generator->PushLocalScope(loopLabel+"Start");
|
generator->PushLocalScope(loopLabel+"Start");
|
||||||
neighbourVariable = token.Source;
|
neighbourVariable = token.Source;
|
||||||
expect(Token::Identifier);
|
expect(Token::Identifier);
|
||||||
generator->ScopeVariableType(Token::IntegerConstant);
|
generator->ScopeVariableType(DataType::Integer);
|
||||||
generator->ScopeVariable(neighbourVariable);
|
generator->ScopeVariable(neighbourVariable);
|
||||||
generator->ScopeVariable(xVar);
|
generator->ScopeVariable(xVar);
|
||||||
generator->ScopeVariable(yVar);
|
generator->ScopeVariable(yVar);
|
||||||
@ -471,6 +497,22 @@ namespace pim
|
|||||||
expect(Token::Identifier);
|
expect(Token::Identifier);
|
||||||
expect(Token::AssignSymbol);
|
expect(Token::AssignSymbol);
|
||||||
expression();
|
expression();
|
||||||
|
|
||||||
|
int t2;
|
||||||
|
StructProperty::PropertyType t = Particle::GetProperty(property).Type;
|
||||||
|
switch(t){
|
||||||
|
case StructProperty::ParticleType:
|
||||||
|
case StructProperty::Colour:
|
||||||
|
case StructProperty::Integer:
|
||||||
|
case StructProperty::UInteger:
|
||||||
|
t2 = DataType::Integer;
|
||||||
|
break;
|
||||||
|
case StructProperty::Float:
|
||||||
|
t2 = DataType::Float;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
generator->AssureType(t2);
|
||||||
generator->LoadVariable(variable);
|
generator->LoadVariable(variable);
|
||||||
generator->StoreProperty(property);
|
generator->StoreProperty(property);
|
||||||
}
|
}
|
||||||
|
@ -10,22 +10,6 @@ namespace pim
|
|||||||
{
|
{
|
||||||
namespace compiler
|
namespace compiler
|
||||||
{
|
{
|
||||||
class ParserExpectException: public std::exception
|
|
||||||
{
|
|
||||||
char * error;
|
|
||||||
public:
|
|
||||||
ParserExpectException(Token token, int expectingSymbol) {
|
|
||||||
error = strdup(std::string("Expecting " + Token::SymbolNames[expectingSymbol] + " got " + token.Source).c_str());
|
|
||||||
}
|
|
||||||
ParserExpectException(Token token, std::string expectingString) {
|
|
||||||
error = strdup(std::string("Expecting " + expectingString + " got " + token.Source).c_str());
|
|
||||||
}
|
|
||||||
const char * what() const throw()
|
|
||||||
{
|
|
||||||
return error;
|
|
||||||
}
|
|
||||||
~ParserExpectException() throw() {};
|
|
||||||
};
|
|
||||||
class Parser
|
class Parser
|
||||||
{
|
{
|
||||||
std::stringstream & source;
|
std::stringstream & source;
|
||||||
|
13
src/pim/Types.h
Normal file
13
src/pim/Types.h
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
#pragma once
|
||||||
|
namespace pim
|
||||||
|
{
|
||||||
|
struct DataType
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
enum
|
||||||
|
{
|
||||||
|
Integer,
|
||||||
|
Float
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
@ -11,9 +11,10 @@ namespace pim
|
|||||||
nativeRom.clear();
|
nativeRom.clear();
|
||||||
unsigned char * esi = new unsigned char[1024*1024];//malloc(1024*1024);
|
unsigned char * esi = new unsigned char[1024*1024];//malloc(1024*1024);
|
||||||
esi += 512;
|
esi += 512;
|
||||||
//int * esi = malloc(1024*1024);
|
|
||||||
emit("BE"); //mov esi, machineStack
|
emit("BE"); //mov esi, machineStack
|
||||||
emit((intptr_t)esi);
|
emit((intptr_t)esi);
|
||||||
|
|
||||||
while(programCounter < romSize)
|
while(programCounter < romSize)
|
||||||
{
|
{
|
||||||
Word argument = rom[programCounter].Parameter;
|
Word argument = rom[programCounter].Parameter;
|
||||||
@ -215,6 +216,14 @@ namespace pim
|
|||||||
emit("83 C6 08"); //add esi, 8
|
emit("83 C6 08"); //add esi, 8
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case Opcode::ToFloat:
|
||||||
|
emit("DB 06"); //fild [esi]
|
||||||
|
emit("D9 1E"); //fstp [esi]
|
||||||
|
break;
|
||||||
|
case Opcode::ToInteger:
|
||||||
|
emit("D9 06"); //fld [esi]
|
||||||
|
emit("DB 1E"); //fistp [esi]
|
||||||
|
break;
|
||||||
case Opcode::JumpEqual:
|
case Opcode::JumpEqual:
|
||||||
emit("83 C6 08"); //add esi, 8
|
emit("83 C6 08"); //add esi, 8
|
||||||
emit("8B 46 FC"); //mov eax, [esi-4]
|
emit("8B 46 FC"); //mov eax, [esi-4]
|
||||||
|
@ -25,3 +25,15 @@ std::vector<StructProperty> Particle::GetProperties()
|
|||||||
properties.push_back(StructProperty("dcolour", StructProperty::UInteger, offsetof(Particle, dcolour)));
|
properties.push_back(StructProperty("dcolour", StructProperty::UInteger, offsetof(Particle, dcolour)));
|
||||||
return properties;
|
return properties;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
StructProperty Particle::GetProperty(std::string propertyName)
|
||||||
|
{
|
||||||
|
std::vector<StructProperty> types = GetProperties();
|
||||||
|
for(std::vector<StructProperty>::iterator iter = types.begin(), end = types.end(); iter != end; ++iter)
|
||||||
|
{
|
||||||
|
if((*iter).Name == propertyName)
|
||||||
|
return *iter;
|
||||||
|
}
|
||||||
|
return StructProperty("unknown", StructProperty::Float, 0);
|
||||||
|
}
|
@ -26,6 +26,7 @@ struct Particle
|
|||||||
/** Returns a list of properties, their type and offset within the structure that can be changed
|
/** Returns a list of properties, their type and offset within the structure that can be changed
|
||||||
by higher-level processes refering to them by name such as Lua or the property tool **/
|
by higher-level processes refering to them by name such as Lua or the property tool **/
|
||||||
static std::vector<StructProperty> GetProperties();
|
static std::vector<StructProperty> GetProperties();
|
||||||
|
static StructProperty GetProperty(std::string propertyName);
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
Loading…
Reference in New Issue
Block a user