Commit 1ff8269e7921a072fceaf40d05240f3ccba094b4
Exists in
master
Merge branch 'master' of git.ucsd.edu:acs008/cse131-pa4
Showing 4 changed files Inline Diff
ast_decl.cc
View file @
1ff8269
/* File: ast_decl.cc | 1 | 1 | /* File: ast_decl.cc | |
* ----------------- | 2 | 2 | * ----------------- | |
* Implementation of Decl node classes. | 3 | 3 | * Implementation of Decl node classes. | |
*/ | 4 | 4 | */ | |
#include "ast_decl.h" | 5 | 5 | #include "ast_decl.h" | |
#include "ast_type.h" | 6 | 6 | #include "ast_type.h" | |
#include "ast_stmt.h" | 7 | 7 | #include "ast_stmt.h" | |
#include "symtable.h" | 8 | 8 | #include "symtable.h" | |
9 | 9 | |||
Decl::Decl(Identifier *n) : Node(*n->GetLocation()) { | 10 | 10 | Decl::Decl(Identifier *n) : Node(*n->GetLocation()) { | |
Assert(n != NULL); | 11 | 11 | Assert(n != NULL); | |
(id=n)->SetParent(this); | 12 | 12 | (id=n)->SetParent(this); | |
} | 13 | 13 | } | |
14 | 14 | |||
VarDecl::VarDecl(Identifier *n, Type *t, Expr *e) : Decl(n) { | 15 | 15 | VarDecl::VarDecl(Identifier *n, Type *t, Expr *e) : Decl(n) { | |
Assert(n != NULL && t != NULL); | 16 | 16 | Assert(n != NULL && t != NULL); | |
(type=t)->SetParent(this); | 17 | 17 | (type=t)->SetParent(this); | |
if (e) (assignTo=e)->SetParent(this); | 18 | 18 | if (e) (assignTo=e)->SetParent(this); | |
typeq = NULL; | 19 | 19 | typeq = NULL; | |
} | 20 | 20 | } | |
21 | 21 | |||
VarDecl::VarDecl(Identifier *n, TypeQualifier *tq, Expr *e) : Decl(n) { | 22 | 22 | VarDecl::VarDecl(Identifier *n, TypeQualifier *tq, Expr *e) : Decl(n) { | |
Assert(n != NULL && tq != NULL); | 23 | 23 | Assert(n != NULL && tq != NULL); | |
(typeq=tq)->SetParent(this); | 24 | 24 | (typeq=tq)->SetParent(this); | |
if (e) (assignTo=e)->SetParent(this); | 25 | 25 | if (e) (assignTo=e)->SetParent(this); | |
type = NULL; | 26 | 26 | type = NULL; | |
} | 27 | 27 | } | |
28 | 28 | |||
VarDecl::VarDecl(Identifier *n, Type *t, TypeQualifier *tq, Expr *e) : Decl(n) { | 29 | 29 | VarDecl::VarDecl(Identifier *n, Type *t, TypeQualifier *tq, Expr *e) : Decl(n) { | |
Assert(n != NULL && t != NULL && tq != NULL); | 30 | 30 | Assert(n != NULL && t != NULL && tq != NULL); | |
(type=t)->SetParent(this); | 31 | 31 | (type=t)->SetParent(this); | |
(typeq=tq)->SetParent(this); | 32 | 32 | (typeq=tq)->SetParent(this); | |
if (e) (assignTo=e)->SetParent(this); | 33 | 33 | if (e) (assignTo=e)->SetParent(this); | |
} | 34 | 34 | } | |
35 | 35 | |||
void VarDecl::PrintChildren(int indentLevel) { | 36 | 36 | void VarDecl::PrintChildren(int indentLevel) { | |
if (typeq) typeq->Print(indentLevel+1); | 37 | 37 | if (typeq) typeq->Print(indentLevel+1); | |
if (type) type->Print(indentLevel+1); | 38 | 38 | if (type) type->Print(indentLevel+1); | |
if (id) id->Print(indentLevel+1); | 39 | 39 | if (id) id->Print(indentLevel+1); | |
if (assignTo) assignTo->Print(indentLevel+1, "(initializer) "); | 40 | 40 | if (assignTo) assignTo->Print(indentLevel+1, "(initializer) "); | |
} | 41 | 41 | } | |
42 | 42 | |||
FnDecl::FnDecl(Identifier *n, Type *r, List<VarDecl*> *d) : Decl(n) { | 43 | 43 | FnDecl::FnDecl(Identifier *n, Type *r, List<VarDecl*> *d) : Decl(n) { | |
Assert(n != NULL && r!= NULL && d != NULL); | 44 | 44 | Assert(n != NULL && r!= NULL && d != NULL); | |
(returnType=r)->SetParent(this); | 45 | 45 | (returnType=r)->SetParent(this); | |
(formals=d)->SetParentAll(this); | 46 | 46 | (formals=d)->SetParentAll(this); | |
body = NULL; | 47 | 47 | body = NULL; | |
returnTypeq = NULL; | 48 | 48 | returnTypeq = NULL; | |
} | 49 | 49 | } | |
50 | 50 | |||
FnDecl::FnDecl(Identifier *n, Type *r, TypeQualifier *rq, List<VarDecl*> *d) : Decl(n) { | 51 | 51 | FnDecl::FnDecl(Identifier *n, Type *r, TypeQualifier *rq, List<VarDecl*> *d) : Decl(n) { | |
Assert(n != NULL && r != NULL && rq != NULL&& d != NULL); | 52 | 52 | Assert(n != NULL && r != NULL && rq != NULL&& d != NULL); | |
(returnType=r)->SetParent(this); | 53 | 53 | (returnType=r)->SetParent(this); | |
(returnTypeq=rq)->SetParent(this); | 54 | 54 | (returnTypeq=rq)->SetParent(this); | |
(formals=d)->SetParentAll(this); | 55 | 55 | (formals=d)->SetParentAll(this); | |
body = NULL; | 56 | 56 | body = NULL; | |
} | 57 | 57 | } | |
58 | 58 | |||
void FnDecl::SetFunctionBody(Stmt *b) { | 59 | 59 | void FnDecl::SetFunctionBody(Stmt *b) { | |
(body=b)->SetParent(this); | 60 | 60 | (body=b)->SetParent(this); | |
} | 61 | 61 | } | |
62 | 62 | |||
void FnDecl::PrintChildren(int indentLevel) { | 63 | 63 | void FnDecl::PrintChildren(int indentLevel) { | |
if (returnType) returnType->Print(indentLevel+1, "(return type) "); | 64 | 64 | if (returnType) returnType->Print(indentLevel+1, "(return type) "); | |
if (id) id->Print(indentLevel+1); | 65 | 65 | if (id) id->Print(indentLevel+1); | |
if (formals) formals->PrintAll(indentLevel+1, "(formals) "); | 66 | 66 | if (formals) formals->PrintAll(indentLevel+1, "(formals) "); | |
if (body) body->Print(indentLevel+1, "(body) "); | 67 | 67 | if (body) body->Print(indentLevel+1, "(body) "); | |
} | 68 | 68 | } | |
69 | ||||
70 | llvm::Value* VarDecl::Emit() { | |||
71 | llvm::Value* val; | |||
72 | if(type == Type::intType || type == Type::uintType) | |||
73 | val = new llvm::AllocaInst(llvm::Type::getInt32Ty(*irgen.GetContext()), id->GetName(), irgen.GetBasicBlock()); | |||
74 | if(type == Type::boolType) | |||
75 | val = new llvm::AllocaInst(llvm::Type::getInt1Ty(*irgen.GetContext()), id->GetName(), irgen.GetBasicBlock()); | |||
76 | else if(type == Type::voidType) | |||
77 | val = new llvm::AllocaInst(llvm::Type::getInt32Ty(*irgen.GetContext()), id->GetName(), irgen.GetBasicBlock()); | |||
78 | else if(type == Type::floatType) | |||
79 | val = new llvm::AllocaInst(llvm::Type::getVoidTy(*irgen.GetContext()), id->GetName(), irgen.GetBasicBlock()); | |||
80 | if(assignTo) val = new llvm::StoreInst(val, assignTo->Emit(), NULL, irgen.GetBasicBlock()); | |||
81 | return val; | |||
82 | } | |||
83 | ||||
84 | llvm::Value* FnDecl::Emit() { | |||
85 | llvm::LLVMContext* context = irgen.GetContext(); | |||
86 | llvm::BasicBlock::Create(*context, "funcBlock", irgen.GetBasicBlock()); | |||
87 | pushScope(); |
ast_decl.h
View file @
1ff8269
/* File: ast_decl.h | 1 | 1 | /* File: ast_decl.h | |
* ---------------- | 2 | 2 | * ---------------- | |
* In our parse tree, Decl nodes are used to represent and | 3 | 3 | * In our parse tree, Decl nodes are used to represent and | |
* manage declarations. There are 4 subclasses of the base class, | 4 | 4 | * manage declarations. There are 4 subclasses of the base class, | |
* specialized for declarations of variables, functions, classes, | 5 | 5 | * specialized for declarations of variables, functions, classes, | |
* and interfaces. | 6 | 6 | * and interfaces. | |
* | 7 | 7 | * | |
* pp3: You will need to extend the Decl classes to implement | 8 | 8 | * pp3: You will need to extend the Decl classes to implement | |
* semantic processing including detection of declaration conflicts | 9 | 9 | * semantic processing including detection of declaration conflicts | |
* and managing scoping issues. | 10 | 10 | * and managing scoping issues. | |
*/ | 11 | 11 | */ | |
12 | 12 | |||
#ifndef _H_ast_decl | 13 | 13 | #ifndef _H_ast_decl | |
#define _H_ast_decl | 14 | 14 | #define _H_ast_decl | |
15 | 15 | |||
#include "ast.h" | 16 | 16 | #include "ast.h" | |
#include "list.h" | 17 | 17 | #include "list.h" | |
#include "ast_expr.h" | 18 | 18 | #include "ast_expr.h" | |
19 | 19 | |||
class Type; | 20 | 20 | class Type; | |
class TypeQualifier; | 21 | 21 | class TypeQualifier; | |
class NamedType; | 22 | 22 | class NamedType; | |
class Identifier; | 23 | 23 | class Identifier; | |
class Stmt; | 24 | 24 | class Stmt; | |
25 | 25 | |||
void yyerror(const char *msg); | 26 | 26 | void yyerror(const char *msg); | |
27 | 27 | |||
class Decl : public Node | 28 | 28 | class Decl : public Node | |
{ | 29 | 29 | { | |
protected: | 30 | 30 | protected: | |
Identifier *id; | 31 | 31 | Identifier *id; | |
32 | 32 | |||
public: | 33 | 33 | public: | |
Decl() : id(NULL) {} | 34 | 34 | Decl() : id(NULL) {} | |
Decl(Identifier *name); | 35 | 35 | Decl(Identifier *name); | |
Identifier *GetIdentifier() const { return id; } | 36 | 36 | Identifier *GetIdentifier() const { return id; } | |
friend ostream& operator<<(ostream& out, Decl *d) { return out << d->id; } | 37 | 37 | friend ostream& operator<<(ostream& out, Decl *d) { return out << d->id; } | |
38 | 38 | |||
}; | 39 | 39 | }; | |
40 | 40 | |||
class VarDecl : public Decl | 41 | 41 | class VarDecl : public Decl | |
{ | 42 | 42 | { | |
protected: | 43 | 43 | protected: | |
Type *type; | 44 | 44 | Type *type; | |
TypeQualifier *typeq; | 45 | 45 | TypeQualifier *typeq; | |
Expr *assignTo; | 46 | 46 | Expr *assignTo; | |
47 | 47 | |||
public: | 48 | 48 | public: | |
VarDecl() : type(NULL), typeq(NULL), assignTo(NULL) {} | 49 | 49 | VarDecl() : type(NULL), typeq(NULL), assignTo(NULL) {} | |
VarDecl(Identifier *name, Type *type, Expr *assignTo = NULL); | 50 | 50 | VarDecl(Identifier *name, Type *type, Expr *assignTo = NULL); | |
VarDecl(Identifier *name, TypeQualifier *typeq, Expr *assignTo = NULL); | 51 | 51 | VarDecl(Identifier *name, TypeQualifier *typeq, Expr *assignTo = NULL); | |
VarDecl(Identifier *name, Type *type, TypeQualifier *typeq, Expr *assignTo = NULL); | 52 | 52 | VarDecl(Identifier *name, Type *type, TypeQualifier *typeq, Expr *assignTo = NULL); | |
const char *GetPrintNameForNode() { return "VarDecl"; } | 53 | 53 | const char *GetPrintNameForNode() { return "VarDecl"; } | |
void PrintChildren(int indentLevel); | 54 | 54 | void PrintChildren(int indentLevel); | |
Type *GetType() const { return type; } | 55 | 55 | Type *GetType() const { return type; } | |
56 | llvm::Value* Emit(); | |||
}; | 56 | 57 | }; | |
57 | 58 | |||
class VarDeclError : public VarDecl | 58 | 59 | class VarDeclError : public VarDecl | |
{ | 59 | 60 | { | |
public: | 60 | 61 | public: | |
VarDeclError() : VarDecl() { yyerror(this->GetPrintNameForNode()); }; | 61 | 62 | VarDeclError() : VarDecl() { yyerror(this->GetPrintNameForNode()); }; | |
const char *GetPrintNameForNode() { return "VarDeclError"; } | 62 | 63 | const char *GetPrintNameForNode() { return "VarDeclError"; } | |
}; | 63 | 64 | }; | |
64 | 65 | |||
class FnDecl : public Decl | 65 | 66 | class FnDecl : public Decl | |
{ | 66 | 67 | { | |
protected: | 67 | 68 | protected: | |
List<VarDecl*> *formals; | 68 | 69 | List<VarDecl*> *formals; | |
Type *returnType; | 69 | 70 | Type *returnType; | |
TypeQualifier *returnTypeq; | 70 | 71 | TypeQualifier *returnTypeq; | |
Stmt *body; | 71 | 72 | Stmt *body; | |
72 | 73 | |||
public: | 73 | 74 | public: | |
FnDecl() : Decl(), formals(NULL), returnType(NULL), returnTypeq(NULL), body(NULL) {} | 74 | 75 | FnDecl() : Decl(), formals(NULL), returnType(NULL), returnTypeq(NULL), body(NULL) {} | |
FnDecl(Identifier *name, Type *returnType, List<VarDecl*> *formals); | 75 | 76 | FnDecl(Identifier *name, Type *returnType, List<VarDecl*> *formals); | |
FnDecl(Identifier *name, Type *returnType, TypeQualifier *returnTypeq, List<VarDecl*> *formals); | 76 | 77 | FnDecl(Identifier *name, Type *returnType, TypeQualifier *returnTypeq, List<VarDecl*> *formals); | |
void SetFunctionBody(Stmt *b); | 77 | 78 | void SetFunctionBody(Stmt *b); | |
const char *GetPrintNameForNode() { return "FnDecl"; } | 78 | 79 | const char *GetPrintNameForNode() { return "FnDecl"; } |
ast_type.cc
View file @
1ff8269
/* File: ast_type.cc | 1 | 1 | /* File: ast_type.cc | |
* ----------------- | 2 | 2 | * ----------------- | |
* Implementation of type node classes. | 3 | 3 | * Implementation of type node classes. | |
*/ | 4 | 4 | */ | |
5 | 5 | |||
#include <string.h> | 6 | 6 | #include <string.h> | |
#include "ast_type.h" | 7 | 7 | #include "ast_type.h" | |
#include "ast_decl.h" | 8 | 8 | #include "ast_decl.h" | |
9 | 9 | |||
/* Class constants | 10 | 10 | /* Class constants | |
* --------------- | 11 | 11 | * --------------- | |
* These are public constants for the built-in base types (int, double, etc.) | 12 | 12 | * These are public constants for the built-in base types (int, double, etc.) | |
* They can be accessed with the syntax Type::intType. This allows you to | 13 | 13 | * They can be accessed with the syntax Type::intType. This allows you to | |
* directly access them and share the built-in types where needed rather that | 14 | 14 | * directly access them and share the built-in types where needed rather that | |
* creates lots of copies. | 15 | 15 | * creates lots of copies. | |
*/ | 16 | 16 | */ | |
17 | 17 | |||
Type *Type::intType = new Type("int"); | 18 | 18 | Type *Type::intType = new Type("int"); | |
Type *Type::floatType = new Type("float"); | 19 | 19 | Type *Type::floatType = new Type("float"); | |
Type *Type::voidType = new Type("void"); | 20 | 20 | Type *Type::voidType = new Type("void"); | |
Type *Type::boolType = new Type("bool"); | 21 | 21 | Type *Type::boolType = new Type("bool"); | |
Type *Type::mat2Type = new Type("mat2"); | 22 | 22 | Type *Type::mat2Type = new Type("mat2"); | |
Type *Type::mat3Type = new Type("mat3"); | 23 | 23 | Type *Type::mat3Type = new Type("mat3"); | |
Type *Type::mat4Type = new Type("mat4"); | 24 | 24 | Type *Type::mat4Type = new Type("mat4"); | |
Type *Type::vec2Type = new Type("vec2"); | 25 | 25 | Type *Type::vec2Type = new Type("vec2"); | |
Type *Type::vec3Type = new Type("vec3"); | 26 | 26 | Type *Type::vec3Type = new Type("vec3"); | |
Type *Type::vec4Type = new Type("vec4"); | 27 | 27 | Type *Type::vec4Type = new Type("vec4"); | |
Type *Type::ivec2Type = new Type("ivec2"); | 28 | 28 | Type *Type::ivec2Type = new Type("ivec2"); | |
Type *Type::ivec3Type = new Type("ivec3"); | 29 | 29 | Type *Type::ivec3Type = new Type("ivec3"); | |
Type *Type::ivec4Type = new Type("ivec4"); | 30 | 30 | Type *Type::ivec4Type = new Type("ivec4"); | |
Type *Type::bvec2Type = new Type("bvec2"); | 31 | 31 | Type *Type::bvec2Type = new Type("bvec2"); | |
Type *Type::bvec3Type = new Type("bvec3"); | 32 | 32 | Type *Type::bvec3Type = new Type("bvec3"); | |
Type *Type::bvec4Type = new Type("bvec4"); | 33 | 33 | Type *Type::bvec4Type = new Type("bvec4"); | |
Type *Type::uintType = new Type("uint"); | 34 | 34 | Type *Type::uintType = new Type("uint"); | |
Type *Type::uvec2Type = new Type("uvec2"); | 35 | 35 | Type *Type::uvec2Type = new Type("uvec2"); | |
Type *Type::uvec3Type = new Type("uvec3"); | 36 | 36 | Type *Type::uvec3Type = new Type("uvec3"); | |
Type *Type::uvec4Type = new Type("uvec4"); | 37 | 37 | Type *Type::uvec4Type = new Type("uvec4"); | |
Type *Type::errorType = new Type("error"); | 38 | 38 | Type *Type::errorType = new Type("error"); | |
39 | 39 | |||
TypeQualifier *TypeQualifier::inTypeQualifier = new TypeQualifier("in"); | 40 | 40 | TypeQualifier *TypeQualifier::inTypeQualifier = new TypeQualifier("in"); | |
TypeQualifier *TypeQualifier::outTypeQualifier = new TypeQualifier("out"); | 41 | 41 | TypeQualifier *TypeQualifier::outTypeQualifier = new TypeQualifier("out"); | |
TypeQualifier *TypeQualifier::constTypeQualifier = new TypeQualifier("const"); | 42 | 42 | TypeQualifier *TypeQualifier::constTypeQualifier = new TypeQualifier("const"); | |
TypeQualifier *TypeQualifier::uniformTypeQualifier = new TypeQualifier("uniform"); | 43 | 43 | TypeQualifier *TypeQualifier::uniformTypeQualifier = new TypeQualifier("uniform"); | |
44 | 44 | |||
Type::Type(const char *n) { | 45 | 45 | Type::Type(const char *n) { | |
Assert(n); | 46 | 46 | Assert(n); | |
typeName = strdup(n); | 47 | 47 | typeName = strdup(n); | |
} | 48 | 48 | } | |
49 | 49 | |||
void Type::PrintChildren(int indentLevel) { | 50 | 50 | void Type::PrintChildren(int indentLevel) { | |
printf("%s", typeName); | 51 | 51 | printf("%s", typeName); | |
} | 52 | 52 | } | |
53 | 53 | |||
TypeQualifier::TypeQualifier(const char *n) { | 54 | 54 | TypeQualifier::TypeQualifier(const char *n) { | |
Assert(n); | 55 | 55 | Assert(n); | |
typeQualifierName = strdup(n); | 56 | 56 | typeQualifierName = strdup(n); | |
} | 57 | 57 | } | |
58 | 58 | |||
void TypeQualifier::PrintChildren(int indentLevel) { | 59 | 59 | void TypeQualifier::PrintChildren(int indentLevel) { | |
printf("%s", typeQualifierName); | 60 | 60 | printf("%s", typeQualifierName); | |
} | 61 | 61 | } | |
62 | 62 | |||
bool Type::IsNumeric() { | 63 | 63 | bool Type::IsNumeric() { | |
return this->IsEquivalentTo(Type::intType) || this->IsEquivalentTo(Type::floatType); | 64 | 64 | return this->IsEquivalentTo(Type::intType) || this->IsEquivalentTo(Type::floatType); | |
} | 65 | 65 | } | |
66 | 66 | |||
bool Type::IsVector() { | 67 | 67 | bool Type::IsVector() { | |
return this->IsEquivalentTo(Type::vec2Type) || | 68 | 68 | return this->IsEquivalentTo(Type::vec2Type) || | |
this->IsEquivalentTo(Type::vec3Type) || | 69 | 69 | this->IsEquivalentTo(Type::vec3Type) || | |
this->IsEquivalentTo(Type::vec4Type); | 70 | 70 | this->IsEquivalentTo(Type::vec4Type); | |
} | 71 | 71 | } | |
72 | 72 | |||
bool Type::IsMatrix() { | 73 | 73 | bool Type::IsMatrix() { | |
return this->IsEquivalentTo(Type::mat2Type) || | 74 | 74 | return this->IsEquivalentTo(Type::mat2Type) || | |
this->IsEquivalentTo(Type::mat3Type) || | 75 | 75 | this->IsEquivalentTo(Type::mat3Type) || | |
this->IsEquivalentTo(Type::mat4Type); | 76 | 76 | this->IsEquivalentTo(Type::mat4Type); | |
} | 77 | 77 | } | |
78 | 78 | |||
bool Type::IsError() { | 79 | 79 | bool Type::IsError() { | |
return this->IsEquivalentTo(Type::errorType); | 80 | 80 | return this->IsEquivalentTo(Type::errorType); | |
} | 81 | 81 | } | |
82 | 82 | |||
NamedType::NamedType(Identifier *i) : Type(*i->GetLocation()) { | 83 | 83 | NamedType::NamedType(Identifier *i) : Type(*i->GetLocation()) { | |
Assert(i != NULL); | 84 | 84 | Assert(i != NULL); | |
(id=i)->SetParent(this); | 85 | 85 | (id=i)->SetParent(this); | |
} | 86 | 86 | } | |
87 | 87 | |||
void NamedType::PrintChildren(int indentLevel) { | 88 | 88 | void NamedType::PrintChildren(int indentLevel) { | |
id->Print(indentLevel+1); | 89 | 89 | id->Print(indentLevel+1); | |
} | 90 | 90 | } | |
91 | 91 | |||
ArrayType::ArrayType(yyltype loc, Type *et, int ec) : Type(loc) { | 92 | 92 | ArrayType::ArrayType(yyltype loc, Type *et, int ec) : Type(loc) { | |
Assert(et != NULL); | 93 | 93 | Assert(et != NULL); | |
(elemType=et)->SetParent(this); | 94 | 94 | (elemType=et)->SetParent(this); | |
elemCount=ec; | 95 | 95 | elemCount=ec; | |
} | 96 | 96 | } | |
void ArrayType::PrintChildren(int indentLevel) { | 97 | 97 | void ArrayType::PrintChildren(int indentLevel) { | |
elemType->Print(indentLevel+1); | 98 | 98 | elemType->Print(indentLevel+1); | |
} | 99 | 99 | } | |
100 |
ast_type.h
View file @
1ff8269
/* File: ast_type.h | 1 | 1 | /* File: ast_type.h | |
* ---------------- | 2 | 2 | * ---------------- | |
* In our parse tree, Type nodes are used to represent and | 3 | 3 | * In our parse tree, Type nodes are used to represent and | |
* store type information. The base Type class is used | 4 | 4 | * store type information. The base Type class is used | |
* for built-in types, the NamedType for classes and interfaces, | 5 | 5 | * for built-in types, the NamedType for classes and interfaces, | |
* and the ArrayType for arrays of other types. | 6 | 6 | * and the ArrayType for arrays of other types. | |
* | 7 | 7 | * | |
* pp3: You will need to extend the Type classes to implement | 8 | 8 | * pp3: You will need to extend the Type classes to implement | |
* the type system and rules for type equivalency and compatibility. | 9 | 9 | * the type system and rules for type equivalency and compatibility. | |
*/ | 10 | 10 | */ | |
11 | 11 | |||
#ifndef _H_ast_type | 12 | 12 | #ifndef _H_ast_type | |
#define _H_ast_type | 13 | 13 | #define _H_ast_type | |
14 | 14 | |||
#include "ast.h" | 15 | 15 | #include "ast.h" | |
#include "list.h" | 16 | 16 | #include "list.h" | |
#include <iostream> | 17 | 17 | #include <iostream> | |
18 | 18 | |||
using namespace std; | 19 | 19 | using namespace std; | |
20 | 20 | |||
class TypeQualifier : public Node | 21 | 21 | class TypeQualifier : public Node | |
{ | 22 | 22 | { | |
protected: | 23 | 23 | protected: | |
char *typeQualifierName; | 24 | 24 | char *typeQualifierName; | |
25 | 25 | |||
public : | 26 | 26 | public : | |
static TypeQualifier *inTypeQualifier, *outTypeQualifier, *constTypeQualifier, *uniformTypeQualifier; | 27 | 27 | static TypeQualifier *inTypeQualifier, *outTypeQualifier, *constTypeQualifier, *uniformTypeQualifier; | |
28 | 28 | |||
TypeQualifier(yyltype loc) : Node(loc) {} | 29 | 29 | TypeQualifier(yyltype loc) : Node(loc) {} | |
TypeQualifier(const char *str); | 30 | 30 | TypeQualifier(const char *str); | |
31 | 31 | |||
const char *GetPrintNameForNode() { return "TypeQualifier"; } | 32 | 32 | const char *GetPrintNameForNode() { return "TypeQualifier"; } | |
void PrintChildren(int indentLevel); | 33 | 33 | void PrintChildren(int indentLevel); | |
}; | 34 | 34 | }; | |
35 | 35 | |||
class Type : public Node | 36 | 36 | class Type : public Node | |
{ | 37 | 37 | { | |
protected: | 38 | 38 | protected: | |
char *typeName; | 39 | 39 | char *typeName; | |
40 | 40 | |||
public : | 41 | 41 | public : | |
static Type *intType, *uintType,*floatType, *boolType, *voidType, | 42 | 42 | static Type *intType, *uintType,*floatType, *boolType, *voidType, | |
*vec2Type, *vec3Type, *vec4Type, | 43 | 43 | *vec2Type, *vec3Type, *vec4Type, | |
*mat2Type, *mat3Type, *mat4Type, | 44 | 44 | *mat2Type, *mat3Type, *mat4Type, | |
*ivec2Type, *ivec3Type, *ivec4Type, | 45 | 45 | *ivec2Type, *ivec3Type, *ivec4Type, | |
*bvec2Type, *bvec3Type, *bvec4Type, | 46 | 46 | *bvec2Type, *bvec3Type, *bvec4Type, | |
*uvec2Type, *uvec3Type,*uvec4Type, | 47 | 47 | *uvec2Type, *uvec3Type,*uvec4Type, | |
*errorType; | 48 | 48 | *errorType; | |
49 | 49 | |||
Type(yyltype loc) : Node(loc) {} | 50 | 50 | Type(yyltype loc) : Node(loc) {} | |
Type(const char *str); | 51 | 51 | Type(const char *str); | |
52 | 52 | |||
const char *GetPrintNameForNode() { return "Type"; } | 53 | 53 | const char *GetPrintNameForNode() { return "Type"; } | |
void PrintChildren(int indentLevel); | 54 | 54 | void PrintChildren(int indentLevel); | |
55 | 55 | |||
virtual void PrintToStream(ostream& out) { out << typeName; } | 56 | 56 | virtual void PrintToStream(ostream& out) { out << typeName; } | |
friend ostream& operator<<(ostream& out, Type *t) { t->PrintToStream(out); return out; } | 57 | 57 | friend ostream& operator<<(ostream& out, Type *t) { t->PrintToStream(out); return out; } | |
virtual bool IsEquivalentTo(Type *other) { return (this == other); } | 58 | 58 | virtual bool IsEquivalentTo(Type *other) { return (this == other); } | |
virtual bool IsConvertibleTo(Type *other) { return (this == other || this == errorType); } | 59 | 59 | virtual bool IsConvertibleTo(Type *other) { return (this == other || this == errorType); } | |
bool IsNumeric(); | 60 | 60 | bool IsNumeric(); | |
bool IsVector(); | 61 | 61 | bool IsVector(); | |
bool IsMatrix(); | 62 | 62 | bool IsMatrix(); | |
bool IsError(); | 63 | 63 | bool IsError(); | |
}; | 64 | 64 | }; | |
65 | 65 | |||
66 | 66 | |||
class NamedType : public Type | 67 | 67 | class NamedType : public Type | |
{ | 68 | 68 | { | |
protected: | 69 | 69 | protected: | |
Identifier *id; | 70 | 70 | Identifier *id; | |
71 | 71 | |||
public: | 72 | 72 | public: | |
NamedType(Identifier *i); | 73 | 73 | NamedType(Identifier *i); | |
74 | 74 | |||
const char *GetPrintNameForNode() { return "NamedType"; } | 75 | 75 | const char *GetPrintNameForNode() { return "NamedType"; } | |
void PrintChildren(int indentLevel); | 76 | 76 | void PrintChildren(int indentLevel); | |
void PrintToStream(ostream& out) { out << id; } | 77 | 77 | void PrintToStream(ostream& out) { out << id; } |