Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support for PUC Lua #320

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
275 changes: 188 additions & 87 deletions Makefile

Large diffs are not rendered by default.

27 changes: 25 additions & 2 deletions src/asdl.lua
Original file line number Diff line number Diff line change
@@ -1,3 +1,22 @@
local function isluajit()
return type(rawget(_G,"jit")) == "table"
end

local iscdata
if isluajit() then
function iscdata(v)
return type(v) == "cdata"
end
else
local ffi = require("ffi")
local function hastype(v)
return ffi.typeof(v)
end
function iscdata(v)
return type(v) == "userdata" and pcall(hastype, v)
end
end

local List = require("terralist")

local Context = {}
Expand Down Expand Up @@ -163,7 +182,11 @@ local function parseAll(text)
end

local function checkbuiltin(t)
return function(v) return type(v) == t end
if t == "cdata" then
return function(v) return iscdata(v) end
else
return function(v) return type(v) == t end
end
end

local function checkoptional(checkt)
Expand Down Expand Up @@ -398,4 +421,4 @@ function Context:Define(text)
end
end
end
package.loaded["asdl"] = { NewContext = NewContext, List = List }
package.loaded["asdl"] = { NewContext = NewContext, List = List, isluajit = isluajit, iscdata = iscdata }
7 changes: 6 additions & 1 deletion src/cudalib.lua
Original file line number Diff line number Diff line change
Expand Up @@ -109,6 +109,7 @@ cudalib.useculink = false
-- this this is only needed for cuda compilation, we load this library lazily below
local terracode = [[
local ffi = require('ffi')
local asdl = require('asdl')
local ef = terralib.externfunction
local struct CUctx_st
local struct CUfunc_st
Expand Down Expand Up @@ -347,7 +348,11 @@ local function dumpsass(data,sz)
local nvdisasm = terralib.cudahome..(ffi.os == "Windows" and "\\bin\\nvdisasm.exe" or "/bin/nvdisasm")
os.execute(string.format("%q --print-life-ranges dump.sass",nvdisasm))
end
dumpsass = terralib.cast({&opaque,uint64} -> {},dumpsass)
if asdl.isluajit() then
dumpsass = terralib.cast({&opaque,uint64} -> {},dumpsass)
else
dumpsass = nil -- FIXME: PUC Lua doesn't support callbacks
end

function cudalib.compile(module,dumpmodule,version,jitload)
version = version or cudalib.localversion()
Expand Down
9 changes: 4 additions & 5 deletions src/geninternalizedfiles.lua
Original file line number Diff line number Diff line change
@@ -1,10 +1,9 @@
local outputfilename = arg[1]
local os,outputfilename = arg[1],arg[2]

local ffi = require("ffi")
local findcmd = ffi.os == "Windows" and "cmd /c dir /b /s \"%s\"" or "find %q"
local findcmd = os == "Windows" and "cmd /c dir /b /s \"%s\"" or "find %q"

local listoffiles = {}
for i = 2,#arg,2 do
for i = 3,#arg,2 do
local path,pattern = arg[i],arg[i+1]
local p = assert(io.popen(findcmd:format(path)))
print(findcmd:format(path))
Expand Down Expand Up @@ -66,4 +65,4 @@ table.insert(output,RegisterTemplate:format(table.concat(names,","),table.concat

local outputfile = io.open(outputfilename,"w")
outputfile:write(table.concat(output))
outputfile:close()
outputfile:close()
9 changes: 9 additions & 0 deletions src/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -73,10 +73,19 @@ static int luapanic(
exit(1);
}

#ifdef TERRA_USE_PUC_LUA
extern "C" {
void preload_ffi(lua_State *L);
}
#endif

int main(int argc, char **argv) {
progname = argv[0];
lua_State *L = luaL_newstate();
luaL_openlibs(L);
#ifdef TERRA_USE_PUC_LUA
preload_ffi(L);
#endif
lua_atpanic(L, luapanic);
terra_Options options;
memset(&options, 0, sizeof(terra_Options));
Expand Down
89 changes: 64 additions & 25 deletions src/tcompiler.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -42,9 +42,22 @@ extern "C" {

using namespace llvm;

#ifdef TERRA_USE_PUC_LUA
#include "tffi.h"
#endif

static const void *tocdata(lua_State *L, int idx) {
#ifdef TERRA_USE_PUC_LUA
// libffi uses a 32 byte header for each cdata object,
// which we have to skip here
return ((char *)lua_topointer(L, idx) + sizeof(struct cdata));
#else
return lua_topointer(L, idx);
#endif
}

#define TERRALIB_FUNCTIONS(_) \
_(inittarget, 1) \
_(freetarget, 0) \
_(initcompilationunit, 1) \
_(compilationunitaddvalue, \
1) /*entry point from lua into compiler to generate LLVM for a function, other \
Expand Down Expand Up @@ -294,6 +307,17 @@ bool HostHasAVX() {
return Features["avx"];
}

static inline void terra_pushpointerwithgc(lua_State *L, void *ptr,
lua_CFunction destructor) {
void **blockaddr = (void **)lua_newuserdata(L, sizeof(void *));
*blockaddr = ptr;
lua_newtable(L);
lua_pushcfunction(L, destructor);
lua_setfield(L, -2, "__gc");
lua_setmetatable(L, -2);
}

int terra_freetarget(lua_State *L);
int terra_inittarget(lua_State *L) {
terra_State *T = terra_getstate(L, 1);
TerraTarget *TT = new TerraTarget();
Expand Down Expand Up @@ -373,14 +397,15 @@ int terra_inittarget(lua_State *L) {
CodeGenOpt::Aggressive);
TT->external = new Module("external", *TT->ctx);
TT->external->setTargetTriple(TT->Triple);
lua_pushlightuserdata(L, TT);
terra_pushpointerwithgc(L, TT, terra_freetarget);
return 1;
}

int terra_freecompilationunit(lua_State *L);
int terra_initcompilationunit(lua_State *L) {
terra_State *T = terra_getstate(L, 1);
TerraCompilationUnit *CU = new TerraCompilationUnit();
TerraTarget *TT = (TerraTarget *)terra_tocdatapointer(L, 1);
TerraTarget *TT = terra_totarget(L, 1);
CU->TT = TT;
CU->TT->nreferences++;
CU->nreferences = 1;
Expand All @@ -404,7 +429,7 @@ int terra_initcompilationunit(lua_State *L) {
llvmutil_addtargetspecificpasses(CU->fpm, TT->tm);
llvmutil_addoptimizationpasses(CU->fpm);
CU->fpm->doInitialization();
lua_pushlightuserdata(L, CU);
terra_pushpointerwithgc(L, CU, terra_freecompilationunit);
return 1;
}

Expand Down Expand Up @@ -487,7 +512,7 @@ void freetarget(TerraTarget *TT) {
}
}
int terra_freetarget(lua_State *L) {
freetarget((TerraTarget *)terra_tocdatapointer(L, 1));
freetarget(terra_totarget(L, 1));
return 0;
}

Expand All @@ -509,7 +534,7 @@ static void freecompilationunit(TerraCompilationUnit *CU) {
}
}
int terra_freecompilationunit(lua_State *L) {
freecompilationunit((TerraCompilationUnit *)terra_tocdatapointer(L, 1));
freecompilationunit(terra_tocompilationunit(L, 1));
return 0;
}

Expand Down Expand Up @@ -2161,7 +2186,7 @@ struct FunctionEmitter {
TType *typ = typeOfValue(exp);
Obj value;
exp->pushfield("value");
const void *data = lua_topointer(L, -1);
const void *data = tocdata(L, -1);
assert(data);
size_t size = CU->getDataLayout().getTypeAllocSize(typ->type);
Value *r;
Expand Down Expand Up @@ -2843,8 +2868,10 @@ static int terra_compilationunitaddvalue(
const char *modulename = (lua_isnil(L, 2)) ? NULL : lua_tostring(L, 2);
lua_pushvalue(L, 3); // the function definition
cu.fromStack(&value);
TerraCompilationUnit *CU = (TerraCompilationUnit *)cu.cd("llvm_cu");
cu.pushfield("llvm_cu");
TerraCompilationUnit *CU = terra_tocompilationunit(L, -1);
assert(CU);
lua_pop(L, 1);

Types Ty(CU);
CCallingConv CC(CU, &Ty);
Expand Down Expand Up @@ -2881,25 +2908,32 @@ static int terra_compilationunitaddvalue(
return 1;
}

static int terra_llvmsizeof(lua_State *L) {
static void RetrieveCUAndType(lua_State *L, TerraCompilationUnit **CUp,
TType **llvmtypp) {
terra_State *T = terra_getstate(L, 1);
int ref_table = lobj_newreftable(L);
TType *llvmtyp;
TerraCompilationUnit *CU;
{
Obj cu, typ, globals;
lua_pushvalue(L, 1);
cu.initFromStack(L, ref_table);
lua_pushvalue(L, 2);
typ.initFromStack(L, ref_table);
cu.obj("symbols", &globals);
CU = (TerraCompilationUnit *)cu.cd("llvm_cu");
CU->symbols = &globals;
llvmtyp = Types(CU).Get(&typ);
CU->symbols = NULL;
cu.pushfield("llvm_cu");
(*CUp) = terra_tocompilationunit(L, -1);
lua_pop(L, 1);
(*CUp)->symbols = &globals;
*llvmtypp = Types(*CUp).Get(&typ);
(*CUp)->symbols = NULL;
}
lobj_removereftable(T->L, ref_table);
lua_pushnumber(T->L, CU->getDataLayout().getTypeAllocSize(llvmtyp->type));
}

static int terra_llvmsizeof(lua_State *L) {
TerraCompilationUnit *CU;
TType *llvmtyp;
RetrieveCUAndType(L, &CU, &llvmtyp);
lua_pushnumber(L, CU->getDataLayout().getTypeAllocSize(llvmtyp->type));
return 1;
}

Expand Down Expand Up @@ -2962,7 +2996,7 @@ static void *JITGlobalValue(TerraCompilationUnit *CU, GlobalValue *gv) {

static int terra_jit(lua_State *L) {
terra_getstate(L, 1);
TerraCompilationUnit *CU = (TerraCompilationUnit *)terra_tocdatapointer(L, 1);
TerraCompilationUnit *CU = terra_tocompilationunit(L, 1);
GlobalValue *gv = (GlobalValue *)lua_touserdata(L, 2);
double begin = CurrentTimeInSeconds();
void *ptr = JITGlobalValue(CU, gv);
Expand All @@ -2973,8 +3007,7 @@ static int terra_jit(lua_State *L) {
}

static int terra_deletefunction(lua_State *L) {
TerraCompilationUnit *CU =
(TerraCompilationUnit *)terra_tocdatapointer(L, lua_upvalueindex(1));
TerraCompilationUnit *CU = terra_tocompilationunit(L, lua_upvalueindex(1));
TerraFunctionState *fstate = (TerraFunctionState *)lua_touserdata(L, -1);
assert(fstate);
Function *func = fstate->func;
Expand Down Expand Up @@ -3149,7 +3182,7 @@ static int terra_saveobjimpl(lua_State *L) {
bool optimize = lua_toboolean(L, 5);

lua_getfield(L, 3, "llvm_cu");
TerraCompilationUnit *CU = (TerraCompilationUnit *)terra_tocdatapointer(L, -1);
TerraCompilationUnit *CU = terra_tocompilationunit(L, -1);
assert(CU);
if (optimize) {
llvmutil_optimizemodule(CU->M, CU->TT->tm);
Expand Down Expand Up @@ -3198,15 +3231,21 @@ static int terra_saveobjimpl(lua_State *L) {
}

static int terra_pointertolightuserdata(lua_State *L) {
lua_pushlightuserdata(L, terra_tocdatapointer(L, -1));
if (10 != lua_type(L, 1))
return 0; // not a cdata, 10 is from LuaJIT sources since it is not exposed in
// the normal API
void *const *cdata = (void *const *)lua_topointer(L, 1);
if (!cdata) return 0;
lua_pushlightuserdata(L, *cdata);
return 1;
}

static int terra_bindtoluaapi(lua_State *L) {
int N = lua_gettop(L);
assert(N >= 1);
void *const *fn = (void *const *)lua_topointer(L, 1);
void *fn = lua_touserdata(L, 1);
assert(fn);
lua_pushcclosure(L, (lua_CFunction)*fn, N - 1);
lua_pushcclosure(L, (lua_CFunction)fn, N - 1);
return 1;
}
#if _MSC_VER < 1900 && defined(_WIN32)
Expand All @@ -3232,7 +3271,7 @@ static int terra_linkllvmimpl(lua_State *L) {
terra_State *T = terra_getstate(L, 1);
(void)T;
std::string Err;
TerraTarget *TT = (TerraTarget *)terra_tocdatapointer(L, 1);
TerraTarget *TT = terra_totarget(L, 1);
size_t length;
const char *filename = lua_tolstring(L, 2, &length);
bool fromstring = lua_toboolean(L, 3);
Expand Down Expand Up @@ -3318,7 +3357,7 @@ static int terra_linkllvmimpl(lua_State *L) {
static int terra_dumpmodule(lua_State *L) {
terra_State *T = terra_getstate(L, 1);
(void)T;
TerraCompilationUnit *CU = (TerraCompilationUnit *)terra_tocdatapointer(L, 1);
TerraCompilationUnit *CU = terra_tocompilationunit(L, 1);
if (CU) TERRA_DUMP_MODULE(CU->M);
return 0;
}
13 changes: 12 additions & 1 deletion src/tcompilerstate.h
Original file line number Diff line number Diff line change
Expand Up @@ -85,4 +85,15 @@ struct terra_CompilerState {
llvm::DenseMap<const void *, TerraFunctionInfo> functioninfo;
};

#endif
static inline TerraCompilationUnit *terra_tocompilationunit(lua_State *L, int idx) {
void *blockaddr = lua_touserdata(L, idx);
if (!blockaddr) return NULL;
return *(TerraCompilationUnit **)blockaddr;
}
static inline TerraTarget *terra_totarget(lua_State *L, int idx) {
void *blockaddr = lua_touserdata(L, idx);
if (!blockaddr) return NULL;
return *(TerraTarget **)blockaddr;
}

#endif
2 changes: 1 addition & 1 deletion src/tcuda.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -267,7 +267,7 @@ int terra_toptx(lua_State *L) {
terra_State *T = terra_getstate(L, 1);
initializeNVVMState(T);
lua_getfield(L, 1, "llvm_cu");
TerraCompilationUnit *CU = (TerraCompilationUnit *)terra_tocdatapointer(L, -1);
TerraCompilationUnit *CU = terra_tocompilationunit(L, -1);
llvm::Module *M = CU->M;
int annotations = 2;
int dumpmodule = lua_toboolean(L, 3);
Expand Down
2 changes: 1 addition & 1 deletion src/tcuda.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,4 +5,4 @@ struct terra_State;
int terra_cudainit(struct terra_State* T);
int terra_cudafree(struct terra_State* T);

#endif
#endif
Loading