allow cl compiler (MSVC) to work as preprocessor

This commit is contained in:
sonoro1234
2018-10-09 20:13:56 +02:00
parent 2d3cf59b21
commit 812af400f1
5 changed files with 48 additions and 22 deletions

View File

@@ -27,9 +27,9 @@ Notes:
# using generator # using generator
* you will need LuaJIT (https://github.com/LuaJIT/LuaJIT.git better 2.1 branch) or precompiled for linux/macOS/windows in https://luapower.com/luajit/download * you will need LuaJIT (https://github.com/LuaJIT/LuaJIT.git better 2.1 branch) or precompiled for linux/macOS/windows in https://luapower.com/luajit/download
* need also gcc compiler for doing preprocessing (In windows MinGW-W64-builds for example) or clang * need also gcc compiler for doing preprocessing (In windows MinGW-W64-builds for example) or clang or cl (MSVC)
* update `imgui` folder to the version you desire. * update `imgui` folder to the version you desire.
* edit `generator/generator.bat` (or make a .sh version and please PR) to choose between gcc or clang. Run it with gcc or clang and LuaJIT on your PATH. * edit `generator/generator.bat` (or make a .sh version and please PR) to choose between gcc, clang or cl. Run it with gcc, clang or cl and LuaJIT on your PATH.
* as a result some files are generated: `cimgui.cpp` and `cimgui.h` for compiling and some lua/json files with information about the binding: `definitions.json` with function info, `structs_and_enums.json` with struct and enum info, `impl_definitions.json` with functions from the implementations info. * as a result some files are generated: `cimgui.cpp` and `cimgui.h` for compiling and some lua/json files with information about the binding: `definitions.json` with function info, `structs_and_enums.json` with struct and enum info, `impl_definitions.json` with functions from the implementations info.
# generate binding # generate binding

View File

@@ -40,7 +40,7 @@ typedef struct ImColor_Simple { ImVec4_Simple Value;} ImColor_Simple;
#ifdef CIMGUI_DEFINE_ENUMS_AND_STRUCTS #ifdef CIMGUI_DEFINE_ENUMS_AND_STRUCTS
struct ImDrawChannel;
typedef struct CustomRect CustomRect; typedef struct CustomRect CustomRect;
typedef struct GlyphRangesBuilder GlyphRangesBuilder; typedef struct GlyphRangesBuilder GlyphRangesBuilder;
typedef struct ImFontGlyph ImFontGlyph; typedef struct ImFontGlyph ImFontGlyph;
@@ -69,7 +69,6 @@ typedef struct ImDrawList ImDrawList;
typedef struct ImDrawData ImDrawData; typedef struct ImDrawData ImDrawData;
typedef struct ImDrawCmd ImDrawCmd; typedef struct ImDrawCmd ImDrawCmd;
typedef struct ImDrawChannel ImDrawChannel; typedef struct ImDrawChannel ImDrawChannel;
struct ImDrawChannel;
struct ImDrawCmd; struct ImDrawCmd;
struct ImDrawData; struct ImDrawData;
struct ImDrawList; struct ImDrawList;

View File

@@ -14,7 +14,7 @@
:: set PATH=%PATH%;C:\luaGL;C:\i686-7.2.0-release-posix-dwarf-rt_v5-rev1\mingw32\bin; :: set PATH=%PATH%;C:\luaGL;C:\i686-7.2.0-release-posix-dwarf-rt_v5-rev1\mingw32\bin;
:: set PATH=%PATH%;C:\luaGL\sources\luajit-master\luajit-master\bin\mingw32;C:\mingw32\bin; :: set PATH=%PATH%;C:\luaGL\sources\luajit-master\luajit-master\bin\mingw32;C:\mingw32\bin;
::process files ::process files
:: arg[1] compiler name gcc or clang :: arg[1] compiler name gcc, clang or cl
:: arg[2..n] name of implementations to generate :: arg[2..n] name of implementations to generate
luajit ./generator.lua "gcc" glfw opengl3 opengl2 sdl luajit ./generator.lua "gcc" glfw opengl3 opengl2 sdl

View File

@@ -6,9 +6,19 @@ assert(_VERSION=='Lua 5.1',"Must use LuaJIT")
assert(bit,"Must use LuaJIT") assert(bit,"Must use LuaJIT")
local script_args = {...} local script_args = {...}
local COMPILER = script_args[1] local COMPILER = script_args[1]
local CPRE,CTEST
if COMPILER == "gcc" or COMPILER == "clang" then
CPRE = COMPILER..[[ -E -DIMGUI_DISABLE_OBSOLETE_FUNCTIONS -DIMGUI_API="" -DIMGUI_IMPL_API="" ]]
CTEST = COMPILER.." --version"
elseif COMPILER == "cl" then
CPRE = COMPILER..[[ /E /DIMGUI_DISABLE_OBSOLETE_FUNCTIONS /DIMGUI_API="" /DIMGUI_IMPL_API="" ]]
CTEST = COMPILER
else
error("not prepared for "..COMPILER)
end
--test compiler present --test compiler present
local HAVE_COMPILER local HAVE_COMPILER
local pipe,err = io.popen(COMPILER.." --version","r") local pipe,err = io.popen(CTEST,"r")
if pipe then if pipe then
local str = pipe:read"*a" local str = pipe:read"*a"
print(str) print(str)
@@ -110,7 +120,12 @@ local function filelines(file)
end end
--iterates lines from a gcc/clang -E in a specific location --iterates lines from a gcc/clang -E in a specific location
local function location(file,locpathT) local function location(file,locpathT)
local location_re = '^# (%d+) "([^"]*)"' local location_re
if COMPILER == "cl" then
location_re = '^#line (%d+) "([^"]*)"'
else --gcc, clang
location_re = '^# (%d+) "([^"]*)"'
end
local path_reT = {} local path_reT = {}
for i,locpath in ipairs(locpathT) do for i,locpath in ipairs(locpathT) do
table.insert(path_reT,'^(.*[\\/])('..locpath..')%.h$') table.insert(path_reT,'^(.*[\\/])('..locpath..')%.h$')
@@ -133,7 +148,9 @@ local function location(file,locpathT)
return nil return nil
end end
end end
if line:sub(1,1) == "#" then if #line==0 then --nothing on emptyline
elseif not line:match("%S") then --nothing if only spaces
elseif line:sub(1,1) == "#" then
-- Is this a location pragma? -- Is this a location pragma?
local loc_num_t,location_match = line:match(location_re) local loc_num_t,location_match = line:match(location_re)
if location_match then if location_match then
@@ -162,7 +179,7 @@ local function location(file,locpathT)
--return line,loc_num_real, which_location --return line,loc_num_real, which_location
end end
end end
until false until false --forever
end end
return location_it return location_it
end end
@@ -267,7 +284,9 @@ local function clean_spaces(cad)
end end
local function split_comment(line) local function split_comment(line)
local comment = line:match("(%s*//.*)") or "" local comment = line:match("(%s*//.*)") or ""
return line:gsub("%s*//.*",""),comment line = line:gsub("%s*//.*","")
line = line:gsub("%s*$","")
return line,comment
end end
local function get_manuals(def) local function get_manuals(def)
return cimgui_manuals[def.ov_cimguiname] or cimgui_manuals[def.cimguiname] return cimgui_manuals[def.ov_cimguiname] or cimgui_manuals[def.cimguiname]
@@ -289,7 +308,7 @@ end
local function struct_parser() local function struct_parser()
local function_re = "(%a*%w+%s*%b())" --"(%a*%w+%b())" --"(%a*%w+%s+%w+%b())" local function_re = "(%a*%w+%s*%b())" --"(%a*%w+%b())" --"(%a*%w+%s+%w+%b())"
local function_closing_re = "}" local function_closing_re = "}"
local function_closed_re = "[;}]$" local function_closed_re = "[;}]%s*$"
local operator_re = "operator.-%b()" local operator_re = "operator.-%b()"
local functype_re = "(%(%*)[%w_]+(%)%([^%(%)]*%))" local functype_re = "(%(%*)[%w_]+(%)%([^%(%)]*%))"
local initial_comment_re = [[^%s*//.*]] local initial_comment_re = [[^%s*//.*]]
@@ -308,6 +327,7 @@ local function struct_parser()
--if in_function discard --if in_function discard
if in_functionst then if in_functionst then
--table.insert(structcdefs,"en function:"..line) --debug
if line:match(function_closing_re) then if line:match(function_closing_re) then
in_functionst = false in_functionst = false
--print("in function:",line) --print("in function:",line)
@@ -315,16 +335,13 @@ local function struct_parser()
return return
end end
if (line:match(function_re) or line:match(operator_re)) and not line:match("typedef.*%b().*%b().*") if (line:match(function_re) or line:match(operator_re)) and not line:match("typedef.*%b().*%b().*")
and not line:match(functype_re) then and not line:match(functype_re) then
--table.insert(structcdefs,"function test2:"..line) --debug
if not line:match(function_closed_re) then if not line:match(function_closed_re) then
--print("match:",line) --print("match:",line)
in_functionst = true in_functionst = true
end end
--else
--table.insert(structcdefs,linecommented)
elseif line:match("template") then elseif line:match("template") then
--nothing --nothing
elseif line:match("public:") then elseif line:match("public:") then
@@ -333,7 +350,6 @@ local function struct_parser()
local linea = line:gsub("%S+",{class="struct",mutable=""}) local linea = line:gsub("%S+",{class="struct",mutable=""})
linea = linea:gsub("(%b<>)","/*%1*/") --comment template parameters linea = linea:gsub("(%b<>)","/*%1*/") --comment template parameters
table.insert(structcdefs,linea..comment) table.insert(structcdefs,linea..comment)
end end
return return
end end
@@ -797,6 +813,11 @@ local function gen_structs_and_enums_table(cdefs)
if (#enumnames > 0) then if (#enumnames > 0) then
assert(#structnames==0,"enum in struct") assert(#structnames==0,"enum in struct")
-- if #structnames~=0 then
-- print(line,#line)
-- print(linecom,#linecom)
-- error"enuminstruct"
-- end
if line:match(struct_closing_re) and not line:match(struct_op_close_re) then if line:match(struct_closing_re) and not line:match(struct_op_close_re) then
enumnames[#enumnames] = nil enumnames[#enumnames] = nil
break break
@@ -930,13 +951,15 @@ local function gen_structs_and_enums(cdefs)
-- ImVector special treatment -- ImVector special treatment
if structnames[#structnames] == "ImVector" then if structnames[#structnames] == "ImVector" then
if line:match(struct_closing_re) then if line:match(struct_closing_re) then
table.insert(outtab,[[struct ImVector table.insert(outtab,[[
struct ImVector
{ {
int Size; int Size;
int Capacity; int Capacity;
void* Data; void* Data;
}; };
typedef struct ImVector ImVector;]]) typedef struct ImVector ImVector;
]])
structnames[#structnames] = nil structnames[#structnames] = nil
end end
break -- dont write break -- dont write
@@ -1210,6 +1233,7 @@ local function check_arg_detection(fdefs,typedefs)
print"-----------------end check arg detection-----------------------" print"-----------------end check arg detection-----------------------"
end end
local function get_defines(t) local function get_defines(t)
if COMPILER == "cl" then print"can't get defines with cl compiler"; return {} end
local pipe,err = io.popen(COMPILER..[[ -E -dM -DIMGUI_DISABLE_OBSOLETE_FUNCTIONS -DIMGUI_API="" -DIMGUI_IMPL_API="" ../imgui/imgui.h]],"r") local pipe,err = io.popen(COMPILER..[[ -E -dM -DIMGUI_DISABLE_OBSOLETE_FUNCTIONS -DIMGUI_API="" -DIMGUI_IMPL_API="" ../imgui/imgui.h]],"r")
local defines = {} local defines = {}
while true do while true do
@@ -1329,7 +1353,7 @@ print"------------------generation with precompiler------------------------"
local pFP,pSTP,typedefs_dict2 local pFP,pSTP,typedefs_dict2
if HAVE_COMPILER then if HAVE_COMPILER then
local pipe,err = io.popen(COMPILER..[[ -E -DIMGUI_DISABLE_OBSOLETE_FUNCTIONS -DIMGUI_API="" -DIMGUI_IMPL_API="" ../imgui/imgui.h]],"r") local pipe,err = io.popen(CPRE..[[../imgui/imgui.h]],"r")
if not pipe then if not pipe then
error("could not execute gcc "..err) error("could not execute gcc "..err)
@@ -1338,13 +1362,17 @@ end
pSTP = struct_parser() --overwrite pSTP = struct_parser() --overwrite
pFP = func_parser() --overwrite pFP = func_parser() --overwrite
--local linesl = {}
for line in location(pipe,{"imgui"}) do for line in location(pipe,{"imgui"}) do
local line, comment = split_comment(line) local line, comment = split_comment(line)
--line = clean_spaces(line) --line = clean_spaces(line)
--table.insert(linesl,line)
pSTP.insert(line,comment) pSTP.insert(line,comment)
pFP.insert(line,comment) pFP.insert(line,comment)
end end
pipe:close() pipe:close()
--save_data("./LINES.txt",table.concat(linesl,"\n"))
--save_data("./STPLINES.txt",table.concat(pSTP.lines,"\n"))
local ovstr = pFP:compute_overloads() local ovstr = pFP:compute_overloads()
ADDnonUDT(pFP) ADDnonUDT(pFP)
save_data("./output/overloads.txt",ovstr) save_data("./output/overloads.txt",ovstr)
@@ -1376,7 +1404,7 @@ if #implementations > 0 then
local locati = [[imgui_impl_]].. impl local locati = [[imgui_impl_]].. impl
local pipe,err local pipe,err
if HAVE_COMPILER then if HAVE_COMPILER then
pipe,err = io.popen(COMPILER..[[ -E -DIMGUI_DISABLE_OBSOLETE_FUNCTIONS -DIMGUI_API="" -DIMGUI_IMPL_API="" ]] ..source,"r") pipe,err = io.popen(CPRE..source,"r")
else else
pipe,err = io.open(source,"r") pipe,err = io.open(source,"r")
end end

View File

@@ -40,7 +40,7 @@ typedef struct ImColor_Simple { ImVec4_Simple Value;} ImColor_Simple;
#ifdef CIMGUI_DEFINE_ENUMS_AND_STRUCTS #ifdef CIMGUI_DEFINE_ENUMS_AND_STRUCTS
struct ImDrawChannel;
typedef struct CustomRect CustomRect; typedef struct CustomRect CustomRect;
typedef struct GlyphRangesBuilder GlyphRangesBuilder; typedef struct GlyphRangesBuilder GlyphRangesBuilder;
typedef struct ImFontGlyph ImFontGlyph; typedef struct ImFontGlyph ImFontGlyph;
@@ -69,7 +69,6 @@ typedef struct ImDrawList ImDrawList;
typedef struct ImDrawData ImDrawData; typedef struct ImDrawData ImDrawData;
typedef struct ImDrawCmd ImDrawCmd; typedef struct ImDrawCmd ImDrawCmd;
typedef struct ImDrawChannel ImDrawChannel; typedef struct ImDrawChannel ImDrawChannel;
struct ImDrawChannel;
struct ImDrawCmd; struct ImDrawCmd;
struct ImDrawData; struct ImDrawData;
struct ImDrawList; struct ImDrawList;