改善了一些实现
This commit is contained in:
parent
e5caca5350
commit
6fd99c95a1
58
acpa.exe.stackdump
Normal file
58
acpa.exe.stackdump
Normal file
@ -0,0 +1,58 @@
|
|||||||
|
Exception: STATUS_STACK_OVERFLOW at rip=000100418AEB
|
||||||
|
rax=00000007FFE0410F rbx=00000007FFE040E0 rcx=00000007FFE040F0
|
||||||
|
rdx=00000007FFE0410F rsi=00000007FFE04108 rdi=0000000000000001
|
||||||
|
r8 =00000007FFE0410F r9 =0000000000000001 r10=0000000800000000
|
||||||
|
r11=000000010040D18C r12=00000007FFFFCC70 r13=00000007FFFFCDF0
|
||||||
|
r14=0000000000000000 r15=0000000000000000
|
||||||
|
rbp=00000007FFE04020 rsp=00000007FFE04000
|
||||||
|
program=C:\Users\lcw\Desktop\code\acpa\acpa.exe, pid 724, thread
|
||||||
|
cs=0033 ds=002B es=002B fs=0053 gs=002B ss=002B
|
||||||
|
Stack trace:
|
||||||
|
Frame Function Args
|
||||||
|
0007FFE04020 000100418AEB (0007FFE0410F, 000000000000, 000000000000, 0007FFE040A0) acpa.exe+0x18AEB
|
||||||
|
0007FFE04050 000100418BD0 (0007FFE0410F, 000A001E79F0, 000000000001, 0007FFE04108) acpa.exe+0x18BD0
|
||||||
|
0007FFE040A0 000100424A96 (000000000001, 0007FFE0410F, 0001004345DB, 0007FFE04108) acpa.exe+0x24A96
|
||||||
|
0007FFE04110 000100403F0F (000A001E79F4, 000A001E79F0, 0007FFE0432C, 0007FFE0435C) acpa.exe+0x3F0F
|
||||||
|
0007FFE041C0 0001004067B1 (000A001E79F4, 000A001E79F4, 000100000007, 000100451110) acpa.exe+0x67B1
|
||||||
|
0007FFE04370 00010040702E (000000000006, 000A001E79F0, 000A001E79F4, 000A001E79F4) acpa.exe+0x702E
|
||||||
|
0007FFE043D0 0001004070C7 (0007FFE045C0, 000A001E7980, 7FFA4F13C600, 0007FFE04440) acpa.exe+0x70C7
|
||||||
|
0007FFE04470 000100405BF3 (000A001E79F4, 000A001E79F4, 000100000005, 000100451110) acpa.exe+0x5BF3
|
||||||
|
0007FFE048A0 0001004062B2 (000A00000004, 000000000000, 000A001E79A0, 0007FFE04910) acpa.exe+0x62B2
|
||||||
|
0007FFE04900 00010040634B (000A001E7980, 000A001E7910, 7FFA4F13C600, 0007FFE04970) acpa.exe+0x634B
|
||||||
|
0007FFE049A0 000100405D12 (000A001E7984, 000A001E7984, 000100000005, 000100451110) acpa.exe+0x5D12
|
||||||
|
0007FFE04DD0 0001004062B2 (000A00000004, 000000000000, 000A001E7930, 0007FFE04E40) acpa.exe+0x62B2
|
||||||
|
0007FFE04E30 00010040634B (000A001E7910, 000A001E78A0, 7FFA4F13C600, 0007FFE04EA0) acpa.exe+0x634B
|
||||||
|
0007FFE04ED0 000100405D12 (000A001E7914, 000A001E7914, 000100000005, 000100451110) acpa.exe+0x5D12
|
||||||
|
0007FFE05300 0001004062B2 (000A00000004, 000000000000, 000A001E78C0, 0007FFE05370) acpa.exe+0x62B2
|
||||||
|
0007FFE05360 00010040634B (000A001E78A0, 000A001E7830, 7FFA4F13C600, 0007FFE053D0) acpa.exe+0x634B
|
||||||
|
0007FFE05400 000100405D12 (000A001E78A4, 000A001E78A4, 000100000005, 000100451110) acpa.exe+0x5D12
|
||||||
|
0007FFE05830 0001004062B2 (000A00000004, 000000000000, 000A001E7850, 0007FFE058A0) acpa.exe+0x62B2
|
||||||
|
0007FFE05890 00010040634B (000A001E7830, 000A001E77C0, 7FFA4F13C600, 0007FFE05900) acpa.exe+0x634B
|
||||||
|
0007FFE05930 000100405D12 (000A001E7834, 000A001E7834, 000100000005, 000100451110) acpa.exe+0x5D12
|
||||||
|
0007FFE05D60 0001004062B2 (000A00000004, 000000000000, 000A001E77E0, 0007FFE05DD0) acpa.exe+0x62B2
|
||||||
|
0007FFE05DC0 00010040634B (000A001E77C0, 000A001E7750, 7FFA4F13C600, 0007FFE05E30) acpa.exe+0x634B
|
||||||
|
0007FFE05E60 000100405D12 (000A001E77C4, 000A001E77C4, 000100000005, 000100451110) acpa.exe+0x5D12
|
||||||
|
0007FFE06290 0001004062B2 (000A00000004, 000000000000, 000A001E7770, 0007FFE06300) acpa.exe+0x62B2
|
||||||
|
0007FFE062F0 00010040634B (000A001E7750, 000A001E76E0, 7FFA4F13C600, 0007FFE06360) acpa.exe+0x634B
|
||||||
|
0007FFE06390 000100405D12 (000A001E7754, 000A001E7754, 000100000005, 000100451110) acpa.exe+0x5D12
|
||||||
|
0007FFE067C0 0001004062B2 (000A00000004, 000000000000, 000A001E7700, 0007FFE06830) acpa.exe+0x62B2
|
||||||
|
0007FFE06820 00010040634B (000A001E76E0, 000A001E7670, 7FFA4F13C600, 0007FFE06890) acpa.exe+0x634B
|
||||||
|
0007FFE068C0 000100405D12 (000A001E76E4, 000A001E76E4, 000100000005, 000100451110) acpa.exe+0x5D12
|
||||||
|
0007FFE06CF0 0001004062B2 (000A00000004, 000000000000, 000A001E7690, 0007FFE06D60) acpa.exe+0x62B2
|
||||||
|
0007FFE06D50 00010040634B (000A001E7670, 000A001E7600, 7FFA4F13C600, 0007FFE06DC0) acpa.exe+0x634B
|
||||||
|
0007FFE06DF0 000100405D12 (000A001E7674, 000A001E7674, 000100000005, 000100451110) acpa.exe+0x5D12
|
||||||
|
End of stack trace (more stack frames may be present)
|
||||||
|
Loaded modules:
|
||||||
|
000100400000 acpa.exe
|
||||||
|
7FFAE2E50000 ntdll.dll
|
||||||
|
7FFAE14F0000 KERNEL32.DLL
|
||||||
|
7FFAE0420000 KERNELBASE.dll
|
||||||
|
7FFA4EF10000 cygwin1.dll
|
||||||
|
0003FB660000 cygstdc++-6.dll
|
||||||
|
0003FF100000 cyggcc_s-seh-1.dll
|
||||||
|
7FFAE2370000 advapi32.dll
|
||||||
|
7FFAE1BB0000 msvcrt.dll
|
||||||
|
7FFAE0F80000 sechost.dll
|
||||||
|
7FFAE1640000 RPCRT4.dll
|
||||||
|
7FFADF8A0000 CRYPTBASE.DLL
|
||||||
|
7FFAE0A60000 bcryptPrimitives.dll
|
@ -2,11 +2,15 @@
|
|||||||
#define ACPA_ELEMENT_H
|
#define ACPA_ELEMENT_H
|
||||||
|
|
||||||
#include <map>
|
#include <map>
|
||||||
|
#include <set>
|
||||||
|
#include <utility>
|
||||||
#include <memory>
|
#include <memory>
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
using std::map;
|
using std::map;
|
||||||
|
using std::set;
|
||||||
|
using std::pair;
|
||||||
using std::shared_ptr;
|
using std::shared_ptr;
|
||||||
using std::string;
|
using std::string;
|
||||||
using std::vector;
|
using std::vector;
|
||||||
@ -27,27 +31,46 @@ struct Struct {
|
|||||||
};
|
};
|
||||||
|
|
||||||
struct ValType {
|
struct ValType {
|
||||||
virtual int type() const = 0;
|
enum Type {
|
||||||
|
TEMPLATE,
|
||||||
|
STRUCT,
|
||||||
|
FUNCTION
|
||||||
|
};
|
||||||
|
virtual ValType::Type type() const = 0;
|
||||||
|
virtual shared_ptr<ValType> struct_replace(shared_ptr<StructType>, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>>&) = 0;
|
||||||
|
virtual shared_ptr<ValType> function_replace(const map<shared_ptr<TemplateType>, shared_ptr<ValType>>&, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>>&) = 0;
|
||||||
|
virtual bool sameType(shared_ptr<ValType>, set<pair<shared_ptr<TemplateType>, shared_ptr<TemplateType>>>&) = 0;
|
||||||
virtual ~ValType() = default;
|
virtual ~ValType() = default;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct TemplateType : ValType {
|
struct TemplateType : ValType {
|
||||||
int type() const override;
|
ValType::Type type() const override;
|
||||||
|
shared_ptr<ValType> struct_replace(shared_ptr<StructType>, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>>&) override;
|
||||||
|
shared_ptr<ValType> function_replace(const map<shared_ptr<TemplateType>, shared_ptr<ValType>>&, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>>&) override;
|
||||||
|
bool sameType(shared_ptr<ValType>, set<pair<shared_ptr<TemplateType>, shared_ptr<TemplateType>>>&) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct StructType : ValType {
|
struct StructType : ValType {
|
||||||
int type() const override;
|
ValType::Type type() const override;
|
||||||
|
shared_ptr<ValType> struct_replace(shared_ptr<StructType>, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>>&) override;
|
||||||
|
shared_ptr<ValType> function_replace(const map<shared_ptr<TemplateType>, shared_ptr<ValType>>&, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>>&) override;
|
||||||
|
bool sameType(shared_ptr<ValType>, set<pair<shared_ptr<TemplateType>, shared_ptr<TemplateType>>>&) override;
|
||||||
shared_ptr<Struct> str;
|
shared_ptr<Struct> str;
|
||||||
map<shared_ptr<TemplateType>, shared_ptr<ValType>> mp;
|
map<shared_ptr<TemplateType>, shared_ptr<ValType>> mp;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct FunctionType : ValType {
|
struct FunctionType : ValType {
|
||||||
int type() const override;
|
ValType::Type type() const override;
|
||||||
|
shared_ptr<ValType> struct_replace(shared_ptr<StructType>, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>>&) override;
|
||||||
|
shared_ptr<ValType> function_replace(const map<shared_ptr<TemplateType>, shared_ptr<ValType>>&, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>>&) override;
|
||||||
|
bool sameType(shared_ptr<ValType>, set<pair<shared_ptr<TemplateType>, shared_ptr<TemplateType>>>&) override;
|
||||||
vector<shared_ptr<TemplateType>> c1;
|
vector<shared_ptr<TemplateType>> c1;
|
||||||
vector<shared_ptr<ValType>> c2;
|
vector<shared_ptr<ValType>> c2;
|
||||||
shared_ptr<ValType> c3;
|
shared_ptr<ValType> c3;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
shared_ptr<ValType> struct_replace(shared_ptr<ValType>, shared_ptr<StructType>);
|
||||||
|
shared_ptr<ValType> function_replace(shared_ptr<ValType>, const map<shared_ptr<TemplateType>, shared_ptr<ValType>>&);
|
||||||
bool sameType(shared_ptr<ValType>, shared_ptr<ValType>);
|
bool sameType(shared_ptr<ValType>, shared_ptr<ValType>);
|
||||||
|
|
||||||
#endif
|
#endif
|
200
src/element.cpp
200
src/element.cpp
@ -1,19 +1,158 @@
|
|||||||
#include "element.h"
|
#include "element.h"
|
||||||
#include <assert.h>
|
#include <assert.h>
|
||||||
#include <set>
|
|
||||||
|
|
||||||
using namespace std;
|
using namespace std;
|
||||||
|
|
||||||
int TemplateType::type() const {
|
ValType::Type TemplateType::type() const {
|
||||||
return 0;
|
return ValType::TEMPLATE;
|
||||||
}
|
}
|
||||||
|
|
||||||
int StructType::type() const {
|
ValType::Type StructType::type() const {
|
||||||
return 1;
|
return ValType::STRUCT;
|
||||||
}
|
}
|
||||||
|
|
||||||
int FunctionType::type() const {
|
ValType::Type FunctionType::type() const {
|
||||||
return 2;
|
return ValType::FUNCTION;
|
||||||
|
}
|
||||||
|
|
||||||
|
shared_ptr<ValType> TemplateType::struct_replace(shared_ptr<StructType> ut, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>> &eq) {
|
||||||
|
auto vt = shared_ptr<TemplateType>(this);
|
||||||
|
auto it1 = ut->mp.find(vt);
|
||||||
|
auto it2 = eq.find(vt);
|
||||||
|
assert(it1 == ut->mp.end() || it2 == eq.end());
|
||||||
|
if (it1 != ut->mp.end()) {
|
||||||
|
return it1->second;
|
||||||
|
}
|
||||||
|
if (it2 != eq.end()) {
|
||||||
|
return static_pointer_cast<ValType>(it2->second);
|
||||||
|
}
|
||||||
|
return static_pointer_cast<ValType>(vt);
|
||||||
|
}
|
||||||
|
|
||||||
|
shared_ptr<ValType> StructType::struct_replace(shared_ptr<StructType> ut, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>> &eq) {
|
||||||
|
auto tt = make_shared<StructType>();
|
||||||
|
(*tt) = (*ut);
|
||||||
|
set<shared_ptr<Struct>> vis;
|
||||||
|
for (auto u = str; u.get() != nullptr; u = u->fa.lock()) {
|
||||||
|
vis.insert(u);
|
||||||
|
}
|
||||||
|
for (auto u = ut->str; u.get() != nullptr && vis.find(u) == vis.end();
|
||||||
|
u = u->fa.lock()) {
|
||||||
|
for (auto tem : u->c1) {
|
||||||
|
tt->mp.erase(tem);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for (auto pr : mp) {
|
||||||
|
tt->mp[pr.first] = pr.second->struct_replace(ut, eq);
|
||||||
|
}
|
||||||
|
return static_pointer_cast<ValType>(tt);
|
||||||
|
}
|
||||||
|
|
||||||
|
shared_ptr<ValType> FunctionType::struct_replace(shared_ptr<StructType> ut, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>> &eq) {
|
||||||
|
auto tt = make_shared<FunctionType>();
|
||||||
|
for (size_t i = 0; i < c1.size(); i++) {
|
||||||
|
tt->c1.push_back(eq[c1[i]] = make_shared<TemplateType>());
|
||||||
|
}
|
||||||
|
for (auto cc : c2) {
|
||||||
|
tt->c2.push_back(cc->struct_replace(ut, eq));
|
||||||
|
}
|
||||||
|
tt->c3 = c3->struct_replace(ut, eq);
|
||||||
|
for (size_t i = 0; i < c1.size(); i++) {
|
||||||
|
eq.erase(c1[i]);
|
||||||
|
}
|
||||||
|
return static_pointer_cast<ValType>(tt);
|
||||||
|
}
|
||||||
|
|
||||||
|
shared_ptr<ValType> struct_replace(shared_ptr<ValType> vt, shared_ptr<StructType> ut) {
|
||||||
|
static map<shared_ptr<TemplateType>, shared_ptr<TemplateType>> eq;
|
||||||
|
return vt->struct_replace(ut,eq);
|
||||||
|
}
|
||||||
|
|
||||||
|
shared_ptr<ValType> TemplateType::function_replace(const map<shared_ptr<TemplateType>, shared_ptr<ValType>> &mp, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>> &eq) {
|
||||||
|
auto tt = shared_ptr<TemplateType>(this);
|
||||||
|
auto it1 = mp.find(tt);
|
||||||
|
auto it2 = eq.find(tt);
|
||||||
|
assert(it1 == mp.end() || it2 == eq.end());
|
||||||
|
if (it1 != mp.end()) {
|
||||||
|
return it1->second;
|
||||||
|
}
|
||||||
|
if (it2 != eq.end()) {
|
||||||
|
return static_pointer_cast<ValType>(it2->second);
|
||||||
|
}
|
||||||
|
return static_pointer_cast<ValType>(tt);
|
||||||
|
}
|
||||||
|
|
||||||
|
shared_ptr<ValType> StructType::function_replace(const map<shared_ptr<TemplateType>, shared_ptr<ValType>> &mp, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>> &eq) {
|
||||||
|
auto tt = make_shared<StructType>();
|
||||||
|
(*tt) = (*this);
|
||||||
|
for (auto& pr : tt->mp) {
|
||||||
|
pr.second = pr.second->function_replace(mp, eq);
|
||||||
|
}
|
||||||
|
return tt;
|
||||||
|
}
|
||||||
|
|
||||||
|
shared_ptr<ValType> FunctionType::function_replace(const map<shared_ptr<TemplateType>, shared_ptr<ValType>> &mp, map<shared_ptr<TemplateType>, shared_ptr<TemplateType>> &eq) {
|
||||||
|
auto tt = make_shared<FunctionType>();
|
||||||
|
for (size_t i = 0; i < c1.size(); i++) {
|
||||||
|
tt->c1.push_back(eq[c1[i]] = make_shared<TemplateType>());
|
||||||
|
}
|
||||||
|
for (auto cc : c2) {
|
||||||
|
tt->c2.push_back(cc->function_replace(mp, eq));
|
||||||
|
}
|
||||||
|
tt->c3 = c3->function_replace(mp, eq);
|
||||||
|
for (size_t i = 0; i < c1.size(); i++) {
|
||||||
|
eq.erase(c1[i]);
|
||||||
|
}
|
||||||
|
return static_pointer_cast<ValType>(tt);
|
||||||
|
}
|
||||||
|
|
||||||
|
shared_ptr<ValType> function_replace(shared_ptr<ValType> t, const map<shared_ptr<TemplateType>, shared_ptr<ValType>>& mp) {
|
||||||
|
static map<shared_ptr<TemplateType>, shared_ptr<TemplateType>> eq;
|
||||||
|
return t->function_replace(mp, eq);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool TemplateType::sameType(shared_ptr<ValType> b, set<pair<shared_ptr<TemplateType>, shared_ptr<TemplateType>>> &eq) {
|
||||||
|
auto aa = shared_ptr<TemplateType>(this), bb = static_pointer_cast<TemplateType>(b);
|
||||||
|
return aa == bb || eq.find({aa, bb}) != eq.end();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool StructType::sameType(shared_ptr<ValType> b, set<pair<shared_ptr<TemplateType>, shared_ptr<TemplateType>>> &eq) {
|
||||||
|
auto bb = static_pointer_cast<StructType>(b);
|
||||||
|
if (str != bb->str) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
assert(mp.size() == bb->mp.size());
|
||||||
|
for (auto ia = mp.begin(), ib = bb->mp.begin(); ia != mp.end(); ia++, ib++) {
|
||||||
|
assert(ia->first == ib->first);
|
||||||
|
if (!ia->second->sameType(ib->second, eq)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool FunctionType::sameType(shared_ptr<ValType> b, set<pair<shared_ptr<TemplateType>, shared_ptr<TemplateType>>> &eq) {
|
||||||
|
auto bb = static_pointer_cast<FunctionType>(b);
|
||||||
|
if (c1.size() != bb->c1.size() || c2.size() != bb->c2.size()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
for (size_t i = 0; i < c1.size(); i++) {
|
||||||
|
eq.insert({c1[i], bb->c1[i]});
|
||||||
|
}
|
||||||
|
bool flag = 1;
|
||||||
|
for (size_t i = 0; i < c2.size(); i++) {
|
||||||
|
if (!c2[i]->sameType(bb->c2[i], eq)) {
|
||||||
|
flag = 0;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!flag && !c3->sameType(bb->c3, eq)) {
|
||||||
|
flag = 0;
|
||||||
|
}
|
||||||
|
for (size_t i = 0; i < c1.size(); i++) {
|
||||||
|
eq.erase({c1[i], bb->c1[i]});
|
||||||
|
}
|
||||||
|
return flag;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool sameType(shared_ptr<ValType> a, shared_ptr<ValType> b) {
|
bool sameType(shared_ptr<ValType> a, shared_ptr<ValType> b) {
|
||||||
@ -21,50 +160,5 @@ bool sameType(shared_ptr<ValType> a, shared_ptr<ValType> b) {
|
|||||||
if (a->type() != b->type()) {
|
if (a->type() != b->type()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if (a->type() == 0) {
|
return a->sameType(b, eq);
|
||||||
auto aa = static_pointer_cast<TemplateType>(a),
|
|
||||||
bb = static_pointer_cast<TemplateType>(b);
|
|
||||||
return aa == bb || eq.find({aa, bb}) != eq.end();
|
|
||||||
}
|
|
||||||
if (a->type() == 1) {
|
|
||||||
auto aa = static_pointer_cast<StructType>(a);
|
|
||||||
auto bb = static_pointer_cast<StructType>(b);
|
|
||||||
if (aa->str != bb->str) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
assert(aa->mp.size() == bb->mp.size());
|
|
||||||
for (auto ia = aa->mp.begin(), ib = bb->mp.begin(); ia != aa->mp.end();
|
|
||||||
ia++, ib++) {
|
|
||||||
assert(ia->first == ib->first);
|
|
||||||
if (!sameType(ia->second, ib->second)) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
// if(a->type()==2)
|
|
||||||
{
|
|
||||||
auto aa = static_pointer_cast<FunctionType>(a);
|
|
||||||
auto bb = static_pointer_cast<FunctionType>(b);
|
|
||||||
if (aa->c1.size() != bb->c1.size() || aa->c2.size() != bb->c2.size()) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
for (size_t i = 0; i < aa->c1.size(); i++) {
|
|
||||||
eq.insert({aa->c1[i], bb->c1[i]});
|
|
||||||
}
|
|
||||||
bool flag = 1;
|
|
||||||
for (size_t i = 0; i < aa->c2.size(); i++) {
|
|
||||||
if (!sameType(aa->c2[i], bb->c2[i])) {
|
|
||||||
flag = 0;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (!flag && !sameType(aa->c3, bb->c3)) {
|
|
||||||
flag = 0;
|
|
||||||
}
|
|
||||||
for (size_t i = 0; i < aa->c1.size(); i++) {
|
|
||||||
eq.erase({aa->c1[i], bb->c1[i]});
|
|
||||||
}
|
|
||||||
return flag;
|
|
||||||
}
|
|
||||||
}
|
}
|
153
src/work.cpp
153
src/work.cpp
@ -1,6 +1,5 @@
|
|||||||
#include "work.h"
|
#include "work.h"
|
||||||
#include <assert.h>
|
#include <assert.h>
|
||||||
#include <set>
|
|
||||||
|
|
||||||
using namespace std;
|
using namespace std;
|
||||||
|
|
||||||
@ -18,27 +17,32 @@ vector<Token> tokens;
|
|||||||
// }
|
// }
|
||||||
|
|
||||||
struct Def {
|
struct Def {
|
||||||
virtual int type() const = 0;
|
enum Type {
|
||||||
|
TEMPLATE,
|
||||||
|
STRUCT,
|
||||||
|
VAR
|
||||||
|
};
|
||||||
|
virtual Def::Type type() const = 0;
|
||||||
virtual ~Def() = default;
|
virtual ~Def() = default;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct DefTemplate : Def {
|
struct DefTemplate : Def {
|
||||||
int type() const override {
|
Def::Type type() const override {
|
||||||
return 0;
|
return Def::TEMPLATE;
|
||||||
}
|
}
|
||||||
shared_ptr<TemplateType> def_template;
|
shared_ptr<TemplateType> def_template;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct DefStruct : Def {
|
struct DefStruct : Def {
|
||||||
int type() const override {
|
Def::Type type() const override {
|
||||||
return 1;
|
return Def::STRUCT;
|
||||||
}
|
}
|
||||||
shared_ptr<Struct> def_struct;
|
shared_ptr<Struct> def_struct;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct DefVar : Def {
|
struct DefVar : Def {
|
||||||
int type() const override {
|
Def::Type type() const override {
|
||||||
return 2;
|
return Def::VAR;
|
||||||
}
|
}
|
||||||
shared_ptr<ValType> def_var;
|
shared_ptr<ValType> def_var;
|
||||||
};
|
};
|
||||||
@ -82,101 +86,6 @@ vector<pair<string, shared_ptr<ValType>>> createPars();
|
|||||||
pair<string, shared_ptr<Struct>> createStruct();
|
pair<string, shared_ptr<Struct>> createStruct();
|
||||||
pair<string, shared_ptr<ValType>> createVar();
|
pair<string, shared_ptr<ValType>> createVar();
|
||||||
|
|
||||||
shared_ptr<ValType> struct_replace(shared_ptr<ValType> vt, shared_ptr<StructType> ut) {
|
|
||||||
static map<shared_ptr<TemplateType>, shared_ptr<TemplateType>> eq;
|
|
||||||
if (vt->type() == 0) {
|
|
||||||
auto vtt = static_pointer_cast<TemplateType>(vt);
|
|
||||||
auto it1 = ut->mp.find(vtt);
|
|
||||||
auto it2 = eq.find(vtt);
|
|
||||||
assert(it1 == ut->mp.end() || it2 == eq.end());
|
|
||||||
if (it1 != ut->mp.end()) {
|
|
||||||
return it1->second;
|
|
||||||
}
|
|
||||||
if (it2 != eq.end()) {
|
|
||||||
return static_pointer_cast<ValType>(it2->second);
|
|
||||||
}
|
|
||||||
return vt;
|
|
||||||
}
|
|
||||||
if (vt->type() == 1) {
|
|
||||||
auto vtt = static_pointer_cast<StructType>(vt);
|
|
||||||
auto tt = make_shared<StructType>();
|
|
||||||
(*tt) = (*ut);
|
|
||||||
set<shared_ptr<Struct>> vis;
|
|
||||||
for (auto u = vtt->str; u.get() != nullptr; u = u->fa.lock()) {
|
|
||||||
vis.insert(u);
|
|
||||||
}
|
|
||||||
for (auto u = ut->str; u.get() != nullptr && vis.find(u) == vis.end();
|
|
||||||
u = u->fa.lock()) {
|
|
||||||
for (auto tem : u->c1) {
|
|
||||||
tt->mp.erase(tem);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
for (auto pr : vtt->mp) {
|
|
||||||
tt->mp[pr.first] = struct_replace(pr.second, ut);
|
|
||||||
}
|
|
||||||
return static_pointer_cast<ValType>(tt);
|
|
||||||
}
|
|
||||||
// if(vt->type()==2)
|
|
||||||
{
|
|
||||||
auto vtt = static_pointer_cast<FunctionType>(vt);
|
|
||||||
auto tt = make_shared<FunctionType>();
|
|
||||||
for (size_t i = 0; i < vtt->c1.size(); i++) {
|
|
||||||
tt->c1.push_back(eq[vtt->c1[i]] = make_shared<TemplateType>());
|
|
||||||
}
|
|
||||||
for (auto cc : vtt->c2) {
|
|
||||||
tt->c2.push_back(struct_replace(cc, ut));
|
|
||||||
}
|
|
||||||
tt->c3 = struct_replace(vtt->c3, ut);
|
|
||||||
for (size_t i = 0; i < vtt->c1.size(); i++) {
|
|
||||||
eq.erase(vtt->c1[i]);
|
|
||||||
}
|
|
||||||
return static_pointer_cast<ValType>(tt);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
shared_ptr<ValType> function_replace(
|
|
||||||
shared_ptr<ValType> t,
|
|
||||||
const map<shared_ptr<TemplateType>, shared_ptr<ValType>>& mp) {
|
|
||||||
static map<shared_ptr<TemplateType>, shared_ptr<TemplateType>> eq;
|
|
||||||
if (t->type() == 0) {
|
|
||||||
auto tt = static_pointer_cast<TemplateType>(t);
|
|
||||||
auto it1 = mp.find(tt);
|
|
||||||
auto it2 = eq.find(tt);
|
|
||||||
assert(it1 == mp.end() || it2 == eq.end());
|
|
||||||
if (it1 != mp.end()) {
|
|
||||||
return it1->second;
|
|
||||||
}
|
|
||||||
if (it2 != eq.end()) {
|
|
||||||
return static_pointer_cast<ValType>(it2->second);
|
|
||||||
}
|
|
||||||
return t;
|
|
||||||
}
|
|
||||||
if (t->type() == 1) {
|
|
||||||
auto tt = make_shared<StructType>();
|
|
||||||
(*tt) = (*static_pointer_cast<StructType>(t));
|
|
||||||
for (auto& pr : static_pointer_cast<StructType>(tt)->mp) {
|
|
||||||
pr.second = function_replace(pr.second, mp);
|
|
||||||
}
|
|
||||||
return tt;
|
|
||||||
}
|
|
||||||
// if(t->type()==2)
|
|
||||||
{
|
|
||||||
auto vt = static_pointer_cast<FunctionType>(t);
|
|
||||||
auto tt = make_shared<FunctionType>();
|
|
||||||
for (size_t i = 0; i < vt->c1.size(); i++) {
|
|
||||||
tt->c1.push_back(eq[vt->c1[i]] = make_shared<TemplateType>());
|
|
||||||
}
|
|
||||||
for (auto cc : vt->c2) {
|
|
||||||
tt->c2.push_back(function_replace(cc, mp));
|
|
||||||
}
|
|
||||||
tt->c3 = function_replace(vt->c3, mp);
|
|
||||||
for (size_t i = 0; i < vt->c1.size(); i++) {
|
|
||||||
eq.erase(vt->c1[i]);
|
|
||||||
}
|
|
||||||
return static_pointer_cast<ValType>(tt);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
shared_ptr<ValType> _createVal(shared_ptr<StructType> ft) {
|
shared_ptr<ValType> _createVal(shared_ptr<StructType> ft) {
|
||||||
auto str = ft->str;
|
auto str = ft->str;
|
||||||
auto s = jump(TokenType::ID);
|
auto s = jump(TokenType::ID);
|
||||||
@ -184,7 +93,8 @@ shared_ptr<ValType> _createVal(shared_ptr<StructType> ft) {
|
|||||||
printf("error on line %d", tokens[pt - 1].line), exit(0);
|
printf("error on line %d", tokens[pt - 1].line), exit(0);
|
||||||
}
|
}
|
||||||
auto t = struct_replace(str->vars[s], ft);
|
auto t = struct_replace(str->vars[s], ft);
|
||||||
while (t->type() == 2 && (preview(TokenType::LT) || preview(TokenType::LP))) {
|
while (t->type() == ValType::FUNCTION
|
||||||
|
&& (preview(TokenType::LT) || preview(TokenType::LP))) {
|
||||||
auto tt = static_pointer_cast<FunctionType>(t);
|
auto tt = static_pointer_cast<FunctionType>(t);
|
||||||
vector<shared_ptr<ValType>> types;
|
vector<shared_ptr<ValType>> types;
|
||||||
if (preview(TokenType::LT)) {
|
if (preview(TokenType::LT)) {
|
||||||
@ -215,7 +125,7 @@ shared_ptr<ValType> _createVal(shared_ptr<StructType> ft) {
|
|||||||
if (!preview(TokenType::DOT)) {
|
if (!preview(TokenType::DOT)) {
|
||||||
return t;
|
return t;
|
||||||
}
|
}
|
||||||
if (t->type() != 1) {
|
if (t->type() != ValType::STRUCT) {
|
||||||
printf("error on line %d", tokens[pt].line), exit(0);
|
printf("error on line %d", tokens[pt].line), exit(0);
|
||||||
}
|
}
|
||||||
pt++;
|
pt++;
|
||||||
@ -275,14 +185,14 @@ shared_ptr<ValType> createVal() {
|
|||||||
flag = 1;
|
flag = 1;
|
||||||
} else if (preview(TokenType::ID)) {
|
} else if (preview(TokenType::ID)) {
|
||||||
auto s = tokens[pt].s;
|
auto s = tokens[pt].s;
|
||||||
if (ndefs.find(s) != ndefs.end() && ndefs[s]->type() == 1) {
|
if (ndefs.find(s) != ndefs.end() && ndefs[s]->type() == Def::STRUCT) {
|
||||||
flag = 1;
|
flag = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (flag) {
|
if (flag) {
|
||||||
t = createType();
|
t = createType();
|
||||||
if (t->type() != 1) {
|
if (t->type() != ValType::STRUCT) {
|
||||||
printf("error on line %d", tokens[pt - 1].line), exit(0);
|
printf("error on line %d", tokens[pt - 1].line), exit(0);
|
||||||
}
|
}
|
||||||
auto tt = static_pointer_cast<StructType>(t);
|
auto tt = static_pointer_cast<StructType>(t);
|
||||||
@ -302,13 +212,14 @@ shared_ptr<ValType> createVal() {
|
|||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
auto s = jump(TokenType::ID);
|
auto s = jump(TokenType::ID);
|
||||||
if (ndefs.find(s) == ndefs.end() || ndefs[s]->type() != 2) {
|
if (ndefs.find(s) == ndefs.end() || ndefs[s]->type() != Def::VAR) {
|
||||||
printf("error on line %d", tokens[pt - 1].line), exit(0);
|
printf("error on line %d", tokens[pt - 1].line), exit(0);
|
||||||
}
|
}
|
||||||
t = static_pointer_cast<DefVar>(ndefs[s])->def_var;
|
t = static_pointer_cast<DefVar>(ndefs[s])->def_var;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
while (t->type() == 2 && (preview(TokenType::LT) || preview(TokenType::LP))) {
|
while (t->type() == ValType::FUNCTION
|
||||||
|
&& (preview(TokenType::LT) || preview(TokenType::LP))) {
|
||||||
auto tt = static_pointer_cast<FunctionType>(t);
|
auto tt = static_pointer_cast<FunctionType>(t);
|
||||||
vector<shared_ptr<ValType>> types;
|
vector<shared_ptr<ValType>> types;
|
||||||
if (preview(TokenType::LT)) {
|
if (preview(TokenType::LT)) {
|
||||||
@ -339,7 +250,7 @@ shared_ptr<ValType> createVal() {
|
|||||||
if (!preview(TokenType::DOT)) {
|
if (!preview(TokenType::DOT)) {
|
||||||
return t;
|
return t;
|
||||||
}
|
}
|
||||||
if (t->type() != 1) {
|
if (t->type() != ValType::STRUCT) {
|
||||||
printf("error on line %d", tokens[pt].line), exit(0);
|
printf("error on line %d", tokens[pt].line), exit(0);
|
||||||
}
|
}
|
||||||
pt++;
|
pt++;
|
||||||
@ -351,9 +262,7 @@ vector<shared_ptr<ValType>> createVals() {
|
|||||||
jump(TokenType::LP);
|
jump(TokenType::LP);
|
||||||
if (!preview(TokenType::RP)) {
|
if (!preview(TokenType::RP)) {
|
||||||
auto single = [&]() { vals.push_back(createVal()); };
|
auto single = [&]() { vals.push_back(createVal()); };
|
||||||
for (single(); preview(TokenType::COMMA); pt++, single()) {
|
for (single(); preview(TokenType::COMMA); pt++, single()) {}
|
||||||
;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
jump(TokenType::RP);
|
jump(TokenType::RP);
|
||||||
return vals;
|
return vals;
|
||||||
@ -411,10 +320,10 @@ shared_ptr<ValType> createType() {
|
|||||||
jump(TokenType::RP);
|
jump(TokenType::RP);
|
||||||
} else {
|
} else {
|
||||||
auto s = jump(TokenType::ID);
|
auto s = jump(TokenType::ID);
|
||||||
if (ndefs.find(s) == ndefs.end() || ndefs[s]->type() == 2) {
|
if (ndefs.find(s) == ndefs.end() || ndefs[s]->type() == Def::VAR) {
|
||||||
printf("error on line %d", tokens[pt - 1].line), exit(0);
|
printf("error on line %d", tokens[pt - 1].line), exit(0);
|
||||||
}
|
}
|
||||||
if (ndefs[s]->type() == 1) {
|
if (ndefs[s]->type() == Def::STRUCT) {
|
||||||
auto tt = make_shared<StructType>();
|
auto tt = make_shared<StructType>();
|
||||||
tt->str = static_pointer_cast<DefStruct>(ndefs[s])->def_struct;
|
tt->str = static_pointer_cast<DefStruct>(ndefs[s])->def_struct;
|
||||||
vector<shared_ptr<ValType>> types;
|
vector<shared_ptr<ValType>> types;
|
||||||
@ -436,7 +345,7 @@ shared_ptr<ValType> createType() {
|
|||||||
if (!preview(TokenType::SCOPE)) {
|
if (!preview(TokenType::SCOPE)) {
|
||||||
return t;
|
return t;
|
||||||
}
|
}
|
||||||
if (t->type() != 1) {
|
if (t->type() != ValType::STRUCT) {
|
||||||
printf("error on line %d", tokens[pt].line), exit(0);
|
printf("error on line %d", tokens[pt].line), exit(0);
|
||||||
}
|
}
|
||||||
pt++;
|
pt++;
|
||||||
@ -448,9 +357,7 @@ vector<shared_ptr<ValType>> createTypes() {
|
|||||||
jump(TokenType::LT);
|
jump(TokenType::LT);
|
||||||
if (!preview(TokenType::RT)) {
|
if (!preview(TokenType::RT)) {
|
||||||
auto single = [&]() { types.push_back(createType()); };
|
auto single = [&]() { types.push_back(createType()); };
|
||||||
for (single(); preview(TokenType::COMMA); pt++, single()) {
|
for (single(); preview(TokenType::COMMA); pt++, single()) {}
|
||||||
;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
jump(TokenType::RT);
|
jump(TokenType::RT);
|
||||||
return types;
|
return types;
|
||||||
@ -471,9 +378,7 @@ vector<pair<string, shared_ptr<TemplateType>>> createTems() {
|
|||||||
ndefs[s] = static_pointer_cast<Def>(d);
|
ndefs[s] = static_pointer_cast<Def>(d);
|
||||||
tems.push_back({s, x});
|
tems.push_back({s, x});
|
||||||
};
|
};
|
||||||
for (single(); preview(TokenType::COMMA); pt++, single()) {
|
for (single(); preview(TokenType::COMMA); pt++, single()) {}
|
||||||
;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
jump(TokenType::RT);
|
jump(TokenType::RT);
|
||||||
return tems;
|
return tems;
|
||||||
@ -495,9 +400,7 @@ vector<pair<string, shared_ptr<ValType>>> createPars() {
|
|||||||
ndefs[s] = static_pointer_cast<Def>(d);
|
ndefs[s] = static_pointer_cast<Def>(d);
|
||||||
pars.push_back({s, t});
|
pars.push_back({s, t});
|
||||||
};
|
};
|
||||||
for (single(); preview(TokenType::COMMA); pt++, single()) {
|
for (single(); preview(TokenType::COMMA); pt++, single()) {}
|
||||||
;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
jump(TokenType::RP);
|
jump(TokenType::RP);
|
||||||
return pars;
|
return pars;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user