1
0
mirror of https://github.com/exaloop/codon.git synced 2025-06-03 15:03:52 +08:00

Add new attributes

This commit is contained in:
A. R. Shajii 2022-01-25 16:10:34 -05:00
parent e7851d8983
commit 8dd7d2e0ea
3 changed files with 212 additions and 12 deletions

View File

@ -1,5 +1,8 @@
#include "value.h"
#include "attribute.h"
#include "codon/sir/func.h"
#include "codon/sir/util/cloning.h"
#include "codon/sir/value.h"
#include "codon/util/fmt/ostream.h"
namespace codon {
@ -36,5 +39,111 @@ std::ostream &MemberAttribute::doFormat(std::ostream &os) const {
const std::string SrcInfoAttribute::AttributeName = "srcInfoAttribute";
const std::string ListLiteralAttribute::AttributeName = "listLiteralAttribute";
std::unique_ptr<Attribute> ListLiteralAttribute::clone(util::CloneVisitor &cv) const {
std::vector<Value *> elementsCloned;
for (auto *val : elements)
elementsCloned.push_back(cv.clone(val));
return std::make_unique<ListLiteralAttribute>(elementsCloned);
}
std::unique_ptr<Attribute>
ListLiteralAttribute::forceClone(util::CloneVisitor &cv) const {
std::vector<Value *> elementsCloned;
for (auto *val : elements)
elementsCloned.push_back(cv.forceClone(val));
return std::make_unique<ListLiteralAttribute>(elementsCloned);
}
std::ostream &ListLiteralAttribute::doFormat(std::ostream &os) const {
std::vector<std::string> strings;
for (auto *val : elements)
strings.push_back(fmt::format(FMT_STRING("{}"), *val));
fmt::print(os, FMT_STRING("[{}]"), fmt::join(strings.begin(), strings.end(), ","));
return os;
}
const std::string SetLiteralAttribute::AttributeName = "setLiteralAttribute";
std::unique_ptr<Attribute> SetLiteralAttribute::clone(util::CloneVisitor &cv) const {
std::vector<Value *> elementsCloned;
for (auto *val : elements)
elementsCloned.push_back(cv.clone(val));
return std::make_unique<SetLiteralAttribute>(elementsCloned);
}
std::unique_ptr<Attribute>
SetLiteralAttribute::forceClone(util::CloneVisitor &cv) const {
std::vector<Value *> elementsCloned;
for (auto *val : elements)
elementsCloned.push_back(cv.forceClone(val));
return std::make_unique<SetLiteralAttribute>(elementsCloned);
}
std::ostream &SetLiteralAttribute::doFormat(std::ostream &os) const {
std::vector<std::string> strings;
for (auto *val : elements)
strings.push_back(fmt::format(FMT_STRING("{}"), *val));
fmt::print(os, FMT_STRING("set([{}])"),
fmt::join(strings.begin(), strings.end(), ","));
return os;
}
const std::string DictLiteralAttribute::AttributeName = "dictLiteralAttribute";
std::unique_ptr<Attribute> DictLiteralAttribute::clone(util::CloneVisitor &cv) const {
std::vector<DictLiteralAttribute::KeyValuePair> elementsCloned;
for (auto &val : elements)
elementsCloned.push_back({cv.clone(val.key), cv.clone(val.value)});
return std::make_unique<DictLiteralAttribute>(elementsCloned);
}
std::unique_ptr<Attribute>
DictLiteralAttribute::forceClone(util::CloneVisitor &cv) const {
std::vector<DictLiteralAttribute::KeyValuePair> elementsCloned;
for (auto &val : elements)
elementsCloned.push_back({cv.forceClone(val.key), cv.forceClone(val.value)});
return std::make_unique<DictLiteralAttribute>(elementsCloned);
}
std::ostream &DictLiteralAttribute::doFormat(std::ostream &os) const {
std::vector<std::string> strings;
for (auto &val : elements)
strings.push_back(fmt::format(FMT_STRING("{}:{}"), *val.key, *val.value));
fmt::print(os, FMT_STRING("dict([{}])"),
fmt::join(strings.begin(), strings.end(), ","));
return os;
}
const std::string PartialFunctionAttribute::AttributeName = "partialFunctionAttribute";
std::unique_ptr<Attribute>
PartialFunctionAttribute::clone(util::CloneVisitor &cv) const {
std::vector<Value *> argsCloned;
for (auto *val : args)
argsCloned.push_back(cv.clone(val));
return std::make_unique<PartialFunctionAttribute>(cast<Func>(cv.clone(func)),
argsCloned);
}
std::unique_ptr<Attribute>
PartialFunctionAttribute::forceClone(util::CloneVisitor &cv) const {
std::vector<Value *> argsCloned;
for (auto *val : args)
argsCloned.push_back(cv.forceClone(val));
return std::make_unique<PartialFunctionAttribute>(cast<Func>(cv.forceClone(func)),
argsCloned);
}
std::ostream &PartialFunctionAttribute::doFormat(std::ostream &os) const {
std::vector<std::string> strings;
for (auto *val : args)
strings.push_back(val ? fmt::format(FMT_STRING("{}"), *val) : "...");
fmt::print(os, FMT_STRING("{}({})"), func->getName(),
fmt::join(strings.begin(), strings.end(), ","));
return os;
}
} // namespace ir
} // namespace codon

View File

