Commit 5ea4aec5 authored by zygzagZ's avatar zygzagZ

Flow + fix Makefile for CLion

parent 5ee30f7d
CC=g++
CCFLAGS=-g -W -Wall -O0 -std=c++2a -Wno-unused-parameter
OBJS=Absyn.o Lexer.o Parser.o Printer.o TypeCheck.o Info.o Skeleton.o ParseError.o Compiler.o Quadruple.o BasicBlock.o QuadrupleGenerator.o RegisterAllocator.o
.PHONY : clean distclean
all : latc
......@@ -10,9 +8,9 @@ all : latc
clean :
rm -f *.o latc Grammar.aux Grammar.log Grammar.pdf Grammar.dvi Grammar.ps Grammar
latc : ${OBJS} Latte.o
latc : Absyn.o Lexer.o Parser.o Printer.o TypeCheck.o Info.o Skeleton.o ParseError.o Compiler.o Quadruple.o BasicBlock.o QuadrupleGenerator.o RegisterAllocator.o Latte.o
@echo "Linking latc..."
${CC} ${CCFLAGS} ${OBJS} Latte.o -lstdc++fs -o latc
${CC} ${CCFLAGS} $^ -lstdc++fs -o latc
Absyn.o : src/Absyn.cpp src/Absyn.h
${CC} ${CCFLAGS} -c src/Absyn.cpp
......@@ -44,10 +42,10 @@ ParseError.o : src/ParseError.cpp src/Info.h src/InfoList.h src/Absyn.h src/Pars
Quadruple.o : src/codeGen/Quadruple.cpp src/Info.h src/InfoList.h src/Absyn.h src/codeGen/Variable.h
${CC} ${CCFLAGS} -c src/codeGen/Quadruple.cpp
Variable.o : src/codeGen/Quadruple.h src/codeGen/Variable.cpp src/Info.h src/InfoList.h src/Absyn.h
Variable.o : src/codeGen/Variable.cpp src/codeGen/Quadruple.h src/Info.h src/InfoList.h src/Absyn.h
${CC} ${CCFLAGS} -c src/codeGen/Variable.cpp
BasicBlock.o : src/codeGen/Quadruple.h src/codeGen/BasicBlock.h src/codeGen/BasicBlock.cpp src/codeGen/Variable.h src/Info.h src/InfoList.h src/Absyn.h
BasicBlock.o : src/codeGen/BasicBlock.cpp src/codeGen/Quadruple.h src/codeGen/BasicBlock.h src/codeGen/Variable.h src/Info.h src/InfoList.h src/Absyn.h
${CC} ${CCFLAGS} -c src/codeGen/BasicBlock.cpp
QuadrupleGenerator.o : src/codeGen/QuadrupleGenerator.cpp src/codeGen/Quadruple.h src/codeGen/BasicBlock.h src/Info.h src/InfoList.h src/Absyn.h src/codeGen/Variable.h src/Compiler.h src/codeGen/QuadrupleGenerator.h
......
#include "Compiler.h"
#include "codeGen/Quadruple.h"
#include "codeGen/RegisterAllocator.h"
#include <filesystem>
#include <iostream>
#include <cassert>
......@@ -54,9 +55,11 @@ void Compiler::compileFunction(const FunctionInfoPtr& f) {
buf << "\"" << name << "\":\n";
auto blocks = quadGen.compileFunction(f);
auto quadEnv = quadGen.compileFunction(f);
for (const auto& b : blocks) {
RegisterAllocator regGen(quadEnv);
for (const auto& b : quadEnv.blocks) {
for (const auto& q : b->quads) {
buf << q->toString() << endl;
}
......
......@@ -14,7 +14,9 @@ void BasicBlock::finishQuads() {
afterInit.clear();
for (auto q : quads) {
auto self = shared_from_this();
for (const auto& q : quads) {
q->useVariables();
q->block = self;
}
}
......@@ -11,12 +11,15 @@ using namespace std;
class BasicBlock : public std::enable_shared_from_this<BasicBlock> {
public:
struct FlowAnalysisData {
set<VariablePtr> in, out, def, use;
};
BasicBlock() = default;
vector<QuadruplePtr> quads;
vector<QuadruplePtr> afterInit;
vector<BasicBlockPtr> in, out;
vector<map<VariablePtr, VariablePtr>> phi;
FlowAnalysisData flow;
void append(const BasicBlockPtr& after) {
out.push_back(after);
after->in.push_back(shared_from_this());
......
......@@ -40,6 +40,7 @@ public:
int lineno;
int index;
BasicBlockPtr block;
virtual ~Quadruple() = default;
virtual std::string toString() const { return to_string(lineno) + "\t"; };
......
......@@ -5,7 +5,7 @@
#include "../Compiler.h"
#include "QuadrupleGenerator.h"
vector<BasicBlockPtr> QuadrupleGenerator::compileFunction(FunctionInfoPtr f) {
QuadrupleGenerator::Result QuadrupleGenerator::compileFunction(FunctionInfoPtr f) {
if (!f->block) return {};
scope->currentFunction = f;
......@@ -55,10 +55,9 @@ vector<BasicBlockPtr> QuadrupleGenerator::compileFunction(FunctionInfoPtr f) {
for (const auto& q : v->uses)
cout << q->toString() << endl;
}
vars.clear();
vector<BasicBlockPtr> ret;
blocks.swap(ret);
QuadrupleGenerator::Result ret;
vars.swap(ret.vars);
blocks.swap(ret.blocks);
scope->currentFunction = nullptr;
return ret;
......
......@@ -13,10 +13,15 @@
#include "Quadruple.h"
#include "BasicBlock.h"
class QuadrupleGenerator : public Skeleton {
public:
QuadrupleGenerator(shared_ptr<Scope> s) : lineno(0), scope(std::move(s)) {}
vector<BasicBlockPtr> compileFunction(FunctionInfoPtr f);
struct Result {
vector<BasicBlockPtr> blocks;
vector<VariablePtr> vars;
};
explicit QuadrupleGenerator(shared_ptr<Scope> s) : lineno(0), scope(std::move(s)) {}
Result compileFunction(FunctionInfoPtr f);
private:
vector<VariablePtr> vars;
vector<BasicBlockPtr> blocks;
......
#include "RegisterAllocator.h"
#include "BasicBlock.h"
#include "setOverloads.h"
void RegisterAllocator::analyseLive() {
for (auto v : vars) {
for (auto q : v->uses) {
q->block->flow.use.emplace(v);
}
for (auto q : v->writes) {
q->block->flow.def.emplace(v);
}
}
for (const auto& b : blocks) {
for (const auto& phiMap : b->phi) {
for (const auto& phiRow : phiMap) {
b->flow.def.emplace(phiRow.first);
b->flow.use.emplace(phiRow.second);
}
}
}
while (true) {
bool changed = false;
for (const auto& b : blocks) {
set<VariablePtr> pIn, pOut, diff;
auto &f = b->flow;
pIn.swap(f.in);
pOut.swap(f.out);
f.in = f.use + (pOut - f.def);
for (const auto& succ : b->out) {
f.out += succ->flow.in;
}
if (f.in != pIn || f.out != pOut) changed = true;
}
if (!changed) break;
}
}
\ No newline at end of file
#ifndef ZAD2_REGISTERALLOCATOR_H
#define ZAD2_REGISTERALLOCATOR_H
#include <utility>
#include "Quadruple.h"
#include "QuadrupleGenerator.h"
class Register : public std::enable_shared_from_this<Register> {
bool available;
......@@ -11,21 +14,22 @@ class Register : public std::enable_shared_from_this<Register> {
class RegisterAllocator {
public:
RegisterAllocator(vector<BasicBlockPtr> v) : blocks(v) {}
void processQJump(shared_ptr<QJump> q) {};
void processQJumpCond(shared_ptr<QJumpCond> q) {};
void processQLabel(shared_ptr<QLabel> q) {};
void processQParam(shared_ptr<QParam> q) {};
void processQReturn(shared_ptr<QReturn> q) {};
void processQWrite(shared_ptr<QWrite> q) {};
void processQAccess(shared_ptr<QAccess> q) {};
void processQAlloc(shared_ptr<QAlloc> q) {};
void processQAssign(shared_ptr<QAssign> q) {};
void processQCall(shared_ptr<QCall> q) {};
RegisterAllocator(const QuadrupleGenerator::Result &r) : blocks(r.blocks), vars(r.vars) {}
void processQJump(shared_ptr<QJump> q);
void processQJumpCond(shared_ptr<QJumpCond> q);
void processQLabel(shared_ptr<QLabel> q);
void processQParam(shared_ptr<QParam> q);
void processQReturn(shared_ptr<QReturn> q);
void processQWrite(shared_ptr<QWrite> q);
void processQAccess(shared_ptr<QAccess> q);
void processQAlloc(shared_ptr<QAlloc> q);
void processQAssign(shared_ptr<QAssign> q);
void processQCall(shared_ptr<QCall> q);
void analyseLive();
private:
vector<BasicBlockPtr> blocks;
vector<VariablePtr> vars;
};
......
#ifndef ZAD2_SETOVERLOADS_H
#define ZAD2_SETOVERLOADS_H
#include <set>
using namespace std;
template<typename T>
set<T> operator+ (const set<T> &l, const set<T> &r) {
set<T> ret;
set_union(l.begin(), l.end(), r.begin(), r.end(), std::inserter(ret, ret.begin()));
return ret;
}
template<typename T>
set<T> operator- (const set<T> &l, const set<T> &r) {
set<T> ret;
set_difference(l.begin(), l.end(), r.begin(), r.end(), std::inserter(ret, ret.begin()));
return ret;
}
template<typename T>
set<T> operator^(const set<T> &l, const set<T> &r) {
set<T> ret;
set_symmetric_difference(l.begin(), l.end(), r.begin(), r.end(), std::inserter(ret, ret.begin()));
return ret;
}
template<typename T>
set<T>& operator+=(set<T> &l, const set<T> &r) {
auto diff = r - l;
l.insert(diff.begin(), diff.end());
return l;
}
template<typename T>
bool operator==(const set<T> &l, const set<T> &r) {
return (r^l).empty();
}
template<typename T>
bool operator!=(const set<T> &l, const set<T> &r) {
return !(r == l);
}
#endif //ZAD2_SETOVERLOADS_H
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment