diff options
author | Mike Pall <mike> | 2024-01-22 19:06:36 +0100 |
---|---|---|
committer | Mike Pall <mike> | 2024-01-22 19:06:36 +0100 |
commit | 4b90f6c4d7420139c135435e1580acb52ea18436 (patch) | |
tree | 1c3543b6baa4f8b30a33e8a624b60edc6feb0206 /src/host | |
parent | c525bcb9024510cad9e170e12b6209aedb330f83 (diff) | |
download | luajit-4b90f6c4d7420139c135435e1580acb52ea18436.tar.gz luajit-4b90f6c4d7420139c135435e1580acb52ea18436.tar.bz2 luajit-4b90f6c4d7420139c135435e1580acb52ea18436.zip |
Add cross-32/64 bit and deterministic bytecode generation.
Contributed by Peter Cawley. #993 #1008
Diffstat (limited to 'src/host')
-rw-r--r-- | src/host/genlibbc.lua | 91 |
1 files changed, 50 insertions, 41 deletions
diff --git a/src/host/genlibbc.lua b/src/host/genlibbc.lua index 3621c3f5..e697fceb 100644 --- a/src/host/genlibbc.lua +++ b/src/host/genlibbc.lua | |||
@@ -138,65 +138,73 @@ local function fixup_dump(dump, fixup) | |||
138 | return { dump = ndump, startbc = startbc, sizebc = sizebc } | 138 | return { dump = ndump, startbc = startbc, sizebc = sizebc } |
139 | end | 139 | end |
140 | 140 | ||
141 | local function find_defs(src) | 141 | local function find_defs(src, mode) |
142 | local defs = {} | 142 | local defs = {} |
143 | for name, code in string.gmatch(src, "LJLIB_LUA%(([^)]*)%)%s*/%*(.-)%*/") do | 143 | for name, code in string.gmatch(src, "LJLIB_LUA%(([^)]*)%)%s*/%*(.-)%*/") do |
144 | local env = {} | ||
145 | local tcode, fixup = transform_lua(code) | 144 | local tcode, fixup = transform_lua(code) |
146 | local func = assert(load(tcode, "", nil, env))() | 145 | local func = assert(load(tcode, "", mode)) |
147 | defs[name] = fixup_dump(string.dump(func, true), fixup) | 146 | defs[name] = fixup_dump(string.dump(func, mode), fixup) |
148 | defs[#defs+1] = name | 147 | defs[#defs+1] = name |
149 | end | 148 | end |
150 | return defs | 149 | return defs |
151 | end | 150 | end |
152 | 151 | ||
153 | local function gen_header(defs) | 152 | local function gen_header(defs32, defs64) |
154 | local t = {} | 153 | local t = {} |
155 | local function w(x) t[#t+1] = x end | 154 | local function w(x) t[#t+1] = x end |
156 | w("/* This is a generated file. DO NOT EDIT! */\n\n") | 155 | w("/* This is a generated file. DO NOT EDIT! */\n\n") |
157 | w("static const int libbc_endian = ") w(isbe and 1 or 0) w(";\n\n") | 156 | w("static const int libbc_endian = ") w(isbe and 1 or 0) w(";\n\n") |
158 | local s, sb = "", "" | 157 | for j,defs in ipairs{defs64, defs32} do |
159 | for i,name in ipairs(defs) do | 158 | local s, sb = "", "" |
160 | local d = defs[name] | 159 | for i,name in ipairs(defs) do |
161 | s = s .. d.dump | 160 | local d = defs[name] |
162 | sb = sb .. string.char(i) .. ("\0"):rep(d.startbc - 1) | 161 | s = s .. d.dump |
163 | .. (isbe and "\0\0\0\255" or "\255\0\0\0"):rep(d.sizebc) | 162 | sb = sb .. string.char(i) .. ("\0"):rep(d.startbc - 1) |
164 | .. ("\0"):rep(#d.dump - d.startbc - d.sizebc*4) | 163 | .. (isbe and "\0\0\0\255" or "\255\0\0\0"):rep(d.sizebc) |
165 | end | 164 | .. ("\0"):rep(#d.dump - d.startbc - d.sizebc*4) |
166 | w("static const uint8_t libbc_code[] = {\n") | 165 | end |
167 | local n = 0 | 166 | if j == 1 then |
168 | for i=1,#s do | 167 | w("static const uint8_t libbc_code[] = {\n#if LJ_FR2\n") |
169 | local x = string.byte(s, i) | ||
170 | local xb = string.byte(sb, i) | ||
171 | if xb == 255 then | ||
172 | local name = BCN[x] | ||
173 | local m = #name + 4 | ||
174 | if n + m > 78 then n = 0; w("\n") end | ||
175 | n = n + m | ||
176 | w("BC_"); w(name) | ||
177 | else | 168 | else |
178 | local m = x < 10 and 2 or (x < 100 and 3 or 4) | 169 | w("\n#else\n") |
179 | if xb == 0 then | 170 | end |
171 | local n = 0 | ||
172 | for i=1,#s do | ||
173 | local x = string.byte(s, i) | ||
174 | local xb = string.byte(sb, i) | ||
175 | if xb == 255 then | ||
176 | local name = BCN[x] | ||
177 | local m = #name + 4 | ||
180 | if n + m > 78 then n = 0; w("\n") end | 178 | if n + m > 78 then n = 0; w("\n") end |
179 | n = n + m | ||
180 | w("BC_"); w(name) | ||
181 | else | 181 | else |
182 | local name = defs[xb]:gsub("_", ".") | 182 | local m = x < 10 and 2 or (x < 100 and 3 or 4) |
183 | if n ~= 0 then w("\n") end | 183 | if xb == 0 then |
184 | w("/* "); w(name); w(" */ ") | 184 | if n + m > 78 then n = 0; w("\n") end |
185 | n = #name + 7 | 185 | else |
186 | local name = defs[xb]:gsub("_", ".") | ||
187 | if n ~= 0 then w("\n") end | ||
188 | w("/* "); w(name); w(" */ ") | ||
189 | n = #name + 7 | ||
190 | end | ||
191 | n = n + m | ||
192 | w(x) | ||
186 | end | 193 | end |
187 | n = n + m | 194 | w(",") |
188 | w(x) | ||
189 | end | 195 | end |
190 | w(",") | ||
191 | end | 196 | end |
192 | w("\n0\n};\n\n") | 197 | w("\n#endif\n0\n};\n\n") |
193 | w("static const struct { const char *name; int ofs; } libbc_map[] = {\n") | 198 | w("static const struct { const char *name; int ofs; } libbc_map[] = {\n") |
194 | local m = 0 | 199 | local m32, m64 = 0, 0 |
195 | for _,name in ipairs(defs) do | 200 | for i,name in ipairs(defs32) do |
196 | w('{"'); w(name); w('",'); w(m) w('},\n') | 201 | assert(name == defs64[i]) |
197 | m = m + #defs[name].dump | 202 | w('{"'); w(name); w('",'); w(m32) w('},\n') |
203 | m32 = m32 + #defs32[name].dump | ||
204 | m64 = m64 + #defs64[name].dump | ||
205 | assert(m32 == m64) | ||
198 | end | 206 | end |
199 | w("{NULL,"); w(m); w("}\n};\n\n") | 207 | w("{NULL,"); w(m32); w("}\n};\n\n") |
200 | return table.concat(t) | 208 | return table.concat(t) |
201 | end | 209 | end |
202 | 210 | ||
@@ -219,7 +227,8 @@ end | |||
219 | 227 | ||
220 | local outfile = parse_arg(arg) | 228 | local outfile = parse_arg(arg) |
221 | local src = read_files(arg) | 229 | local src = read_files(arg) |
222 | local defs = find_defs(src) | 230 | local defs32 = find_defs(src, "Wdts") |
223 | local hdr = gen_header(defs) | 231 | local defs64 = find_defs(src, "Xdts") |
232 | local hdr = gen_header(defs32, defs64) | ||
224 | write_file(outfile, hdr) | 233 | write_file(outfile, hdr) |
225 | 234 | ||