Skip to content

Instantly share code, notes, and snippets.

@fffonion
Created April 2, 2021 14:38
Show Gist options
  • Save fffonion/7092b5b04aff3607fd6e08d3a7a341d5 to your computer and use it in GitHub Desktop.
Save fffonion/7092b5b04aff3607fd6e08d3a7a341d5 to your computer and use it in GitHub Desktop.
LuaJIT FFI avoid incoditionally function create patch
diff --git a/src/lib_ffi.c b/src/lib_ffi.c
index a29014e5..268c948c 100644
--- a/src/lib_ffi.c
+++ b/src/lib_ffi.c
@@ -494,6 +494,7 @@ LJLIB_CF(ffi_new) LJLIB_REC(.)
{
CTState *cts = ctype_cts(L);
CTypeID id = ffi_checkctype(L, cts, NULL);
+ printf("my type is %d\n", id);
CType *ct = ctype_raw(cts, id);
CTSize sz;
CTInfo info = lj_ctype_info(cts, id, &sz);
@@ -537,6 +538,10 @@ LJLIB_CF(ffi_cast) LJLIB_REC(ffi_new)
if (!(ctype_isnum(d->info) || ctype_isptr(d->info) || ctype_isenum(d->info)))
lj_err_arg(L, 1, LJ_ERR_FFI_INVTYPE);
if (!(tviscdata(o) && cdataV(o)->ctypeid == id)) {
+ if tviscdata(o) {
+ printf("id %d -> %d\n", cdataV(o)->ctypeid, id);
+ }
+ printf("lj_cdata_new %d\n", id);
GCcdata *cd = lj_cdata_new(cts, id, d->size);
lj_cconv_ct_tv(cts, d, cdataptr(cd), o, CCF_CAST);
setcdataV(L, o, cd);
diff --git a/src/lj_cparse.c b/src/lj_cparse.c
index 16a1d7b7..b538e164 100644
--- a/src/lj_cparse.c
+++ b/src/lj_cparse.c
@@ -808,6 +808,7 @@ static void cp_push_type(CPDecl *decl, CTypeID id)
CType *ct = ctype_get(decl->cp->cts, id);
CTInfo info = ct->info;
CTSize size = ct->size;
+ CPDeclIdx idx;
switch (ctype_type(info)) {
case CT_STRUCT: case CT_ENUM:
cp_push(decl, CTINFO(CT_TYPEDEF, id), 0); /* Don't copy unique types. */
@@ -834,8 +835,11 @@ static void cp_push_type(CPDecl *decl, CTypeID id)
/* Note: this is not copied to the ct->sib in the C type table. */
break;
case CT_FUNC:
+ printf("CT_FUNC %d\n", id);
/* Copy type, link parameters (shared). */
- decl->stack[cp_push(decl, info, size)].sib = ct->sib;
+ idx = cp_push(decl, info, size);
+ decl->stack[idx].sib = ct->sib;
+ decl->stack[idx].me = id;
break;
default:
/* Copy type, merge common qualifiers. */
@@ -853,12 +857,14 @@ static CTypeID cp_decl_intern(CPState *cp, CPDecl *decl)
CTSize csize = CTSIZE_INVALID;
CTSize cinfo = 0;
do {
+ printf("%d ", idx);
CType *ct = &decl->stack[idx];
CTInfo info = ct->info;
CTInfo size = ct->size;
/* The cid is already part of info for copies of pointers/functions. */
idx = ct->next;
if (ctype_istypedef(info)) {
+ printf("is typedef\n");
lj_assertCP(id == 0, "typedef not at toplevel");
id = ctype_cid(info);
/* Always refetch info/size, since struct/enum may have been completed. */
@@ -871,25 +877,32 @@ static CTypeID cp_decl_intern(CPState *cp, CPDecl *decl)
CTypeID fid;
CTypeID sib;
if (id) {
- CType *refct = ctype_raw(cp->cts, id);
- /* Reject function or refarray return types. */
- if (ctype_isfunc(refct->info) || ctype_isrefarray(refct->info))
- cp_err(cp, LJ_ERR_FFI_INVTYPE);
+ CType *refct = ctype_raw(cp->cts, id);
+ /* Reject function or refarray return types. */
+ if (ctype_isfunc(refct->info) || ctype_isrefarray(refct->info))
+ cp_err(cp, LJ_ERR_FFI_INVTYPE);
+ }
+ printf("is function %d, idx=%d\n", ct->me, idx);
+ if (ct->me < 32768) {
+ // id = ct->me;
+ // continue;
}
/* No intervening attributes allowed, skip forward. */
while (idx) {
- CType *ctn = &decl->stack[idx];
- if (!ctype_isattrib(ctn->info)) break;
- idx = ctn->next; /* Skip attribute. */
+ CType *ctn = &decl->stack[idx];
+ if (!ctype_isattrib(ctn->info)) break;
+ idx = ctn->next; /* Skip attribute. */
}
sib = ct->sib; /* Next line may reallocate the C type table. */
fid = lj_ctype_new(cp->cts, &fct);
+ printf("lj_ctype_new called %d\n", fid);
csize = CTSIZE_INVALID;
fct->info = cinfo = info + id;
fct->size = size;
fct->sib = sib;
id = fid;
} else if (ctype_isattrib(info)) {
+ printf("is attrib\n");
if (ctype_isxattrib(info, CTA_QUAL))
cinfo |= size;
else if (ctype_isxattrib(info, CTA_ALIGN))
@@ -923,6 +936,7 @@ static CTypeID cp_decl_intern(CPState *cp, CPDecl *decl)
}
}
} else if (ctype_isptr(info)) {
+ printf("is ptr\n");
/* Reject pointer/ref to ref. */
if (id && ctype_isref(ctype_raw(cp->cts, id)->info))
cp_err(cp, LJ_ERR_FFI_INVTYPE);
@@ -1903,10 +1917,13 @@ static TValue *cpcparser(lua_State *L, lua_CFunction dummy, void *ud)
UNUSED(dummy);
cframe_errfunc(L->cframe) = -1; /* Inherit error function. */
cp_init(cp);
- if ((cp->mode & CPARSE_MODE_MULTI))
+ if ((cp->mode & CPARSE_MODE_MULTI)){
+ printf("decl multi\n");
cp_decl_multi(cp);
- else
+ }else{
+ printf("decl single\n");
cp_decl_single(cp);
+ }
if (cp->param && cp->param != cp->L->top)
cp_err(cp, LJ_ERR_FFI_NUMPARAM);
lj_assertCP(cp->depth == 0, "unbalanced cparser declaration depth");
diff --git a/src/lj_ctype.c b/src/lj_ctype.c
index 4e913556..1f3bf5ba 100644
--- a/src/lj_ctype.c
+++ b/src/lj_ctype.c
@@ -152,6 +152,7 @@ CTKWDEF(CTKWNAMEDEF)
CTypeID lj_ctype_new(CTState *cts, CType **ctp)
{
CTypeID id = cts->top;
+ printf("a new ctype is created %d\n", id);
CType *ct;
lj_assertCTS(cts->L, "uninitialized cts->L");
if (LJ_UNLIKELY(id >= cts->sizetab)) {
@@ -173,6 +174,7 @@ CTypeID lj_ctype_new(CTState *cts, CType **ctp)
ct->size = 0;
ct->sib = 0;
ct->next = 0;
+ ct->me = id;
setgcrefnull(ct->name);
return id;
}
diff --git a/src/lj_ctype.h b/src/lj_ctype.h
index 49ec71da..c16e0947 100644
--- a/src/lj_ctype.h
+++ b/src/lj_ctype.h
@@ -146,6 +146,7 @@ typedef struct CType {
CTypeID1 sib; /* Sibling element. */
CTypeID1 next; /* Next element in hash chain. */
GCRef name; /* Element name (GCstr). */
+ CTypeID me;
} CType;
#define CTHASH_SIZE 128 /* Number of hash anchors. */
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment