mirror of
https://github.com/autc04/Retro68.git
synced 2024-11-23 15:32:26 +00:00
start with semantics
This commit is contained in:
parent
cb554ed40f
commit
2b3e533937
@ -43,6 +43,9 @@ add_executable(Rez
|
|||||||
RezLexer.cc
|
RezLexer.cc
|
||||||
RezLexerWaveToken.h
|
RezLexerWaveToken.h
|
||||||
RezLexerNextToken.cc
|
RezLexerNextToken.cc
|
||||||
|
|
||||||
|
ResourceDefinitions.cc
|
||||||
|
ResourceDefinitions.h
|
||||||
)
|
)
|
||||||
target_link_libraries(Rez ${Boost_LIBRARIES})
|
target_link_libraries(Rez ${Boost_LIBRARIES})
|
||||||
|
|
||||||
|
27
Rez/ResourceDefinitions.cc
Normal file
27
Rez/ResourceDefinitions.cc
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
#include "ResourceDefinitions.h"
|
||||||
|
#include <ostream>
|
||||||
|
|
||||||
|
ResourceDefinitions::ResourceDefinitions()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
std::ostream &operator<<(std::ostream &out, ResType t)
|
||||||
|
{
|
||||||
|
char c1 = static_cast<char>((int)t >> 24);
|
||||||
|
char c2 = static_cast<char>((int)t >> 16);
|
||||||
|
char c3 = static_cast<char>((int)t >> 8);
|
||||||
|
char c4 = static_cast<char>((int)t);
|
||||||
|
|
||||||
|
out << "'" << c1 << c2 << c3 << c4 << "'";
|
||||||
|
return out;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::ostream &operator<<(std::ostream &out, TypeSpec ts)
|
||||||
|
{
|
||||||
|
out << ts.getType();
|
||||||
|
if(ts.hasID())
|
||||||
|
out << " (" << ts.getID() << ")";
|
||||||
|
return out;
|
||||||
|
}
|
112
Rez/ResourceDefinitions.h
Normal file
112
Rez/ResourceDefinitions.h
Normal file
@ -0,0 +1,112 @@
|
|||||||
|
#ifndef RESOURCEDEFINITIONS_H
|
||||||
|
#define RESOURCEDEFINITIONS_H
|
||||||
|
|
||||||
|
#include <iosfwd>
|
||||||
|
#include <memory>
|
||||||
|
#include <map>
|
||||||
|
|
||||||
|
class ResType
|
||||||
|
{
|
||||||
|
int x;
|
||||||
|
public:
|
||||||
|
ResType() : x(0) {}
|
||||||
|
ResType(int x) : x(x) {}
|
||||||
|
operator int() const { return x; }
|
||||||
|
};
|
||||||
|
|
||||||
|
std::ostream& operator<<(std::ostream& out, ResType t);
|
||||||
|
|
||||||
|
class TypeSpec
|
||||||
|
{
|
||||||
|
ResType type;
|
||||||
|
int id;
|
||||||
|
public:
|
||||||
|
static const int noID = 65536;
|
||||||
|
|
||||||
|
TypeSpec() : id(noID) {}
|
||||||
|
TypeSpec(ResType type) : type(type), id(noID) {}
|
||||||
|
TypeSpec(ResType type, int id) : type(type), id(id) {}
|
||||||
|
|
||||||
|
ResType getType() const { return type; }
|
||||||
|
int getID() const { return id; }
|
||||||
|
|
||||||
|
bool hasID() const { return id != noID; }
|
||||||
|
};
|
||||||
|
|
||||||
|
std::ostream& operator<<(std::ostream& out, TypeSpec ts);
|
||||||
|
|
||||||
|
class Context
|
||||||
|
{
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
class Expression
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
//virtual int evaluateInt(Context *ctx);
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
class StringExpr : public Expression
|
||||||
|
{
|
||||||
|
std::string str;
|
||||||
|
public:
|
||||||
|
StringExpr(const std::string& str) : str(str) {}
|
||||||
|
};
|
||||||
|
|
||||||
|
class IntExpr : public Expression
|
||||||
|
{
|
||||||
|
int val;
|
||||||
|
public:
|
||||||
|
IntExpr(int val) : val(val) {}
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef std::shared_ptr<Expression> ExprPtr;
|
||||||
|
|
||||||
|
class Field
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
virtual bool needsValue() { return true; }
|
||||||
|
};
|
||||||
|
typedef std::shared_ptr<Field> FieldPtr;
|
||||||
|
|
||||||
|
class SimpleField : public Field
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
enum class Type
|
||||||
|
{
|
||||||
|
boolean, byte, integer, longint, rect, point, char_,
|
||||||
|
pstring, wstring, string, bitstring
|
||||||
|
};
|
||||||
|
|
||||||
|
enum class Attrs
|
||||||
|
{
|
||||||
|
none = 0, hex = 1, key = 2, unsigned_ = 4, literal = 8
|
||||||
|
};
|
||||||
|
|
||||||
|
Type type;
|
||||||
|
Attrs attrs = Attrs::none;
|
||||||
|
ExprPtr arrayCount;
|
||||||
|
|
||||||
|
ExprPtr value;
|
||||||
|
std::map<std::string, ExprPtr> namedValues;
|
||||||
|
|
||||||
|
void addNamedValue(std::string n) {}
|
||||||
|
void addNamedValue(std::string n, ExprPtr val) {}
|
||||||
|
};
|
||||||
|
typedef std::shared_ptr<SimpleField> SimpleFieldPtr;
|
||||||
|
|
||||||
|
|
||||||
|
inline SimpleField::Attrs operator|(SimpleField::Attrs a, SimpleField::Attrs b)
|
||||||
|
{
|
||||||
|
return SimpleField::Attrs( int(a) | int(b) );
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
class ResourceDefinitions
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
ResourceDefinitions();
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // RESOURCEDEFINITIONS_H
|
@ -49,6 +49,24 @@ static int readInt(const char *str)
|
|||||||
return x;
|
return x;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int readCharLit(const char *str)
|
||||||
|
{
|
||||||
|
const char *p = str + 1;
|
||||||
|
const char *e = str + strlen(str) - 1;
|
||||||
|
|
||||||
|
if(e - p != 4)
|
||||||
|
std::cout << "warning: CHAR LITERAL " << str << "\n";
|
||||||
|
|
||||||
|
int x = 0;
|
||||||
|
while(p != e)
|
||||||
|
{
|
||||||
|
x <<= 8;
|
||||||
|
x |= (*p) & 0xFF;
|
||||||
|
++p;
|
||||||
|
}
|
||||||
|
return x;
|
||||||
|
}
|
||||||
|
|
||||||
RezSymbol RezLexer::nextToken()
|
RezSymbol RezLexer::nextToken()
|
||||||
{
|
{
|
||||||
for(auto tok = nextWave(); tok != T_EOI && tok != T_EOF; tok = nextWave())
|
for(auto tok = nextWave(); tok != T_EOI && tok != T_EOF; tok = nextWave())
|
||||||
@ -154,7 +172,7 @@ case T_ ## name: /*std::cout << #name << std::endl;*/ return RezParser::make_ ##
|
|||||||
{
|
{
|
||||||
case T_INTLIT: return RezParser::make_INTLIT(readInt(tok.get_value().c_str()), loc);
|
case T_INTLIT: return RezParser::make_INTLIT(readInt(tok.get_value().c_str()), loc);
|
||||||
|
|
||||||
case T_CHARLIT: return RezParser::make_CHARLIT(tok.get_value().c_str(), loc);
|
case T_CHARLIT: return RezParser::make_CHARLIT(readCharLit(tok.get_value().c_str()), loc);
|
||||||
case T_STRINGLIT: return RezParser::make_STRINGLIT(tok.get_value().c_str(), loc);
|
case T_STRINGLIT: return RezParser::make_STRINGLIT(tok.get_value().c_str(), loc);
|
||||||
|
|
||||||
NOVAL_TOK(LEFTBRACE);
|
NOVAL_TOK(LEFTBRACE);
|
||||||
|
112
Rez/RezParser.yy
112
Rez/RezParser.yy
@ -10,7 +10,7 @@
|
|||||||
%define parse.assert
|
%define parse.assert
|
||||||
|
|
||||||
%token<std::string> IDENTIFIER;
|
%token<std::string> IDENTIFIER;
|
||||||
%token<std::string> CHARLIT;
|
%token<int> CHARLIT;
|
||||||
%token<std::string> STRINGLIT;
|
%token<std::string> STRINGLIT;
|
||||||
%token<int> INTLIT;
|
%token<int> INTLIT;
|
||||||
|
|
||||||
@ -83,6 +83,8 @@
|
|||||||
%param { RezLexer& lexer }
|
%param { RezLexer& lexer }
|
||||||
|
|
||||||
%code requires {
|
%code requires {
|
||||||
|
#include "ResourceDefinitions.h"
|
||||||
|
|
||||||
#define YY_NULLPTR nullptr
|
#define YY_NULLPTR nullptr
|
||||||
class RezLexer;
|
class RezLexer;
|
||||||
}
|
}
|
||||||
@ -120,14 +122,6 @@ rez : %empty
|
|||||||
| rez resource ";"
|
| rez resource ";"
|
||||||
;
|
;
|
||||||
|
|
||||||
simpletype : "boolean"
|
|
||||||
| "bit" | "byte" | "word" | "integer" | "long" | "longint" | "rect"
|
|
||||||
| "point"
|
|
||||||
| "char"
|
|
||||||
| "pstring" array_count_opt
|
|
||||||
| "wstring" array_count_opt
|
|
||||||
| "string" array_count_opt;
|
|
||||||
| "bitstring" "[" expression "]";
|
|
||||||
|
|
||||||
type_definition : "type" type_spec "{" field_definitions "}"
|
type_definition : "type" type_spec "{" field_definitions "}"
|
||||||
{ std::cout << "TYPE " << $2 << std::endl; }
|
{ std::cout << "TYPE " << $2 << std::endl; }
|
||||||
@ -135,9 +129,12 @@ type_definition : "type" type_spec "{" field_definitions "}"
|
|||||||
{ std::cout << "TYPE " << $2 << std::endl; }
|
{ std::cout << "TYPE " << $2 << std::endl; }
|
||||||
;
|
;
|
||||||
|
|
||||||
%type <std::string> type_spec;
|
%type <ResType> res_type;
|
||||||
type_spec : CHARLIT { $$ = $1; }
|
res_type : CHARLIT { $$ = ResType($1); } ;
|
||||||
| CHARLIT "(" INTLIT ")" { $$ = $1; }
|
|
||||||
|
%type <TypeSpec> type_spec;
|
||||||
|
type_spec : res_type { $$ = TypeSpec($res_type); }
|
||||||
|
| res_type "(" INTLIT ")" { $$ = TypeSpec($res_type, $INTLIT); }
|
||||||
;
|
;
|
||||||
|
|
||||||
field_definitions : %empty
|
field_definitions : %empty
|
||||||
@ -145,40 +142,78 @@ field_definitions : %empty
|
|||||||
| field_definitions ";"
|
| field_definitions ";"
|
||||||
| field_definitions field_definition ";" ;
|
| field_definitions field_definition ";" ;
|
||||||
|
|
||||||
field_definition: simple_field_definition
|
%type <FieldPtr> field_definition;
|
||||||
|
field_definition: simple_field_definition { $$ = $1; }
|
||||||
| array_definition
|
| array_definition
|
||||||
| switch_definition
|
| switch_definition
|
||||||
| fill_statement
|
| fill_statement
|
||||||
| align_statement;
|
| align_statement;
|
||||||
|
|
||||||
|
%type <SimpleFieldPtr> simple_field_definition;
|
||||||
|
simple_field_definition: field_attributes simpletype array_count_opt value_spec_opt
|
||||||
|
{
|
||||||
|
$$ = std::make_shared<SimpleField>();
|
||||||
|
$$->attrs = $field_attributes;
|
||||||
|
$$->type = $simpletype;
|
||||||
|
$$->arrayCount = $array_count_opt;
|
||||||
|
$$->value = $value_spec_opt;
|
||||||
|
}
|
||||||
|
| simple_field_definition IDENTIFIER
|
||||||
|
{ $$ = $1; $$->addNamedValue($IDENTIFIER); }
|
||||||
|
| simple_field_definition IDENTIFIER "=" value
|
||||||
|
{ $$ = $1; $$->addNamedValue($IDENTIFIER, $value); }
|
||||||
|
| simple_field_definition "," IDENTIFIER
|
||||||
|
{ $$ = $1; $$->addNamedValue($IDENTIFIER); }
|
||||||
|
| simple_field_definition "," IDENTIFIER "=" value
|
||||||
|
{ $$ = $1; $$->addNamedValue($IDENTIFIER, $value); }
|
||||||
|
;
|
||||||
|
|
||||||
|
%type <ExprPtr> array_count array_count_opt value_spec_opt value ;
|
||||||
|
%type <ExprPtr> expression expression1 expression2 ;
|
||||||
|
%type <ExprPtr> expression3 expression4 expression5 expression6;
|
||||||
|
%type <ExprPtr> expression7 expression8;
|
||||||
|
|
||||||
|
value_spec_opt : %empty { $$ = nullptr; } | "=" value { $$ = $2; } ;
|
||||||
|
|
||||||
|
%type <SimpleField::Type> simpletype;
|
||||||
|
simpletype : "boolean" { $$ = SimpleField::Type::boolean; }
|
||||||
|
| "byte" { $$ = SimpleField::Type::byte; }
|
||||||
|
| "integer" { $$ = SimpleField::Type::integer; }
|
||||||
|
| "longint" { $$ = SimpleField::Type::longint; }
|
||||||
|
| "rect" { $$ = SimpleField::Type::rect; }
|
||||||
|
| "point" { $$ = SimpleField::Type::point; }
|
||||||
|
| "char" { $$ = SimpleField::Type::char_; }
|
||||||
|
| "pstring" { $$ = SimpleField::Type::pstring; }
|
||||||
|
| "wstring" { $$ = SimpleField::Type::wstring; }
|
||||||
|
| "string" { $$ = SimpleField::Type::string; }
|
||||||
|
| "bitstring" { $$ = SimpleField::Type::bitstring; }
|
||||||
|
;
|
||||||
|
|
||||||
fill_statement : "fill" fill_unit array_count_opt;
|
fill_statement : "fill" fill_unit array_count_opt;
|
||||||
align_statement : "align" fill_unit;
|
align_statement : "align" fill_unit;
|
||||||
|
|
||||||
fill_unit : "bit" | "byte" | "word" | "long";
|
fill_unit : "bit" | "byte" | "word" | "long";
|
||||||
|
|
||||||
simple_field_definition: field_attributes simpletype value_spec;
|
|
||||||
|
|
||||||
value_spec : %empty
|
|
||||||
| named_values
|
|
||||||
| "=" expression;
|
|
||||||
|
|
||||||
named_values: named_value
|
|
||||||
| named_values "," named_value
|
|
||||||
| named_values named_value;
|
|
||||||
|
|
||||||
named_value : IDENTIFIER
|
|
||||||
| IDENTIFIER "=" expression ;
|
|
||||||
|
|
||||||
array_definition: array_attributes "array" array_name_opt array_count_opt "{" field_definitions "}" ;
|
array_definition: array_attributes "array" array_name_opt array_count_opt "{" field_definitions "}" ;
|
||||||
|
|
||||||
array_count : "[" expression "]" ;
|
array_count : "[" expression "]" { $$ = $2; }
|
||||||
array_count_opt : %empty | array_count ;
|
array_count_opt : %empty { $$ = nullptr; } | array_count;
|
||||||
|
|
||||||
array_name_opt : %empty | IDENTIFIER ;
|
array_name_opt : %empty | IDENTIFIER ;
|
||||||
|
|
||||||
array_attributes: %empty | "wide" ;
|
array_attributes: %empty | "wide" ;
|
||||||
field_attributes: %empty | field_attributes field_attribute;
|
|
||||||
field_attribute : "hex" | "key" | "unsigned" | "literal";
|
%type <SimpleField::Attrs> field_attributes field_attribute;
|
||||||
|
field_attributes: %empty { $$ = SimpleField::Attrs::none; }
|
||||||
|
| field_attributes field_attribute { $$ = $1 | $2; }
|
||||||
|
;
|
||||||
|
|
||||||
|
field_attribute : "hex" { $$ = SimpleField::Attrs::hex; }
|
||||||
|
| "key" { $$ = SimpleField::Attrs::key; }
|
||||||
|
| "unsigned" { $$ = SimpleField::Attrs::unsigned_; }
|
||||||
|
| "literal" { $$ = SimpleField::Attrs::literal; }
|
||||||
|
;
|
||||||
|
|
||||||
switch_definition: "switch" "{"
|
switch_definition: "switch" "{"
|
||||||
switch_cases
|
switch_cases
|
||||||
@ -206,6 +241,11 @@ expression
|
|||||||
;
|
;
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
value : expression
|
||||||
|
| "{" resource_body "}"
|
||||||
|
| STRINGLIT { $$ = std::make_shared<StringExpr>($1); }
|
||||||
|
;
|
||||||
|
|
||||||
expression : expression1
|
expression : expression1
|
||||||
| expression "^" expression1
|
| expression "^" expression1
|
||||||
;
|
;
|
||||||
@ -243,20 +283,20 @@ expression7 : expression8
|
|||||||
| "~" expression7
|
| "~" expression7
|
||||||
;
|
;
|
||||||
|
|
||||||
expression8 : INTLIT
|
expression8 : INTLIT { $$ = std::make_shared<IntExpr>($1); }
|
||||||
| CHARLIT
|
| CHARLIT { $$ = std::make_shared<IntExpr>($1); }
|
||||||
| STRINGLIT
|
|
||||||
| IDENTIFIER
|
| IDENTIFIER
|
||||||
| IDENTIFIER "(" function_argument_list ")"
|
| IDENTIFIER "(" function_argument_list ")"
|
||||||
| IDENTIFIER "[" function_argument_list1 "]"
|
| IDENTIFIER "[" function_argument_list1 "]"
|
||||||
| "(" expression ")"
|
| "(" expression ")" { $$ = $2; }
|
||||||
| "{" resource_body "}"
|
|
||||||
;
|
;
|
||||||
|
|
||||||
function_argument_list : %empty | function_argument_list1 ;
|
function_argument_list : %empty | function_argument_list1 ;
|
||||||
function_argument_list1 : expression | function_argument_list "," expression ;
|
function_argument_list1 : expression | function_argument_list "," expression ;
|
||||||
|
|
||||||
resource: "resource" CHARLIT "(" function_argument_list ")" "{" resource_body "}"
|
resource: "resource" res_type "(" function_argument_list ")" "{" resource_body "}"
|
||||||
{ std::cout << "RESOURCE " << $2 << std::endl; }
|
{ std::cout << "RESOURCE " << $2 << std::endl; }
|
||||||
|
|
||||||
resource_body : %empty | resource_body1 ;
|
resource_body : %empty | resource_body1 ;
|
||||||
@ -266,6 +306,6 @@ resource_body1 : resource_item
|
|||||||
| resource_body1 ";"
|
| resource_body1 ";"
|
||||||
;
|
;
|
||||||
|
|
||||||
resource_item : expression | IDENTIFIER "{" resource_body "}" ;
|
resource_item : value | IDENTIFIER "{" resource_body "}" ;
|
||||||
|
|
||||||
%%
|
%%
|
||||||
|
Loading…
Reference in New Issue
Block a user