Commit 1b3210488e83a5db401110253d18b3c6c13ec8ec

Authored by Austin Sun
1 parent c189b2afe2
Exists in master

hope this works still got some syntax

Showing 4 changed files with 274 additions and 1 deletions Side-by-side Diff

... ... @@ -135,11 +135,12 @@
135 135 llvm::Value* VarExpr::Emit() {
136 136 return new llvm::LoadInst(findSymbol(id->GetName()).second, "", irgen.GetBasicBlock());
137 137 }
138   -
  138 +/*
139 139 llvm::Value* AssignExpr::Emit() {
140 140 VarExpr* ve = dynamic_cast<VarExpr*>(left);
141 141 return new llvm::StoreInst(right->Emit(), findSymbol(ve->GetIdentifier()->GetName()).second, false, irgen.GetBasicBlock());
142 142 }
  143 + */
143 144  
144 145 string Operator::getToken() const {
145 146 return tokenString;
... ... @@ -241,5 +242,239 @@
241 242 return llvm::BinaryOperator::Create(llvm::Instruction::Or, l, r, "", b);
242 243 }
243 244 return NULL;
  245 +}
  246 +
  247 +//----------------------------------------------------------------------------------------
  248 +//----------------------------------------------------------------------------------------
  249 +llvm::Value * AssignExpr::AssignField(){
  250 + FieldAccess * f = (FieldAccess *) left;
  251 + llvm::Value * rightval = right->Emit();
  252 + string operationStr(op->getToken());
  253 + bool isFloat = rightval->getType()->isFloatingPointTy();
  254 + llvm::Type * intTyp = irgen.GetIntType();
  255 + char * ptr = f->getField()->GetName();;
  256 +
  257 + std::vector<llvm::Constant *> maskI;
  258 + for(; *ptr; ptr++){
  259 + switch(*ptr){
  260 + case 'x':
  261 + maskI.push_back(llvm::ConstantInt::get(intTyp, 0));
  262 + break;
  263 + case 'y':
  264 + maskI.push_back(llvm::ConstantInt::get(intTyp, 1));
  265 + break;
  266 + case 'z':
  267 + maskI.push_back(llvm::ConstantInt::get(intTyp, 2));
  268 + break;
  269 + case 'w':
  270 + maskI.push_back(llvm::ConstantInt::get(intTyp, 3));
  271 + break;
  272 + default:
  273 + break;
  274 + }
  275 + }
  276 + llvm::Value * element;
  277 + llvm::Value * rightop = rightval;
  278 + llvm::Value * base_field = f->getBase()->Emit();
  279 + llvm::Value * storeInst = f->getBase()->Emit();
  280 +
  281 +
  282 + for (int i = 0; i < maskI.size(); i++){
  283 + element = llvm::ExtractElementInst::Create (base_field, maskI[i], "", irgen.GetBasicBlock());
  284 + if (rightval->getType()->isVectorTy()){
  285 + rightop = llvm::ExtractElementInst::Create(rightval, llvm::ConstantInt::get(intTyp, i), "", irgen.GetBasicBlock());
  286 + }
  287 + if (!operationStr.compare("=")){
  288 + storeInst = llvm::InsertElementInst::Create (storeInst, rightop, maskI[i], "", irgen.GetBasicBlock());
  289 + }
  290 + if (!operationStr.compare("+=")){
  291 + element = llvm::BinaryOperator::CreateFAdd(element, rightop, "", irgen.GetBasicBlock());
  292 + storeInst = llvm::InsertElementInst::Create (storeInst, element, maskI[i], "", irgen.GetBasicBlock());
  293 + }
  294 + if (!operationStr.compare("-=")){
  295 + element = llvm::BinaryOperator::CreateFSub(element, rightop, "", irgen.GetBasicBlock());
  296 + storeInst = llvm::InsertElementInst::Create (storeInst, element, maskI[i], "", irgen.GetBasicBlock());
  297 + }
  298 + if (!operationStr.compare("*=")){
  299 + element = llvm::BinaryOperator::CreateFMul(element, rightop, "", irgen.GetBasicBlock());
  300 + storeInst = llvm::InsertElementInst::Create (storeInst, element, maskI[i], "", irgen.GetBasicBlock());
  301 + }
  302 + if (!operationStr.compare("/=")){
  303 + element = llvm::BinaryOperator::CreateFDiv(element, rightop, "", irgen.GetBasicBlock());
  304 + storeInst = llvm::InsertElementInst::Create (storeInst, element, maskI[i], "", irgen.GetBasicBlock());
  305 + }
  306 + }
  307 + VarExpr * ve = dynamic_cast<VarExpr *>(f->getBase());
  308 + ve->AddressStore(storeInst);
  309 + if (isFloat){
  310 + return llvm::ExtractElementInst::Create (storeInst, maskI.back(), "", irgen.GetBasicBlock());
  311 + }
  312 + return storeInst;
  313 +}
  314 +
  315 +llvm::Value * AssignExpr::Emit(){
  316 + llvm::Value * leftval;
  317 + llvm::Value * rightval;
  318 +
  319 + FieldAccess * f = dynamic_cast<FieldAccess *>(left);
  320 + if (f){
  321 + return this->AssignField();
  322 + }
  323 + leftval = left->Emit();
  324 + rightval = right->Emit();
  325 +
  326 + string operationStr(op->getToken());
  327 +
  328 + VarExpr * vd = dynamic_cast<VarExpr *>(left);
  329 +
  330 + llvm::Value * storeInst = NULL;
  331 + if ( operationStr.compare("=") == 0 ){
  332 + if (vd){
  333 + vd->AddressStore(rightval);
  334 + return rightval;
  335 + }
  336 + return ((VarExpr *) left)->AddressStore(rightval);
  337 + }
  338 + else if ( operationStr.compare("+=") == 0 ){
  339 + if (leftval->getType()->isIntegerTy()){
  340 + storeInst = llvm::BinaryOperator::CreateAdd(leftval, rightval, "", irgen.GetBasicBlock());
  341 + if (vd){
  342 + vd->AddressStore(storeInst);
  343 + return storeInst;
  344 + }
  345 + }
  346 + else if (leftval->getType()->isFloatingPointTy() || rightval->getType()->isVectorTy()){
  347 + storeInst = llvm::BinaryOperator::CreateFAdd(leftval, rightval, "", irgen.GetBasicBlock());
  348 + if (vd){
  349 + vd->AddressStore(storeInst);
  350 + return storeInst;
  351 + }
  352 + }
  353 + else{
  354 + storeInst = convert(leftval, rightval, 0);
  355 + if (vd){
  356 + vd->AddressStore(storeInst);
  357 + return storeInst;
  358 + }
  359 + }
  360 + }
  361 + else if ( operationStr.compare("-=") == 0 ){
  362 + if (leftval->getType()->isIntegerTy()){
  363 + storeInst = llvm::BinaryOperator::CreateSub(leftval, rightval, "", irgen.GetBasicBlock());
  364 + if (vd){
  365 + vd->AddressStore(storeInst);
  366 + return storeInst;
  367 + }
  368 + }
  369 + else if (leftval->getType()->isFloatingPointTy() || rightval->getType()->isVectorTy()){
  370 + storeInst = llvm::BinaryOperator::CreateFSub(leftval, rightval, "", irgen.GetBasicBlock());
  371 + if (vd){
  372 + vd->AddressStore(storeInst);
  373 + return storeInst;
  374 + }
  375 + }
  376 + else{
  377 + storeInst = convert(leftval, rightval, 1);
  378 + if (vd){
  379 + vd->AddressStore(storeInst);
  380 + return storeInst;
  381 + }
  382 + }
  383 + }
  384 + else if ( operationStr.compare("*=") == 0 ){
  385 + if (leftval->getType()->isIntegerTy()){
  386 + storeInst = llvm::BinaryOperator::CreateMul(leftval, rightval, "", irgen.GetBasicBlock());
  387 + if (vd){
  388 + vd->AddressStore(storeInst);
  389 + return storeInst;
  390 + }
  391 + }
  392 + else if (leftval->getType()->isFloatingPointTy() || rightval->getType()->isVectorTy()){
  393 + storeInst = llvm::BinaryOperator::CreateFMul(leftval, rightval, "", irgen.GetBasicBlock());
  394 + if (vd){
  395 + vd->AddressStore(storeInst);
  396 + return storeInst;
  397 + }
  398 + }
  399 + else{
  400 + storeInst = convert(leftval, rightval, 3);
  401 + if (vd){
  402 + vd->AddressStore(storeInst);
  403 + return storeInst;
  404 + }
  405 + }
  406 + }
  407 + else if ( operationStr.compare("/=") == 0 ){
  408 + if (leftval->getType()->isIntegerTy()){
  409 + storeInst = llvm::BinaryOperator::CreateSDiv(leftval, rightval, "", irgen.GetBasicBlock());
  410 + if (vd){
  411 + vd->AddressStore(storeInst);
  412 + return storeInst;
  413 + }
  414 + }
  415 + else if (leftval->getType()->isFloatingPointTy() || rightval->getType()->isVectorTy()){
  416 + storeInst = llvm::BinaryOperator::CreateFDiv(leftval, rightval, "", irgen.GetBasicBlock());
  417 + if (vd){
  418 + vd->AddressStore(storeInst);
  419 + return storeInst;
  420 + }
  421 + }
  422 + else{
  423 + storeInst = convert(leftval, rightval, 2);
  424 + if (vd){
  425 + vd->AddressStore(storeInst);
  426 + return storeInst;
  427 + }
  428 + }
  429 + }
  430 + return NULL;
  431 +}
  432 +
  433 +llvm::Value * AssignExpr::convert(llvm::Value * vec, llvm::Value * val, int status ){
  434 + llvm::Type * intTyp = irgen.GetIntType();
  435 + llvm::Type * fltTyp = irgen.GetFloatType();
  436 + llvm::Value *idVal;
  437 + llvm::Value * element;
  438 + llvm::Value * retVal = vec;
  439 +
  440 + //get vector size
  441 + int numElements=-1;
  442 + if(vec->getType()==irgen.GetVec2Type()){
  443 + numElements=2;
  444 + }
  445 + else if(vec->getType()==irgen.GetVec3Type()){
  446 + numElements=3;
  447 + }
  448 + else if(vec->getType()==irgen.GetVec4Type()){
  449 + numElements=4;
  450 + }
  451 +
  452 + for (int i = 0; i < numElements; i++){
  453 + idVal = llvm::ConstantInt::get(intTyp, i);
  454 + element = llvm::ExtractElementInst::Create (vec, idVal, "", irgen.GetBasicBlock());
  455 + if (status == 0){
  456 + element = llvm::BinaryOperator::CreateFAdd(element, val, "", irgen.GetBasicBlock());
  457 + }
  458 + else if (status == 1){
  459 + element = llvm::BinaryOperator::CreateFSub(element, val, "", irgen.GetBasicBlock());
  460 + }
  461 + else if (status == 2){
  462 + element = llvm::BinaryOperator::CreateFMul(element, val, "", irgen.GetBasicBlock());
  463 + }
  464 + else{
  465 + element = llvm::BinaryOperator::CreateFDiv(element, val, "", irgen.GetBasicBlock());
  466 + }
  467 + retVal = llvm::InsertElementInst::Create (retVal, element, idVal, "", irgen.GetBasicBlock());
  468 + }
  469 + return retVal;
  470 +}
  471 +
  472 +llvm::Value* VarExpr::AddressStore(llvm::Value *store){
  473 + char * varname = GetIdentifier()->GetName();
  474 +
  475 + pair<Decl *, llvm::Value *> symbol = findSymbol(string(varname));
  476 + //value of symbol
  477 + llvm::StoreInst* storeInst = new llvm::StoreInst(store, symbol.second, "",irgen.GetBasicBlock());
  478 + return storeInst;
244 479 }
... ... @@ -94,6 +94,7 @@
94 94 void PrintChildren(int indentLevel);
95 95 Identifier *GetIdentifier() {return id;}
96 96 llvm::Value* Emit();
  97 + llvm::Value * AddressStore(llvm::Value* store);
