diff options
author | Mike Pall <mike> | 2016-05-28 05:03:18 +0200 |
---|---|---|
committer | Mike Pall <mike> | 2016-05-28 05:09:24 +0200 |
commit | e3c4c9af0f07a114fb754fed6ac358a102f49e2f (patch) | |
tree | 36ae43b6bd84fd339c3f947a5c8dbc0f77042247 | |
parent | 5e2b609b3f6145fa9fe0b396b76ff76f732c6fe6 (diff) | |
download | luajit-e3c4c9af0f07a114fb754fed6ac358a102f49e2f.tar.gz luajit-e3c4c9af0f07a114fb754fed6ac358a102f49e2f.tar.bz2 luajit-e3c4c9af0f07a114fb754fed6ac358a102f49e2f.zip |
DynASM/MIPS: Add missing MIPS64 instructions.
Contributed by Djordje Kovacevic and Stefan Pejic from RT-RK.com.
Sponsored by Cisco Systems, Inc.
-rw-r--r-- | dynasm/dasm_mips.h | 11 | ||||
-rw-r--r-- | dynasm/dasm_mips.lua | 75 | ||||
-rw-r--r-- | dynasm/dasm_mips64.lua | 12 |
3 files changed, 84 insertions, 14 deletions
diff --git a/dynasm/dasm_mips.h b/dynasm/dasm_mips.h index c10528fa..f3b43211 100644 --- a/dynasm/dasm_mips.h +++ b/dynasm/dasm_mips.h | |||
@@ -21,7 +21,7 @@ enum { | |||
21 | /* The following actions need a buffer position. */ | 21 | /* The following actions need a buffer position. */ |
22 | DASM_ALIGN, DASM_REL_LG, DASM_LABEL_LG, | 22 | DASM_ALIGN, DASM_REL_LG, DASM_LABEL_LG, |
23 | /* The following actions also have an argument. */ | 23 | /* The following actions also have an argument. */ |
24 | DASM_REL_PC, DASM_LABEL_PC, DASM_IMM, | 24 | DASM_REL_PC, DASM_LABEL_PC, DASM_IMM, DASM_IMMS, |
25 | DASM__MAX | 25 | DASM__MAX |
26 | }; | 26 | }; |
27 | 27 | ||
@@ -231,7 +231,7 @@ void dasm_put(Dst_DECL, int start, ...) | |||
231 | *pl = -pos; /* Label exists now. */ | 231 | *pl = -pos; /* Label exists now. */ |
232 | b[pos++] = ofs; /* Store pass1 offset estimate. */ | 232 | b[pos++] = ofs; /* Store pass1 offset estimate. */ |
233 | break; | 233 | break; |
234 | case DASM_IMM: | 234 | case DASM_IMM: case DASM_IMMS: |
235 | #ifdef DASM_CHECKS | 235 | #ifdef DASM_CHECKS |
236 | CK((n & ((1<<((ins>>10)&31))-1)) == 0, RANGE_I); | 236 | CK((n & ((1<<((ins>>10)&31))-1)) == 0, RANGE_I); |
237 | #endif | 237 | #endif |
@@ -299,7 +299,7 @@ int dasm_link(Dst_DECL, size_t *szp) | |||
299 | case DASM_ALIGN: ofs -= (b[pos++] + ofs) & (ins & 255); break; | 299 | case DASM_ALIGN: ofs -= (b[pos++] + ofs) & (ins & 255); break; |
300 | case DASM_REL_LG: case DASM_REL_PC: pos++; break; | 300 | case DASM_REL_LG: case DASM_REL_PC: pos++; break; |
301 | case DASM_LABEL_LG: case DASM_LABEL_PC: b[pos++] += ofs; break; | 301 | case DASM_LABEL_LG: case DASM_LABEL_PC: b[pos++] += ofs; break; |
302 | case DASM_IMM: pos++; break; | 302 | case DASM_IMM: case DASM_IMMS: pos++; break; |
303 | } | 303 | } |
304 | } | 304 | } |
305 | stop: (void)0; | 305 | stop: (void)0; |
@@ -356,7 +356,7 @@ int dasm_encode(Dst_DECL, void *buffer) | |||
356 | if (ins & 2048) | 356 | if (ins & 2048) |
357 | n = n - (int)((char *)cp - base); | 357 | n = n - (int)((char *)cp - base); |
358 | else | 358 | else |
359 | n = (n + (int)base) & 0x0fffffff; | 359 | n = (n + (int)(size_t)base) & 0x0fffffff; |
360 | patchrel: | 360 | patchrel: |
361 | CK((n & 3) == 0 && | 361 | CK((n & 3) == 0 && |
362 | ((n + ((ins & 2048) ? 0x00020000 : 0)) >> | 362 | ((n + ((ins & 2048) ? 0x00020000 : 0)) >> |
@@ -367,6 +367,9 @@ int dasm_encode(Dst_DECL, void *buffer) | |||
367 | ins &= 2047; if (ins >= 20) D->globals[ins-10] = (void *)(base + n); | 367 | ins &= 2047; if (ins >= 20) D->globals[ins-10] = (void *)(base + n); |
368 | break; | 368 | break; |
369 | case DASM_LABEL_PC: break; | 369 | case DASM_LABEL_PC: break; |
370 | case DASM_IMMS: | ||
371 | cp[-1] |= ((n>>3) & 4); n &= 0x1f; | ||
372 | /* fallthrough */ | ||
370 | case DASM_IMM: | 373 | case DASM_IMM: |
371 | cp[-1] |= (n & ((1<<((ins>>5)&31))-1)) << (ins&31); | 374 | cp[-1] |= (n & ((1<<((ins>>5)&31))-1)) << (ins&31); |
372 | break; | 375 | break; |
diff --git a/dynasm/dasm_mips.lua b/dynasm/dasm_mips.lua index c5a5595c..c8010561 100644 --- a/dynasm/dasm_mips.lua +++ b/dynasm/dasm_mips.lua | |||
@@ -1,17 +1,19 @@ | |||
1 | ------------------------------------------------------------------------------ | 1 | ------------------------------------------------------------------------------ |
2 | -- DynASM MIPS module. | 2 | -- DynASM MIPS32/MIPS64 module. |
3 | -- | 3 | -- |
4 | -- Copyright (C) 2005-2016 Mike Pall. All rights reserved. | 4 | -- Copyright (C) 2005-2016 Mike Pall. All rights reserved. |
5 | -- See dynasm.lua for full copyright notice. | 5 | -- See dynasm.lua for full copyright notice. |
6 | ------------------------------------------------------------------------------ | 6 | ------------------------------------------------------------------------------ |
7 | 7 | ||
8 | local mips64 = mips64 | ||
9 | |||
8 | -- Module information: | 10 | -- Module information: |
9 | local _info = { | 11 | local _info = { |
10 | arch = "mips", | 12 | arch = mips64 and "mips64" or "mips", |
11 | description = "DynASM MIPS module", | 13 | description = "DynASM MIPS32/MIPS64 module", |
12 | version = "1.4.0", | 14 | version = "1.4.0", |
13 | vernum = 10400, | 15 | vernum = 10400, |
14 | release = "2015-10-18", | 16 | release = "2016-05-24", |
15 | author = "Mike Pall", | 17 | author = "Mike Pall", |
16 | license = "MIT", | 18 | license = "MIT", |
17 | } | 19 | } |
@@ -27,7 +29,8 @@ local sub, format, byte, char = _s.sub, _s.format, _s.byte, _s.char | |||
27 | local match, gmatch = _s.match, _s.gmatch | 29 | local match, gmatch = _s.match, _s.gmatch |
28 | local concat, sort = table.concat, table.sort | 30 | local concat, sort = table.concat, table.sort |
29 | local bit = bit or require("bit") | 31 | local bit = bit or require("bit") |
30 | local band, shl, sar, tohex = bit.band, bit.lshift, bit.arshift, bit.tohex | 32 | local band, shl, shr, sar = bit.band, bit.lshift, bit.rshift, bit.arshift |
33 | local tohex = bit.tohex | ||
31 | 34 | ||
32 | -- Inherited tables and callbacks. | 35 | -- Inherited tables and callbacks. |
33 | local g_opt, g_arch | 36 | local g_opt, g_arch |
@@ -38,7 +41,7 @@ local wline, werror, wfatal, wwarn | |||
38 | local action_names = { | 41 | local action_names = { |
39 | "STOP", "SECTION", "ESC", "REL_EXT", | 42 | "STOP", "SECTION", "ESC", "REL_EXT", |
40 | "ALIGN", "REL_LG", "LABEL_LG", | 43 | "ALIGN", "REL_LG", "LABEL_LG", |
41 | "REL_PC", "LABEL_PC", "IMM", | 44 | "REL_PC", "LABEL_PC", "IMM", "IMMS", |
42 | } | 45 | } |
43 | 46 | ||
44 | -- Maximum number of section buffer positions for dasm_put(). | 47 | -- Maximum number of section buffer positions for dasm_put(). |
@@ -251,6 +254,10 @@ local map_op = { | |||
251 | bnel_3 = "54000000STB", | 254 | bnel_3 = "54000000STB", |
252 | blezl_2 = "58000000SB", | 255 | blezl_2 = "58000000SB", |
253 | bgtzl_2 = "5c000000SB", | 256 | bgtzl_2 = "5c000000SB", |
257 | daddi_3 = mips64 and "60000000TSI", | ||
258 | daddiu_3 = mips64 and "64000000TSI", | ||
259 | ldl_2 = mips64 and "68000000TO", | ||
260 | ldr_2 = mips64 and "6c000000TO", | ||
254 | lb_2 = "80000000TO", | 261 | lb_2 = "80000000TO", |
255 | lh_2 = "84000000TO", | 262 | lh_2 = "84000000TO", |
256 | lwl_2 = "88000000TO", | 263 | lwl_2 = "88000000TO", |
@@ -258,23 +265,30 @@ local map_op = { | |||
258 | lbu_2 = "90000000TO", | 265 | lbu_2 = "90000000TO", |
259 | lhu_2 = "94000000TO", | 266 | lhu_2 = "94000000TO", |
260 | lwr_2 = "98000000TO", | 267 | lwr_2 = "98000000TO", |
268 | lwu_2 = mips64 and "9c000000TO", | ||
261 | sb_2 = "a0000000TO", | 269 | sb_2 = "a0000000TO", |
262 | sh_2 = "a4000000TO", | 270 | sh_2 = "a4000000TO", |
263 | swl_2 = "a8000000TO", | 271 | swl_2 = "a8000000TO", |
264 | sw_2 = "ac000000TO", | 272 | sw_2 = "ac000000TO", |
273 | sdl_2 = mips64 and "b0000000TO", | ||
274 | sdr_2 = mips64 and "b1000000TO", | ||
265 | swr_2 = "b8000000TO", | 275 | swr_2 = "b8000000TO", |
266 | cache_2 = "bc000000NO", | 276 | cache_2 = "bc000000NO", |
267 | ll_2 = "c0000000TO", | 277 | ll_2 = "c0000000TO", |
268 | lwc1_2 = "c4000000HO", | 278 | lwc1_2 = "c4000000HO", |
269 | pref_2 = "cc000000NO", | 279 | pref_2 = "cc000000NO", |
270 | ldc1_2 = "d4000000HO", | 280 | ldc1_2 = "d4000000HO", |
281 | ld_2 = mips64 and "dc000000TO", | ||
271 | sc_2 = "e0000000TO", | 282 | sc_2 = "e0000000TO", |
272 | swc1_2 = "e4000000HO", | 283 | swc1_2 = "e4000000HO", |
284 | scd_2 = mips64 and "f0000000TO", | ||
273 | sdc1_2 = "f4000000HO", | 285 | sdc1_2 = "f4000000HO", |
286 | sd_2 = mips64 and "fc000000TO", | ||
274 | 287 | ||
275 | -- Opcode SPECIAL. | 288 | -- Opcode SPECIAL. |
276 | nop_0 = "00000000", | 289 | nop_0 = "00000000", |
277 | sll_3 = "00000000DTA", | 290 | sll_3 = "00000000DTA", |
291 | sextw_2 = "00000000DT", | ||
278 | movf_2 = "00000001DS", | 292 | movf_2 = "00000001DS", |
279 | movf_3 = "00000001DSC", | 293 | movf_3 = "00000001DSC", |
280 | movt_2 = "00010001DS", | 294 | movt_2 = "00010001DS", |
@@ -285,6 +299,7 @@ local map_op = { | |||
285 | sllv_3 = "00000004DTS", | 299 | sllv_3 = "00000004DTS", |
286 | srlv_3 = "00000006DTS", | 300 | srlv_3 = "00000006DTS", |
287 | rotrv_3 = "00000046DTS", | 301 | rotrv_3 = "00000046DTS", |
302 | drotrv_3 = mips64 and "00000056DTS", | ||
288 | srav_3 = "00000007DTS", | 303 | srav_3 = "00000007DTS", |
289 | jr_1 = "00000008S", | 304 | jr_1 = "00000008S", |
290 | jalr_1 = "0000f809S", | 305 | jalr_1 = "0000f809S", |
@@ -300,15 +315,22 @@ local map_op = { | |||
300 | mthi_1 = "00000011S", | 315 | mthi_1 = "00000011S", |
301 | mflo_1 = "00000012D", | 316 | mflo_1 = "00000012D", |
302 | mtlo_1 = "00000013S", | 317 | mtlo_1 = "00000013S", |
318 | dsllv_3 = mips64 and "00000014DTS", | ||
319 | dsrlv_3 = mips64 and "00000016DTS", | ||
320 | dsrav_3 = mips64 and "00000017DTS", | ||
303 | mult_2 = "00000018ST", | 321 | mult_2 = "00000018ST", |
304 | multu_2 = "00000019ST", | 322 | multu_2 = "00000019ST", |
305 | div_2 = "0000001aST", | 323 | div_2 = "0000001aST", |
306 | divu_2 = "0000001bST", | 324 | divu_2 = "0000001bST", |
325 | dmult_2 = mips64 and "0000001cST", | ||
326 | dmultu_2 = mips64 and "0000001dST", | ||
327 | ddiv_2 = mips64 and "0000001eST", | ||
328 | ddivu_2 = mips64 and "0000001fST", | ||
307 | add_3 = "00000020DST", | 329 | add_3 = "00000020DST", |
308 | move_2 = "00000021DS", | 330 | move_2 = mips64 and "00000025DS" or "00000021DS", |
309 | addu_3 = "00000021DST", | 331 | addu_3 = "00000021DST", |
310 | sub_3 = "00000022DST", | 332 | sub_3 = "00000022DST", |
311 | negu_2 = "00000023DT", | 333 | negu_2 = mips64 and "0000002fDT" or "00000023DT", |
312 | subu_3 = "00000023DST", | 334 | subu_3 = "00000023DST", |
313 | and_3 = "00000024DST", | 335 | and_3 = "00000024DST", |
314 | or_3 = "00000025DST", | 336 | or_3 = "00000025DST", |
@@ -317,6 +339,10 @@ local map_op = { | |||
317 | nor_3 = "00000027DST", | 339 | nor_3 = "00000027DST", |
318 | slt_3 = "0000002aDST", | 340 | slt_3 = "0000002aDST", |
319 | sltu_3 = "0000002bDST", | 341 | sltu_3 = "0000002bDST", |
342 | dadd_3 = mips64 and "0000002cDST", | ||
343 | daddu_3 = mips64 and "0000002dDST", | ||
344 | dsub_3 = mips64 and "0000002eDST", | ||
345 | dsubu_3 = mips64 and "0000002fDST", | ||
320 | tge_2 = "00000030ST", | 346 | tge_2 = "00000030ST", |
321 | tge_3 = "00000030STZ", | 347 | tge_3 = "00000030STZ", |
322 | tgeu_2 = "00000031ST", | 348 | tgeu_2 = "00000031ST", |
@@ -329,6 +355,14 @@ local map_op = { | |||
329 | teq_3 = "00000034STZ", | 355 | teq_3 = "00000034STZ", |
330 | tne_2 = "00000036ST", | 356 | tne_2 = "00000036ST", |
331 | tne_3 = "00000036STZ", | 357 | tne_3 = "00000036STZ", |
358 | dsll_3 = mips64 and "00000038DTa", | ||
359 | dsrl_3 = mips64 and "0000003aDTa", | ||
360 | drotr_3 = mips64 and "0020003aDTa", | ||
361 | dsra_3 = mips64 and "0000003bDTa", | ||
362 | dsll32_3 = mips64 and "0000003cDTA", | ||
363 | dsrl32_3 = mips64 and "0000003eDTA", | ||
364 | drotr32_3 = mips64 and "0020003eDTA", | ||
365 | dsra32_3 = mips64 and "0000003fDTA", | ||
332 | 366 | ||
333 | -- Opcode REGIMM. | 367 | -- Opcode REGIMM. |
334 | bltz_2 = "04000000SB", | 368 | bltz_2 = "04000000SB", |
@@ -356,13 +390,24 @@ local map_op = { | |||
356 | msubu_2 = "70000005ST", | 390 | msubu_2 = "70000005ST", |
357 | clz_2 = "70000020DS=", | 391 | clz_2 = "70000020DS=", |
358 | clo_2 = "70000021DS=", | 392 | clo_2 = "70000021DS=", |
393 | dclz_2 = mips64 and "70000024DS=", | ||
394 | dclo_2 = mips64 and "70000025DS=", | ||
359 | sdbbp_0 = "7000003f", | 395 | sdbbp_0 = "7000003f", |
360 | sdbbp_1 = "7000003fY", | 396 | sdbbp_1 = "7000003fY", |
361 | 397 | ||
362 | -- Opcode SPECIAL3. | 398 | -- Opcode SPECIAL3. |
363 | ext_4 = "7c000000TSAM", -- Note: last arg is msbd = size-1 | 399 | ext_4 = "7c000000TSAM", -- Note: last arg is msbd = size-1 |
400 | dextm_4 = mips64 and "7c000001TSAM", -- Args: pos | size-1-32 | ||
401 | dextu_4 = mips64 and "7c000002TSAM", -- Args: pos-32 | size-1 | ||
402 | dext_4 = mips64 and "7c000003TSAM", -- Args: pos | size-1 | ||
403 | zextw_2 = mips64 and "7c00f803TS", | ||
364 | ins_4 = "7c000004TSAM", -- Note: last arg is msb = pos+size-1 | 404 | ins_4 = "7c000004TSAM", -- Note: last arg is msb = pos+size-1 |
405 | dinsm_4 = mips64 and "7c000005TSAM", -- Args: pos | pos+size-33 | ||
406 | dinsu_4 = mips64 and "7c000006TSAM", -- Args: pos-32 | pos+size-33 | ||
407 | dins_4 = mips64 and "7c000007TSAM", -- Args: pos | pos+size-1 | ||
365 | wsbh_2 = "7c0000a0DT", | 408 | wsbh_2 = "7c0000a0DT", |
409 | dsbh_2 = mips64 and "7c0000a4DT", | ||
410 | dshd_2 = mips64 and "7c000164DT", | ||
366 | seb_2 = "7c000420DT", | 411 | seb_2 = "7c000420DT", |
367 | seh_2 = "7c000620DT", | 412 | seh_2 = "7c000620DT", |
368 | rdhwr_2 = "7c00003bTD", | 413 | rdhwr_2 = "7c00003bTD", |
@@ -370,8 +415,12 @@ local map_op = { | |||
370 | -- Opcode COP0. | 415 | -- Opcode COP0. |
371 | mfc0_2 = "40000000TD", | 416 | mfc0_2 = "40000000TD", |
372 | mfc0_3 = "40000000TDW", | 417 | mfc0_3 = "40000000TDW", |
418 | dmfc0_2 = mips64 and "40200000TD", | ||
419 | dmfc0_3 = mips64 and "40200000TDW", | ||
373 | mtc0_2 = "40800000TD", | 420 | mtc0_2 = "40800000TD", |
374 | mtc0_3 = "40800000TDW", | 421 | mtc0_3 = "40800000TDW", |
422 | dmtc0_2 = mips64 and "40a00000TD", | ||
423 | dmtc0_3 = mips64 and "40a00000TDW", | ||
375 | rdpgpr_2 = "41400000DT", | 424 | rdpgpr_2 = "41400000DT", |
376 | di_0 = "41606000", | 425 | di_0 = "41606000", |
377 | di_1 = "41606000T", | 426 | di_1 = "41606000T", |
@@ -388,9 +437,11 @@ local map_op = { | |||
388 | 437 | ||
389 | -- Opcode COP1. | 438 | -- Opcode COP1. |
390 | mfc1_2 = "44000000TG", | 439 | mfc1_2 = "44000000TG", |
440 | dmfc1_2 = mips64 and "44200000TG", | ||
391 | cfc1_2 = "44400000TG", | 441 | cfc1_2 = "44400000TG", |
392 | mfhc1_2 = "44600000TG", | 442 | mfhc1_2 = "44600000TG", |
393 | mtc1_2 = "44800000TG", | 443 | mtc1_2 = "44800000TG", |
444 | dmtc1_2 = mips64 and "44a00000TG", | ||
394 | ctc1_2 = "44c00000TG", | 445 | ctc1_2 = "44c00000TG", |
395 | mthc1_2 = "44e00000TG", | 446 | mthc1_2 = "44e00000TG", |
396 | 447 | ||
@@ -633,7 +684,7 @@ local function parse_fpr(expr) | |||
633 | werror("bad register name `"..expr.."'") | 684 | werror("bad register name `"..expr.."'") |
634 | end | 685 | end |
635 | 686 | ||
636 | local function parse_imm(imm, bits, shift, scale, signed) | 687 | local function parse_imm(imm, bits, shift, scale, signed, action) |
637 | local n = tonumber(imm) | 688 | local n = tonumber(imm) |
638 | if n then | 689 | if n then |
639 | local m = sar(n, scale) | 690 | local m = sar(n, scale) |
@@ -651,7 +702,8 @@ local function parse_imm(imm, bits, shift, scale, signed) | |||
651 | match(imm, "^([%w_]+):([rf][1-3]?[0-9])$") then | 702 | match(imm, "^([%w_]+):([rf][1-3]?[0-9])$") then |
652 | werror("expected immediate operand, got register") | 703 | werror("expected immediate operand, got register") |
653 | else | 704 | else |
654 | waction("IMM", (signed and 32768 or 0)+scale*1024+bits*32+shift, imm) | 705 | waction(action or "IMM", |
706 | (signed and 32768 or 0)+shl(scale, 10)+shl(bits, 5)+shift, imm) | ||
655 | return 0 | 707 | return 0 |
656 | end | 708 | end |
657 | end | 709 | end |
@@ -763,6 +815,9 @@ map_op[".template__"] = function(params, template, nparams) | |||
763 | n = n + 1 | 815 | n = n + 1 |
764 | elseif p == "A" then | 816 | elseif p == "A" then |
765 | op = op + parse_imm(params[n], 5, 6, 0, false); n = n + 1 | 817 | op = op + parse_imm(params[n], 5, 6, 0, false); n = n + 1 |
818 | elseif p == "a" then | ||
819 | local m = parse_imm(params[n], 6, 6, 0, false, "IMMS"); n = n + 1 | ||
820 | op = op + band(m, 0x7c0) + band(shr(m, 9), 4) | ||
766 | elseif p == "M" then | 821 | elseif p == "M" then |
767 | op = op + parse_imm(params[n], 5, 11, 0, false); n = n + 1 | 822 | op = op + parse_imm(params[n], 5, 11, 0, false); n = n + 1 |
768 | elseif p == "N" then | 823 | elseif p == "N" then |
diff --git a/dynasm/dasm_mips64.lua b/dynasm/dasm_mips64.lua new file mode 100644 index 00000000..94f21921 --- /dev/null +++ b/dynasm/dasm_mips64.lua | |||
@@ -0,0 +1,12 @@ | |||
1 | ------------------------------------------------------------------------------ | ||
2 | -- DynASM MIPS64 module. | ||
3 | -- | ||
4 | -- Copyright (C) 2005-2016 Mike Pall. All rights reserved. | ||
5 | -- See dynasm.lua for full copyright notice. | ||
6 | ------------------------------------------------------------------------------ | ||
7 | -- This module just sets 64 bit mode for the combined MIPS/MIPS64 module. | ||
8 | -- All the interesting stuff is there. | ||
9 | ------------------------------------------------------------------------------ | ||
10 | |||
11 | mips64 = true -- Using a global is an ugly, but effective solution. | ||
12 | return require("dasm_mips") | ||