aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorYann Herklotz <ymherklotz@gmail.com>2017-03-28 11:16:55 +0100
committerYann Herklotz <ymherklotz@gmail.com>2017-03-28 11:16:55 +0100
commitc15bba765558e1017ef68f6d319141d4fb0b71fd (patch)
treefc432c5fdc9068439e2601c68c6e73f1f6ae4473
parent28f3bd2ff6984d653709716e092a322d4de4e3ea (diff)
downloadCompiler-c15bba765558e1017ef68f6d319141d4fb0b71fd.tar.gz
Compiler-c15bba765558e1017ef68f6d319141d4fb0b71fd.zip
can insert mult dim arrays
-rw-r--r--c_compiler/include/bindings.hpp4
-rw-r--r--c_compiler/include/declaration.hpp3
-rw-r--r--c_compiler/include/expression.hpp18
-rw-r--r--c_compiler/src/bindings.cpp22
-rw-r--r--c_compiler/src/c_parser.y4
-rw-r--r--c_compiler/src/declaration.cpp56
-rw-r--r--c_compiler/src/expression.cpp68
-rw-r--r--test.c8
-rw-r--r--test_deliverable/testcases/test_MAINPRINTF.c3
-rw-r--r--test_deliverable/testcases/test_MULTARR0.c10
-rw-r--r--test_deliverable/testcases/test_MULTARR0_driver.c6
11 files changed, 170 insertions, 32 deletions
diff --git a/c_compiler/include/bindings.hpp b/c_compiler/include/bindings.hpp
index d99d97b..42d52e1 100644
--- a/c_compiler/include/bindings.hpp
+++ b/c_compiler/include/bindings.hpp
@@ -15,6 +15,7 @@ struct DeclarationData
{
TypePtr type;
int stack_position;
+ std::vector<int> array_sizes;
};
// stores bindings for the current scope and where they are in the stack
@@ -31,7 +32,8 @@ private:
public:
Bindings();
- void insertBinding(const std::string &id, TypePtr type, const int &stack_position);
+ void insertBinding(const std::string &id, const TypePtr &type, const int &stack_position);
+ void insertBinding(const std::string &id, const TypePtr &type, const int &stack_position, const std::vector<int> array_sizes);
int insertStringLiteral(const std::string &string_literal);
void increaseStackPosition();
void increaseStackPosition(const int &position);
diff --git a/c_compiler/include/declaration.hpp b/c_compiler/include/declaration.hpp
index 9fe4db2..ef45737 100644
--- a/c_compiler/include/declaration.hpp
+++ b/c_compiler/include/declaration.hpp
@@ -69,6 +69,9 @@ public:
virtual Bindings localAsm(Bindings bindings, int &label_count) const;
virtual void countDeclarations(int &declaration_count) const;
virtual std::string getId() const;
+
+ int getSize() const;
+ DeclarationPtr getNextArrayDeclaration() const;
};
#endif
diff --git a/c_compiler/include/expression.hpp b/c_compiler/include/expression.hpp
index c784de7..6bade38 100644
--- a/c_compiler/include/expression.hpp
+++ b/c_compiler/include/expression.hpp
@@ -14,7 +14,7 @@ typedef std::shared_ptr<Expression> ExpressionPtr;
class Expression : public Node
{
-private:
+protected:
ExpressionPtr next_expression_;
public:
@@ -74,6 +74,8 @@ public:
virtual void expressionDepth(int &depth_count) const;
virtual void stackPosition(Bindings bindings, int &depth_count) const;
virtual TypePtr getType(const Bindings &bindings) const;
+
+ ExpressionPtr getIndex() const;
};
class PostfixFunctionCall : public UnaryExpression
@@ -312,4 +314,18 @@ public:
virtual TypePtr getType(const Bindings &bindings) const;
};
+class Initializer : public Expression
+{
+private:
+ ExpressionPtr next_initializer_;
+public:
+ Initializer(Expression *next_initializer);
+
+ virtual Bindings printAsm(Bindings bindings, int &label_count) const;
+ virtual TypePtr getType(const Bindings &bindings) const;
+
+ void printInitializerAsm(Bindings &bindings, int &label_count, int position, const std::vector<int> &iteration_vector, const TypePtr &type) const;
+ ExpressionPtr getNext() const;
+};
+
#endif
diff --git a/c_compiler/src/bindings.cpp b/c_compiler/src/bindings.cpp
index e91d408..0fe4c2f 100644
--- a/c_compiler/src/bindings.cpp
+++ b/c_compiler/src/bindings.cpp
@@ -8,7 +8,7 @@ Bindings::Bindings()
: break_label_(""), continue_label_(""), stack_counter_(0), expression_stack_(16)
{}
-void Bindings::insertBinding(const std::string &id, TypePtr type, const int &stack_position)
+void Bindings::insertBinding(const std::string &id,const TypePtr &type, const int &stack_position)
{
auto binding = bindings_.find(id);
@@ -26,6 +26,26 @@ void Bindings::insertBinding(const std::string &id, TypePtr type, const int &sta
}
}
+void Bindings::insertBinding(const std::string &id, const TypePtr &type, const int &stack_position, const std::vector<int> array_sizes)
+{
+ auto binding = bindings_.find(id);
+
+ if(binding == bindings_.end())
+ {
+ DeclarationData decl_data;
+ decl_data.type = type;
+ decl_data.stack_position = stack_position;
+ decl_data.array_sizes = array_sizes;
+ bindings_.insert(std::make_pair(id, decl_data));
+ }
+ else
+ {
+ (*binding).second.stack_position = stack_position;
+ (*binding).second.type = type;
+ (*binding).second.array_sizes = array_sizes;
+ }
+}
+
int Bindings::insertStringLiteral(const std::string &string_literal)
{
string_literals.push_back(string_literal);
diff --git a/c_compiler/src/c_parser.y b/c_compiler/src/c_parser.y
index feb5d0b..a7f05e0 100644
--- a/c_compiler/src/c_parser.y
+++ b/c_compiler/src/c_parser.y
@@ -250,8 +250,8 @@ IdentifierList: T_IDENTIFIER { $$ = new IdentifierDeclaration(); }
| IdentifierList T_CMA T_IDENTIFIER { $$ = new IdentifierDeclaration(); }
Initializer: AssignmentExpression { $$ = $1; }
- | T_LCB InitializerList T_RCB { $$ = $2; }
- | T_LCB InitializerList T_CMA T_RCB { $$ = $2; }
+ | T_LCB InitializerList T_RCB { $$ = new Initializer($2); }
+ | T_LCB InitializerList T_CMA T_RCB { $$ = new Initializer($2); }
;
InitializerList:
diff --git a/c_compiler/src/declaration.cpp b/c_compiler/src/declaration.cpp
index ca8f1f5..149bdab 100644
--- a/c_compiler/src/declaration.cpp
+++ b/c_compiler/src/declaration.cpp
@@ -4,6 +4,7 @@
#include "expression.hpp"
#include <cstdio>
+#include <memory>
#include <vector>
@@ -200,27 +201,21 @@ Bindings ArrayDeclaration::localAsm(Bindings bindings, int &label_count) const
if(getId() != "")
{
int stack_position = bindings.currentStackPosition();
- if(initializer_ != nullptr)
+ std::shared_ptr<ArrayDeclaration> array_declaration(
+ std::dynamic_pointer_cast<ArrayDeclaration>(declarator_));
+ std::vector<int> array_sizes = { size_ };
+ while(array_declaration != nullptr)
{
- ExpressionPtr initializer = initializer_;
- std::vector<ExpressionPtr> initializer_vector;
-
- while(initializer != nullptr)
- {
- initializer_vector.push_back(initializer);
- initializer = initializer->nextExpression();
- }
-
- for(auto itr = initializer_vector.rbegin(); itr != initializer_vector.rend(); ++itr)
- {
- int initializer_count = itr-initializer_vector.rbegin();
- (*itr)->printAsm(bindings, label_count);
- type_->store(stack_position+type_->getSize()*initializer_count);
- }
+ array_sizes.push_back(array_declaration->getSize());
+ array_declaration = std::dynamic_pointer_cast<ArrayDeclaration>
+ (array_declaration->getNextArrayDeclaration());
}
-
+
+ std::shared_ptr<Initializer> initializer;
+ initializer = std::static_pointer_cast<Initializer>(initializer_);
+ initializer->printInitializerAsm(bindings, label_count, array_sizes.size()-1, array_sizes, type_->type());
+
bindings.insertBinding(getId(), type_, stack_position);
- type_->increaseStackPosition(bindings);
}
return bindings;
@@ -233,15 +228,30 @@ void ArrayDeclaration::countDeclarations(int &declaration_count) const
if(next_list_declaration_ != nullptr)
next_list_declaration_->countDeclarations(declaration_count);
- std::shared_ptr<ArrayDeclaration> next_array;
- next_array = std::dynamic_pointer_cast<ArrayDeclaration>(declarator_);
- if(next_array != nullptr)
- next_array->countDeclarations(declaration_count);
+ std::shared_ptr<ArrayDeclaration> array_declaration(
+ std::dynamic_pointer_cast<ArrayDeclaration>(declarator_));
+ int size = size_;
+ while(array_declaration != nullptr)
+ {
+ size *= array_declaration->getSize();
+ array_declaration = std::dynamic_pointer_cast<ArrayDeclaration>(
+ array_declaration->getNextArrayDeclaration());
+ }
- declaration_count += size_;
+ declaration_count += size;
}
std::string ArrayDeclaration::getId() const
{
return declarator_->getId();
}
+
+int ArrayDeclaration::getSize() const
+{
+ return size_;
+}
+
+DeclarationPtr ArrayDeclaration::getNextArrayDeclaration() const
+{
+ return declarator_;
+}
diff --git a/c_compiler/src/expression.cpp b/c_compiler/src/expression.cpp
index 8d2e7cf..3df0a94 100644
--- a/c_compiler/src/expression.cpp
+++ b/c_compiler/src/expression.cpp
@@ -1,5 +1,6 @@
#include "expression.hpp"
+#include <algorithm>
#include <cstdio>
#include <exception>
#include <vector>
@@ -166,8 +167,8 @@ void PostfixArrayElement::stackPosition(Bindings bindings, int &label_count) con
unary_expression = std::static_pointer_cast<UnaryExpression>(postfix_expression_);
unary_expression->stackPosition(bindings, label_count);
- printf("\tli\t$3,%d\n\tmul\t$2,$2,$3\n\taddu\t$t0,$t0,$2\n",
- unary_expression->getType(bindings)->getSize());
+ printf("\tsll\t$2,$2,%d\n\taddu\t$t0,$t0,$2\n",
+ unary_expression->getType(bindings)->getSize()/2);
}
void PostfixArrayElement::expressionDepth(int &depth_count) const
@@ -926,3 +927,66 @@ TypePtr Constant::getType(const Bindings &) const
{
return std::make_shared<Int>();
}
+
+// Initializer definition
+
+Initializer::Initializer(Expression *next_initializer)
+ : next_initializer_(next_initializer)
+{}
+
+Bindings Initializer::printAsm(Bindings bindings, int &) const
+{
+ return bindings;
+}
+
+TypePtr Initializer::getType(const Bindings &bindings) const
+{
+ return next_initializer_->getType(bindings);
+}
+
+void Initializer::printInitializerAsm(Bindings &bindings, int &label_count, int position, const
+ std::vector<int> &iteration_vector, const TypePtr &type) const
+{
+ std::shared_ptr<Initializer> next_initializer
+ (std::dynamic_pointer_cast<Initializer>(next_initializer_));
+ ExpressionPtr current_expression = next_initializer_;
+ std::vector<ExpressionPtr> expression_vector;
+
+ while(current_expression != nullptr)
+ {
+ expression_vector.push_back(current_expression);
+ current_expression = current_expression->nextExpression();
+ }
+
+ std::reverse(expression_vector.begin(), expression_vector.end());
+ int size = (int)expression_vector.size();
+ for(int i = size; i < iteration_vector[position]; ++i)
+ {
+ expression_vector.emplace_back(nullptr);
+ }
+
+ for(int i = 0; i < iteration_vector[position]; ++i)
+ {
+ next_initializer = std::dynamic_pointer_cast<Initializer>(expression_vector[i]);
+ if(next_initializer != nullptr)
+ {
+ next_initializer->printInitializerAsm(bindings, label_count,
+ position-1, iteration_vector, type);
+ }
+ else
+ {
+ if(expression_vector[i] != nullptr)
+ {
+ Bindings temp_bindings = bindings;
+ expression_vector[i]->printAsm(temp_bindings, label_count);
+ printf("\tsw\t$2,%d($fp)\n", bindings.currentStackPosition());
+ }
+ type->increaseStackPosition(bindings);
+ }
+ }
+}
+
+ExpressionPtr Initializer::getNext() const
+{
+ return next_initializer_;
+}
diff --git a/test.c b/test.c
new file mode 100644
index 0000000..cb188a3
--- /dev/null
+++ b/test.c
@@ -0,0 +1,8 @@
+int main()
+{
+ int x[4][3] = {
+ { 1, 2 },
+ { 3, 4, 5},
+ { 6, 7, 8 }
+ };
+}
diff --git a/test_deliverable/testcases/test_MAINPRINTF.c b/test_deliverable/testcases/test_MAINPRINTF.c
index 62ddab6..de94817 100644
--- a/test_deliverable/testcases/test_MAINPRINTF.c
+++ b/test_deliverable/testcases/test_MAINPRINTF.c
@@ -2,7 +2,6 @@ int printf(const char *format, ...);
int main()
{
- char input[50] = {'H', 'e', 'l', 'l', 'o', ' ', 'W', 'o', 'r', 'l', 'd', };
- printf(input);
+ printf("Hello World\n");
return 0;
}
diff --git a/test_deliverable/testcases/test_MULTARR0.c b/test_deliverable/testcases/test_MULTARR0.c
new file mode 100644
index 0000000..c2072fc
--- /dev/null
+++ b/test_deliverable/testcases/test_MULTARR0.c
@@ -0,0 +1,10 @@
+int multarr0(int a, int b, int c, int d, int e, int f)
+{
+ int x[3][2] = {
+ { a, b, },
+ { c, d, },
+ { e, f, },
+ };
+
+ return x[1][0];
+}
diff --git a/test_deliverable/testcases/test_MULTARR0_driver.c b/test_deliverable/testcases/test_MULTARR0_driver.c
new file mode 100644
index 0000000..78672f9
--- /dev/null
+++ b/test_deliverable/testcases/test_MULTARR0_driver.c
@@ -0,0 +1,6 @@
+int multarr0(int, int, int, int, int, int);
+
+int main()
+{
+ return !( 21983 == multarr0(1298, 549, 21983, 39, 9035, 23944) );
+}