diff --git a/ASTNode.h b/ASTNode.h index 3a30814..8ac6e1c 100644 --- a/ASTNode.h +++ b/ASTNode.h @@ -12,7 +12,7 @@ public: NODE_INVALID, NODE_NODELIST, NODE_OBJECT, NODE_UNARY, NODE_BINARY, NODE_COMPARE, NODE_SLICE, NODE_STORE, NODE_RETURN, NODE_NAME, NODE_DELETE, NODE_FUNCTION, NODE_CLASS, NODE_CALL, NODE_IMPORT, - NODE_TUPLE, NODE_LIST, NODE_MAP, NODE_SUBSCR, NODE_PRINT, + NODE_TUPLE, NODE_LIST, NODE_SET, NODE_MAP, NODE_SUBSCR, NODE_PRINT, NODE_CONVERT, NODE_KEYWORD, NODE_RAISE, NODE_EXEC, NODE_BLOCK, NODE_COMPREHENSION, NODE_LOADBUILDCLASS, NODE_AWAITABLE, NODE_FORMATTEDVALUE, NODE_JOINEDSTR, NODE_CONST_MAP, @@ -358,6 +358,18 @@ private: value_t m_values; }; +class ASTSet : public ASTNode { +public: + typedef std::set> value_t; + + ASTSet(value_t values) + : ASTNode(NODE_SET), m_values(std::move(values)) { } + + const value_t& values() const { return m_values; } + +private: + value_t m_values; +}; class ASTMap : public ASTNode { public: diff --git a/ASTree.cpp b/ASTree.cpp index 1c283a1..a95b8ef 100644 --- a/ASTree.cpp +++ b/ASTree.cpp @@ -322,6 +322,16 @@ PycRef BuildFromCode(PycRef code, PycModule* mod) stack.push(new ASTList(values)); } break; + case Pyc::BUILD_SET_A: + { + ASTSet::value_t values; + for (int i=0; iverCompare(3, 5) >= 0) { auto map = new ASTMap; @@ -1547,6 +1557,33 @@ PycRef BuildFromCode(PycRef code, PycModule* mod) } } break; + case Pyc::SET_UPDATE_A: + { + PycRef rhs = stack.top(); + stack.pop(); + PycRef lhs = stack.top().cast(); + stack.pop(); + + if (rhs.type() != ASTNode::NODE_OBJECT) { + fprintf(stderr, "Unsupported argument found for SET_UPDATE\n"); + break; + } + + // I've only ever seen this be a TYPE_FROZENSET, but let's be careful... + PycRef obj = rhs.cast()->object(); + if (obj->type() != PycObject::TYPE_FROZENSET) { + fprintf(stderr, "Unsupported argument type found for SET_UPDATE\n"); + break; + } + + ASTSet::value_t result = lhs->values(); + for (const auto& it : obj.cast()->values()) { + result.insert(new ASTObject(it)); + } + + stack.push(new ASTSet(result)); + } + break; case Pyc::LIST_EXTEND_A: { PycRef rhs = stack.top(); @@ -2838,6 +2875,24 @@ void print_src(PycRef node, PycModule* mod) fputs("]", pyc_output); } break; + case ASTNode::NODE_SET: + { + fputs("{", pyc_output); + bool first = true; + cur_indent++; + for (const auto& val : node.cast()->values()) { + if (first) + fputs("\n", pyc_output); + else + fputs(",\n", pyc_output); + start_line(cur_indent); + print_src(val, mod); + first = false; + } + cur_indent--; + fputs("}", pyc_output); + } + break; case ASTNode::NODE_COMPREHENSION: { PycRef comp = node.cast();