mirror of https://github.com/exaloop/codon.git
Remove vtables from objects (use __id__ only); Add static itemgetter
parent
12c858970d
commit
710a38539f
|
@ -29,7 +29,7 @@
|
|||
#define TYPE_SLICE "std.internal.types.slice.Slice"
|
||||
#define FN_UNWRAP "std.internal.types.optional.unwrap"
|
||||
#define VAR_ARGV "__argv__"
|
||||
#define VAR_VTABLE ".__vtable__"
|
||||
#define VAR_CLSID ".__id__"
|
||||
|
||||
#define MAX_INT_WIDTH 10000
|
||||
#define MAX_REALIZATION_DEPTH 200
|
||||
|
|
|
@ -328,14 +328,12 @@ std::vector<ClassStmt *> SimplifyVisitor::parseBaseClasses(
|
|||
E(Error::CLASS_NO_INHERIT, getSrcInfo(), "internal");
|
||||
|
||||
// Add __vtable__ to parent classes if it is not there already
|
||||
auto var = format("{}.{}", VAR_VTABLE, name);
|
||||
auto var = format("{}.{}", VAR_CLSID, name);
|
||||
if (typeAst && (cachedCls->fields.empty() || cachedCls->fields[0].name != var)) {
|
||||
// LOG("[virtual] vtable({}) := {}", name, var);
|
||||
cachedCls->fields.insert(cachedCls->fields.begin(), {var, nullptr});
|
||||
cachedCls->ast->args.insert(
|
||||
cachedCls->ast->args.begin(),
|
||||
Param{var, transformType(N<IndexExpr>(N<IdExpr>("Ptr"), N<IdExpr>("cobj"))),
|
||||
nullptr});
|
||||
cachedCls->ast->args.insert(cachedCls->ast->args.begin(),
|
||||
Param{var, transformType(N<IdExpr>("int")), nullptr});
|
||||
}
|
||||
|
||||
// Add generics first
|
||||
|
@ -348,8 +346,8 @@ std::vector<ClassStmt *> SimplifyVisitor::parseBaseClasses(
|
|||
if (si == subs.size())
|
||||
E(Error::GENERICS_MISMATCH, cls, ctx->cache->rev(asts.back()->name),
|
||||
nGenerics, subs.size());
|
||||
args.emplace_back(Param{a.name, a.type, transformType(subs[si++], false),
|
||||
Param::HiddenGeneric});
|
||||
args.emplace_back(a.name, a.type, transformType(subs[si++], false),
|
||||
Param::HiddenGeneric);
|
||||
} else if (a.status == Param::HiddenGeneric) {
|
||||
args.emplace_back(a);
|
||||
}
|
||||
|
@ -372,14 +370,12 @@ std::vector<ClassStmt *> SimplifyVisitor::parseBaseClasses(
|
|||
for (auto &a : ast->args) {
|
||||
if (a.status == Param::Normal && !ClassStmt::isClassVar(a)) {
|
||||
auto name = a.name;
|
||||
if (startswith(name, VAR_VTABLE)) { // prevent clashing names
|
||||
int i = 0;
|
||||
for (auto &aa : args)
|
||||
i += bool(startswith(aa.name, a.name));
|
||||
i += aa.name == a.name || startswith(aa.name, a.name + "#");
|
||||
if (i)
|
||||
name = format("{}#{}", name, i);
|
||||
}
|
||||
args.emplace_back(Param{name, a.type, a.defaultValue});
|
||||
args.emplace_back(name, a.type, a.defaultValue);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -510,7 +506,7 @@ StmtPtr SimplifyVisitor::codegenMagic(const std::string &op, const ExprPtr &typE
|
|||
|
||||
std::vector<Param> args;
|
||||
for (auto &a : allArgs)
|
||||
if (!startswith(a.name, VAR_VTABLE))
|
||||
if (!startswith(a.name, VAR_CLSID))
|
||||
args.push_back(a);
|
||||
|
||||
if (op == "new") {
|
||||
|
|
|
@ -172,8 +172,8 @@ ExprPtr TypecheckVisitor::transformDot(DotExpr *expr,
|
|||
return transform(N<BoolExpr>(expr->expr->isStatic()));
|
||||
return nullptr;
|
||||
}
|
||||
// Special case: cls.__vtable_id__
|
||||
if (expr->expr->isType() && expr->member == "__vtable_id__") {
|
||||
// Special case: cls.__id__
|
||||
if (expr->expr->isType() && expr->member == "__id__") {
|
||||
if (auto c = realize(expr->expr->type))
|
||||
return transform(N<IntExpr>(ctx->cache->classes[c->getClass()->name]
|
||||
.realizations[c->getClass()->realizedTypeName()]
|
||||
|
@ -195,11 +195,11 @@ ExprPtr TypecheckVisitor::transformDot(DotExpr *expr,
|
|||
unify(expr->type, ctx->instantiate(bestMethod, typ));
|
||||
|
||||
// Handle virtual calls
|
||||
auto vtableName = format("{}.{}", VAR_VTABLE, typ->name);
|
||||
auto clsidName = format("{}.{}", VAR_CLSID, typ->name);
|
||||
// A function is deemed virtual if it is marked as such and if a base class has a
|
||||
// vtable
|
||||
bool isVirtual = in(ctx->cache->classes[typ->name].virtuals, expr->member);
|
||||
isVirtual &= ctx->findMember(typ->name, vtableName) != nullptr;
|
||||
isVirtual &= ctx->findMember(typ->name, clsidName) != nullptr;
|
||||
isVirtual &= !expr->expr->isType();
|
||||
if (isVirtual && !bestMethod->ast->attributes.has(Attr::StaticMethod) &&
|
||||
!bestMethod->ast->attributes.has(Attr::Property)) {
|
||||
|
@ -217,9 +217,12 @@ ExprPtr TypecheckVisitor::transformDot(DotExpr *expr,
|
|||
NT<IdExpr>("Function"),
|
||||
std::vector<ExprPtr>{NT<InstantiateExpr>(NT<IdExpr>(name), ids),
|
||||
NT<IdExpr>(fn->getRetType()->realizedName())});
|
||||
// Function[Tuple[TArg1, TArg2, ...], TRet](expr.__vtable__T[VIRTUAL_ID])
|
||||
// Function[Tuple[TArg1, TArg2, ...],
|
||||
// TRet](__vtables__[expr.__id__][T[VIRTUAL_ID]])
|
||||
auto e = N<CallExpr>(
|
||||
fnType, N<IndexExpr>(N<DotExpr>(expr->expr, vtableName), N<IntExpr>(vid)));
|
||||
fnType, N<IndexExpr>(N<IndexExpr>(N<IdExpr>("__vtables__"),
|
||||
N<DotExpr>(expr->expr, clsidName)),
|
||||
N<IntExpr>(vid)));
|
||||
return transform(e);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -488,12 +488,10 @@ StmtPtr TypecheckVisitor::prepareVTables() {
|
|||
const auto &fields = ctx->cache->classes[clsTyp->name].fields;
|
||||
auto suite = N<SuiteStmt>();
|
||||
for (auto &f : fields)
|
||||
if (startswith(f.name, VAR_VTABLE)) {
|
||||
if (startswith(f.name, VAR_CLSID)) {
|
||||
suite->stmts.push_back(N<AssignMemberStmt>(
|
||||
N<IdExpr>(varName), f.name,
|
||||
N<IndexExpr>(
|
||||
N<IdExpr>("__vtables__"),
|
||||
N<DotExpr>(N<IdExpr>(clsTyp->realizedName()), "__vtable_id__"))));
|
||||
N<DotExpr>(N<IdExpr>(clsTyp->realizedName()), "__id__")));
|
||||
}
|
||||
|
||||
LOG_REALIZE("[poly] {} : {}", t, *suite);
|
||||
|
@ -516,7 +514,7 @@ StmtPtr TypecheckVisitor::prepareVTables() {
|
|||
auto types = std::vector<ExprPtr>{};
|
||||
auto found = false;
|
||||
for (auto &f : fields) {
|
||||
if (f.name == format("{}.{}", VAR_VTABLE, baseTyp->name)) {
|
||||
if (endswith(f.name, format(".{}", baseTyp->name))) {
|
||||
found = true;
|
||||
break;
|
||||
} else {
|
||||
|
|
|
@ -45,23 +45,6 @@ if(NOT (EXISTS ${CPM_DOWNLOAD_LOCATION}))
|
|||
file(DOWNLOAD https://github.com/TheLartians/CPM.cmake/releases/download/v${CPM_DOWNLOAD_VERSION}/CPM.cmake ${CPM_DOWNLOAD_LOCATION})
|
||||
endif()
|
||||
include(${CPM_DOWNLOAD_LOCATION})
|
||||
CPMAddPackage(
|
||||
NAME libzmq
|
||||
VERSION 4.3.4
|
||||
URL https://github.com/zeromq/libzmq/releases/download/v4.3.4/zeromq-4.3.4.tar.gz
|
||||
EXCLUDE_FROM_ALL YES
|
||||
OPTIONS "WITH_PERF_TOOL OFF"
|
||||
"ZMQ_BUILD_TESTS OFF"
|
||||
"ENABLE_CPACK OFF"
|
||||
"BUILD_SHARED ON"
|
||||
"WITH_LIBSODIUM OFF"
|
||||
"WITH_TLS OFF")
|
||||
CPMAddPackage(
|
||||
NAME cppzmq
|
||||
URL https://github.com/zeromq/cppzmq/archive/refs/tags/v4.8.1.tar.gz
|
||||
VERSION 4.8.1
|
||||
EXCLUDE_FROM_ALL YES
|
||||
OPTIONS "CPPZMQ_BUILD_TESTS OFF")
|
||||
CPMAddPackage(
|
||||
NAME xtl
|
||||
GITHUB_REPOSITORY "xtensor-stack/xtl"
|
||||
|
@ -76,8 +59,8 @@ CPMAddPackage(
|
|||
CPMAddPackage(
|
||||
NAME xeus
|
||||
GITHUB_REPOSITORY "jupyter-xeus/xeus"
|
||||
VERSION 2.2.0
|
||||
GIT_TAG 2.2.0
|
||||
VERSION 3.0.5
|
||||
GIT_TAG 3.0.5
|
||||
EXCLUDE_FROM_ALL YES
|
||||
PATCH_COMMAND patch -N -u CMakeLists.txt --ignore-whitespace -b ${CMAKE_SOURCE_DIR}/xeus.patch || true
|
||||
OPTIONS "BUILD_EXAMPLES OFF"
|
||||
|
|
|
@ -39,9 +39,9 @@ class __internal__:
|
|||
|
||||
def class_set_obj_vtable(pf: T, T: type) -> None:
|
||||
"""
|
||||
Initialize a vtable of a T() object. Compiler generated.
|
||||
Initialize a vtable ID of a T() object. Compiler generated.
|
||||
Corresponds to:
|
||||
pf.__vtable__ = __vtables__[pf.__vtable_id___]
|
||||
pf.__id__ = pf.__id__
|
||||
"""
|
||||
pass
|
||||
|
||||
|
|
|
@ -175,6 +175,7 @@ def attrgetter(attr: Static[str]):
|
|||
return getattr(obj, attr)
|
||||
return getter
|
||||
|
||||
@overload
|
||||
def itemgetter(*items):
|
||||
if staticlen(items) == 1:
|
||||
item = items[0]
|
||||
|
@ -190,6 +191,10 @@ def itemgetter(*items):
|
|||
|
||||
return g
|
||||
|
||||
@overload
|
||||
def itemgetter(item: Static[int]):
|
||||
return lambda o: o[item]
|
||||
|
||||
def methodcaller(name: Static[str], *args, **kwargs):
|
||||
def caller(obj):
|
||||
return getattr(obj, name)(*args, **kwargs)
|
||||
|
|
|
@ -1132,7 +1132,8 @@ class Foo:
|
|||
class Bar:
|
||||
x: float
|
||||
class FooBar(Static[Foo], Static[Bar]):
|
||||
pass #! duplicate data attribute 'x' in class definition
|
||||
pass
|
||||
# right now works as we rename other fields
|
||||
|
||||
#%% keyword_prefix,barebones
|
||||
def foo(return_, pass_, yield_, break_, continue_, print_, assert_):
|
||||
|
|
Loading…
Reference in New Issue