@ -14,6 +14,13 @@
namespace codon {
namespace ir {
class Func;
class Value;
namespace util {
class CloneVisitor;
}
/// Base for SIR attributes.
struct Attribute {
virtual ~Attribute() noexcept = default;
@ -26,14 +33,15 @@ struct Attribute {
}
/// @return a clone of the attribute
std::unique_ptr<Attribute> clone() const {
return std::unique_ptr<Attribute>(doClone());
virtual std::unique_ptr<Attribute> clone(util::CloneVisitor &cv) const = 0;
/// @return a clone of the attribute
virtual std::unique_ptr<Attribute> forceClone(util::CloneVisitor &cv) const {
return clone(cv);
}
private:
virtual std::ostream &doFormat(std::ostream &os) const = 0;
virtual Attribute *doClone() const = 0;
};
/// Attribute containing SrcInfo
@ -48,10 +56,12 @@ struct SrcInfoAttribute : public Attribute {
/// @param info the source info
explicit SrcInfoAttribute(codon::SrcInfo info) : info(std::move(info)) {}
std::unique_ptr<Attribute> clone(util::CloneVisitor &cv) const override {
return std::make_unique<SrcInfoAttribute>(*this);
}
private:
std::ostream &doFormat(std::ostream &os) const override { return os << info; }
Attribute *doClone() const override { return new SrcInfoAttribute(*this); }
};
/// Attribute containing function information
@ -76,10 +86,12 @@ struct KeyValueAttribute : public Attribute {
/// string if none
std::string get(const std::string &key) const;
std::unique_ptr<Attribute> clone(util::CloneVisitor &cv) const override {
return std::make_unique<KeyValueAttribute>(*this);
}
private:
std::ostream &doFormat(std::ostream &os) const override;
Attribute *doClone() const override { return new KeyValueAttribute(*this); }
};
/// Attribute containing type member information
@ -95,10 +107,89 @@ struct MemberAttribute : public Attribute {
explicit MemberAttribute(std::map<std::string, SrcInfo> memberSrcInfo)
: memberSrcInfo(std::move(memberSrcInfo)) {}
std::unique_ptr<Attribute> clone(util::CloneVisitor &cv) const override {
return std::make_unique<MemberAttribute>(*this);
}
private:
std::ostream &doFormat(std::ostream &os) const override;
};
Attribute *doClone() const override { return new MemberAttribute(*this); }
/// Attribute attached to IR structures corresponding to list literals
struct ListLiteralAttribute : public Attribute {
static const std::string AttributeName;
/// values contained in list literal
std::vector<Value *> elements;
explicit ListLiteralAttribute(std::vector<Value *> elements)
: elements(std::move(elements)) {}
std::unique_ptr<Attribute> clone(util::CloneVisitor &cv) const override;
std::unique_ptr<Attribute> forceClone(util::CloneVisitor &cv) const override;
private:
std::ostream &doFormat(std::ostream &os) const override;
};
/// Attribute attached to IR structures corresponding to set literals
struct SetLiteralAttribute : public Attribute {
static const std::string AttributeName;
/// values contained in set literal
std::vector<Value *> elements;
explicit SetLiteralAttribute(std::vector<Value *> elements)
: elements(std::move(elements)) {}
std::unique_ptr<Attribute> clone(util::CloneVisitor &cv) const override;
std::unique_ptr<Attribute> forceClone(util::CloneVisitor &cv) const override;
private:
std::ostream &doFormat(std::ostream &os) const override;
};
/// Attribute attached to IR structures corresponding to dict literals
struct DictLiteralAttribute : public Attribute {
struct KeyValuePair {
Value *key;
Value *value;
};
static const std::string AttributeName;
/// keys and values contained in dict literal
std::vector<KeyValuePair> elements;
explicit DictLiteralAttribute(std::vector<KeyValuePair> elements)
: elements(std::move(elements)) {}
std::unique_ptr<Attribute> clone(util::CloneVisitor &cv) const override;
std::unique_ptr<Attribute> forceClone(util::CloneVisitor &cv) const override;
private:
std::ostream &doFormat(std::ostream &os) const override;
};
/// Attribute attached to IR structures corresponding to partial functions
struct PartialFunctionAttribute : public Attribute {
static const std::string AttributeName;
/// function being called
Func *func;
/// partial arguments, or null if none
/// e.g. "f(a, ..., b)" has elements [a, null, b]
std::vector<Value *> args;
PartialFunctionAttribute(Func *func, std::vector<Value *> args)
: func(func), args(std::move(args)) {}
std::unique_ptr<Attribute> clone(util::CloneVisitor &cv) const override;
std::unique_ptr<Attribute> forceClone(util::CloneVisitor &cv) const override;
private:
std::ostream &doFormat(std::ostream &os) const override;
};
} // namespace ir

View File

@ -82,7 +82,7 @@ public:
for (auto it = other->attributes_begin(); it != other->attributes_end(); ++it) {
const auto *attr = other->getAttribute(*it);
if (attr->needsClone()) {
ctx[id]->setAttribute(attr->clone(), *it);
ctx[id]->setAttribute(attr->clone(*this), *it);
}
}
}
@ -125,7 +125,7 @@ public:
for (auto it = other->attributes_begin(); it != other->attributes_end(); ++it) {
const auto *attr = other->getAttribute(*it);
if (attr->needsClone()) {
ctx[id]->setAttribute(attr->clone(), *it);
ctx[id]->setAttribute(attr->forceClone(*this), *it);
}
}
}