97 98 };
98 99  
99 100 class Operator : public Node
... ... @@ -160,6 +161,8 @@
160 161 AssignExpr(Expr *lhs, Operator *op, Expr *rhs) : CompoundExpr(lhs,op,rhs) {}
161 162 const char *GetPrintNameForNode() { return "AssignExpr"; }
162 163 llvm::Value* Emit();
  164 + llvm::Value * convert(llvm::Value * vec, llvm::Value * val, int status );
  165 + llvm::Value *AssignField();
163 166 };
164 167  
165 168 class PostfixExpr : public CompoundExpr
... ... @@ -212,6 +215,8 @@
212 215 FieldAccess(Expr *base, Identifier *field); //ok to pass NULL base
213 216 const char *GetPrintNameForNode() { return "FieldAccess"; }
214 217 void PrintChildren(int indentLevel);
  218 + Expr * getBase(){ return base; }
  219 + Identifier * getField(){return field;}
215 220 };
216 221  
217 222 /* Like field access, call is used both for qualified base.field()
... ... @@ -81,4 +81,26 @@
81 81 const char *IRGenerator::TargetLayout = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-a0:0:64-s0:64:64-f80:128:128-n8:16:32:64-S128";
82 82  
83 83 const char *IRGenerator::TargetTriple = "x86_64-redhat-linux-gnu";
  84 +
  85 +llvm::Type *IRGenerator::GetVec2Type() const{
  86 + return llvm::VectorType::get(llvm::Type::getFloatTy(*context), 2);
  87 +}
  88 +llvm::Type *IRGenerator::GetVec3Type() const{
  89 + return llvm::VectorType::get(llvm::Type::getFloatTy(*context), 3);
  90 +}
  91 +llvm::Type *IRGenerator::GetVec4Type() const{
  92 + return llvm::VectorType::get(llvm::Type::getFloatTy(*context), 4);
  93 +}
  94 +llvm::Type *IRGenerator::GetMat2Type() const{
  95 + llvm::Type *elementTy = llvm::VectorType::get(llvm::Type::getFloatTy(*context), 2);
  96 + return llvm::ArrayType::get(elementTy, 2);
  97 +}
  98 +llvm::Type *IRGenerator::GetMat3Type() const{
  99 + llvm::Type *elementTy = llvm::VectorType::get(llvm::Type::getFloatTy(*context), 3);
  100 + return llvm::ArrayType::get(elementTy, 3);
  101 +}
  102 +llvm::Type *IRGenerator::GetMat4Type() const{
  103 + llvm::Type *elementTy = llvm::VectorType::get(llvm::Type::getFloatTy(*context), 4);
  104 + return llvm::ArrayType::get(elementTy, 4);
  105 +}
... ... @@ -42,6 +42,18 @@
42 42 llvm::Type *GetBoolType() const;
43 43 llvm::Type *GetFloatType() const;
44 44  
  45 + llvm::Type *GetVec2Type() const;
  46 +
  47 + llvm::Type *GetVec3Type() const;
  48 +
  49 + llvm::Type *GetVec4Type() const;
  50 +
  51 + llvm::Type *GetMat2Type() const;
  52 +
  53 + llvm::Type *GetMat3Type() const;
  54 +
  55 + llvm::Type *GetMat4Type() const;
  56 +
45 57 private:
46 58 llvm::LLVMContext *context;
47 59 llvm::Module *module;
... ... @@ -54,6 +66,7 @@
54 66  
55 67 static const char *TargetTriple;
56 68 static const char *TargetLayout;
  69 +
57 70 };
58 71  
59 72 extern IRGenerator irgen;