root/lj_ir.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. lj_ir_growtop
  2. lj_ir_growbot
  3. lj_ir_emit
  4. lj_ir_call
  5. lj_ir_ggfload
  6. ir_nextk
  7. ir_nextk64
  8. lj_ir_kint
  9. lj_ir_k64
  10. lj_ir_knum_u64
  11. lj_ir_kint64
  12. numistrueint
  13. lj_ir_knumint
  14. lj_ir_kgc
  15. lj_ir_ktrace
  16. lj_ir_kptr_
  17. lj_ir_knull
  18. lj_ir_kslot
  19. lj_ir_kvalue
  20. lj_ir_tonumber
  21. lj_ir_tonum
  22. lj_ir_tostr
  23. lj_ir_numcmp
  24. lj_ir_strcmp
  25. lj_ir_rollback

   1 /*
   2 ** SSA IR (Intermediate Representation) emitter.
   3 ** Copyright (C) 2005-2017 Mike Pall. See Copyright Notice in luajit.h
   4 */
   5 
   6 #define lj_ir_c
   7 #define LUA_CORE
   8 
   9 /* For pointers to libc/libm functions. */
  10 #include <stdio.h>
  11 #include <math.h>
  12 
  13 #include "lj_obj.h"
  14 
  15 #if LJ_HASJIT
  16 
  17 #include "lj_gc.h"
  18 #include "lj_buf.h"
  19 #include "lj_str.h"
  20 #include "lj_tab.h"
  21 #include "lj_ir.h"
  22 #include "lj_jit.h"
  23 #include "lj_ircall.h"
  24 #include "lj_iropt.h"
  25 #include "lj_trace.h"
  26 #if LJ_HASFFI
  27 #include "lj_ctype.h"
  28 #include "lj_cdata.h"
  29 #include "lj_carith.h"
  30 #endif
  31 #include "lj_vm.h"
  32 #include "lj_strscan.h"
  33 #include "lj_strfmt.h"
  34 #include "lj_lib.h"
  35 
  36 /* Some local macros to save typing. Undef'd at the end. */
  37 #define IR(ref)                 (&J->cur.ir[(ref)])
  38 #define fins                    (&J->fold.ins)
  39 
  40 /* Pass IR on to next optimization in chain (FOLD). */
  41 #define emitir(ot, a, b)        (lj_ir_set(J, (ot), (a), (b)), lj_opt_fold(J))
  42 
  43 /* -- IR tables ----------------------------------------------------------- */
  44 
  45 /* IR instruction modes. */
  46 LJ_DATADEF const uint8_t lj_ir_mode[IR__MAX+1] = {
  47 IRDEF(IRMODE)
  48   0
  49 };
  50 
  51 /* IR type sizes. */
  52 LJ_DATADEF const uint8_t lj_ir_type_size[IRT__MAX+1] = {
  53 #define IRTSIZE(name, size)     size,
  54 IRTDEF(IRTSIZE)
  55 #undef IRTSIZE
  56   0
  57 };
  58 
  59 /* C call info for CALL* instructions. */
  60 LJ_DATADEF const CCallInfo lj_ir_callinfo[] = {
  61 #define IRCALLCI(cond, name, nargs, kind, type, flags) \
  62   { (ASMFunction)IRCALLCOND_##cond(name), \
  63     (nargs)|(CCI_CALL_##kind)|(IRT_##type<<CCI_OTSHIFT)|(flags) },
  64 IRCALLDEF(IRCALLCI)
  65 #undef IRCALLCI
  66   { NULL, 0 }
  67 };
  68 
  69 /* -- IR emitter ---------------------------------------------------------- */
  70 
  71 /* Grow IR buffer at the top. */
  72 void LJ_FASTCALL lj_ir_growtop(jit_State *J)
  73 {
  74   IRIns *baseir = J->irbuf + J->irbotlim;
  75   MSize szins = J->irtoplim - J->irbotlim;
  76   if (szins) {
  77     baseir = (IRIns *)lj_mem_realloc(J->L, baseir, szins*sizeof(IRIns),
  78                                      2*szins*sizeof(IRIns));
  79     J->irtoplim = J->irbotlim + 2*szins;
  80   } else {
  81     baseir = (IRIns *)lj_mem_realloc(J->L, NULL, 0, LJ_MIN_IRSZ*sizeof(IRIns));
  82     J->irbotlim = REF_BASE - LJ_MIN_IRSZ/4;
  83     J->irtoplim = J->irbotlim + LJ_MIN_IRSZ;
  84   }
  85   J->cur.ir = J->irbuf = baseir - J->irbotlim;
  86 }
  87 
  88 /* Grow IR buffer at the bottom or shift it up. */
  89 static void lj_ir_growbot(jit_State *J)
  90 {
  91   IRIns *baseir = J->irbuf + J->irbotlim;
  92   MSize szins = J->irtoplim - J->irbotlim;
  93   lua_assert(szins != 0);
  94   lua_assert(J->cur.nk == J->irbotlim || J->cur.nk-1 == J->irbotlim);
  95   if (J->cur.nins + (szins >> 1) < J->irtoplim) {
  96     /* More than half of the buffer is free on top: shift up by a quarter. */
  97     MSize ofs = szins >> 2;
  98     memmove(baseir + ofs, baseir, (J->cur.nins - J->irbotlim)*sizeof(IRIns));
  99     J->irbotlim -= ofs;
 100     J->irtoplim -= ofs;
 101     J->cur.ir = J->irbuf = baseir - J->irbotlim;
 102   } else {
 103     /* Double the buffer size, but split the growth amongst top/bottom. */
 104     IRIns *newbase = lj_mem_newt(J->L, 2*szins*sizeof(IRIns), IRIns);
 105     MSize ofs = szins >= 256 ? 128 : (szins >> 1);  /* Limit bottom growth. */
 106     memcpy(newbase + ofs, baseir, (J->cur.nins - J->irbotlim)*sizeof(IRIns));
 107     lj_mem_free(G(J->L), baseir, szins*sizeof(IRIns));
 108     J->irbotlim -= ofs;
 109     J->irtoplim = J->irbotlim + 2*szins;
 110     J->cur.ir = J->irbuf = newbase - J->irbotlim;
 111   }
 112 }
 113 
 114 /* Emit IR without any optimizations. */
 115 TRef LJ_FASTCALL lj_ir_emit(jit_State *J)
 116 {
 117   IRRef ref = lj_ir_nextins(J);
 118   IRIns *ir = IR(ref);
 119   IROp op = fins->o;
 120   ir->prev = J->chain[op];
 121   J->chain[op] = (IRRef1)ref;
 122   ir->o = op;
 123   ir->op1 = fins->op1;
 124   ir->op2 = fins->op2;
 125   J->guardemit.irt |= fins->t.irt;
 126   return TREF(ref, irt_t((ir->t = fins->t)));
 127 }
 128 
 129 /* Emit call to a C function. */
 130 TRef lj_ir_call(jit_State *J, IRCallID id, ...)
 131 {
 132   const CCallInfo *ci = &lj_ir_callinfo[id];
 133   uint32_t n = CCI_NARGS(ci);
 134   TRef tr = TREF_NIL;
 135   va_list argp;
 136   va_start(argp, id);
 137   if ((ci->flags & CCI_L)) n--;
 138   if (n > 0)
 139     tr = va_arg(argp, IRRef);
 140   while (n-- > 1)
 141     tr = emitir(IRT(IR_CARG, IRT_NIL), tr, va_arg(argp, IRRef));
 142   va_end(argp);
 143   if (CCI_OP(ci) == IR_CALLS)
 144     J->needsnap = 1;  /* Need snapshot after call with side effect. */
 145   return emitir(CCI_OPTYPE(ci), tr, id);
 146 }
 147 
 148 /* Load field of type t from GG_State + offset. Must be 32 bit aligned. */
 149 LJ_FUNC TRef lj_ir_ggfload(jit_State *J, IRType t, uintptr_t ofs)
 150 {
 151   lua_assert((ofs & 3) == 0);
 152   ofs >>= 2;
 153   lua_assert(ofs >= IRFL__MAX && ofs <= 0x3ff);  /* 10 bit FOLD key limit. */
 154   lj_ir_set(J, IRT(IR_FLOAD, t), REF_NIL, ofs);
 155   return lj_opt_fold(J);
 156 }
 157 
 158 /* -- Interning of constants ---------------------------------------------- */
 159 
 160 /*
 161 ** IR instructions for constants are kept between J->cur.nk >= ref < REF_BIAS.
 162 ** They are chained like all other instructions, but grow downwards.
 163 ** The are interned (like strings in the VM) to facilitate reference
 164 ** comparisons. The same constant must get the same reference.
 165 */
 166 
 167 /* Get ref of next IR constant and optionally grow IR.
 168 ** Note: this may invalidate all IRIns *!
 169 */
 170 static LJ_AINLINE IRRef ir_nextk(jit_State *J)
 171 {
 172   IRRef ref = J->cur.nk;
 173   if (LJ_UNLIKELY(ref <= J->irbotlim)) lj_ir_growbot(J);
 174   J->cur.nk = --ref;
 175   return ref;
 176 }
 177 
 178 /* Get ref of next 64 bit IR constant and optionally grow IR.
 179 ** Note: this may invalidate all IRIns *!
 180 */
 181 static LJ_AINLINE IRRef ir_nextk64(jit_State *J)
 182 {
 183   IRRef ref = J->cur.nk - 2;
 184   lua_assert(J->state != LJ_TRACE_ASM);
 185   if (LJ_UNLIKELY(ref < J->irbotlim)) lj_ir_growbot(J);
 186   J->cur.nk = ref;
 187   return ref;
 188 }
 189 
 190 #if LJ_GC64
 191 #define ir_nextkgc ir_nextk64
 192 #else
 193 #define ir_nextkgc ir_nextk
 194 #endif
 195 
 196 /* Intern int32_t constant. */
 197 TRef LJ_FASTCALL lj_ir_kint(jit_State *J, int32_t k)
 198 {
 199   IRIns *ir, *cir = J->cur.ir;
 200   IRRef ref;
 201   for (ref = J->chain[IR_KINT]; ref; ref = cir[ref].prev)
 202     if (cir[ref].i == k)
 203       goto found;
 204   ref = ir_nextk(J);
 205   ir = IR(ref);
 206   ir->i = k;
 207   ir->t.irt = IRT_INT;
 208   ir->o = IR_KINT;
 209   ir->prev = J->chain[IR_KINT];
 210   J->chain[IR_KINT] = (IRRef1)ref;
 211 found:
 212   return TREF(ref, IRT_INT);
 213 }
 214 
 215 /* Intern 64 bit constant, given by its 64 bit pattern. */
 216 TRef lj_ir_k64(jit_State *J, IROp op, uint64_t u64)
 217 {
 218   IRIns *ir, *cir = J->cur.ir;
 219   IRRef ref;
 220   IRType t = op == IR_KNUM ? IRT_NUM : IRT_I64;
 221   for (ref = J->chain[op]; ref; ref = cir[ref].prev)
 222     if (ir_k64(&cir[ref])->u64 == u64)
 223       goto found;
 224   ref = ir_nextk64(J);
 225   ir = IR(ref);
 226   ir[1].tv.u64 = u64;
 227   ir->t.irt = t;
 228   ir->o = op;
 229   ir->op12 = 0;
 230   ir->prev = J->chain[op];
 231   J->chain[op] = (IRRef1)ref;
 232 found:
 233   return TREF(ref, t);
 234 }
 235 
 236 /* Intern FP constant, given by its 64 bit pattern. */
 237 TRef lj_ir_knum_u64(jit_State *J, uint64_t u64)
 238 {
 239   return lj_ir_k64(J, IR_KNUM, u64);
 240 }
 241 
 242 /* Intern 64 bit integer constant. */
 243 TRef lj_ir_kint64(jit_State *J, uint64_t u64)
 244 {
 245   return lj_ir_k64(J, IR_KINT64, u64);
 246 }
 247 
 248 /* Check whether a number is int and return it. -0 is NOT considered an int. */
 249 static int numistrueint(lua_Number n, int32_t *kp)
 250 {
 251   int32_t k = lj_num2int(n);
 252   if (n == (lua_Number)k) {
 253     if (kp) *kp = k;
 254     if (k == 0) {  /* Special check for -0. */
 255       TValue tv;
 256       setnumV(&tv, n);
 257       if (tv.u32.hi != 0)
 258         return 0;
 259     }
 260     return 1;
 261   }
 262   return 0;
 263 }
 264 
 265 /* Intern number as int32_t constant if possible, otherwise as FP constant. */
 266 TRef lj_ir_knumint(jit_State *J, lua_Number n)
 267 {
 268   int32_t k;
 269   if (numistrueint(n, &k))
 270     return lj_ir_kint(J, k);
 271   else
 272     return lj_ir_knum(J, n);
 273 }
 274 
 275 /* Intern GC object "constant". */
 276 TRef lj_ir_kgc(jit_State *J, GCobj *o, IRType t)
 277 {
 278   IRIns *ir, *cir = J->cur.ir;
 279   IRRef ref;
 280   lua_assert(!isdead(J2G(J), o));
 281   for (ref = J->chain[IR_KGC]; ref; ref = cir[ref].prev)
 282     if (ir_kgc(&cir[ref]) == o)
 283       goto found;
 284   ref = ir_nextkgc(J);
 285   ir = IR(ref);
 286   /* NOBARRIER: Current trace is a GC root. */
 287   ir->op12 = 0;
 288   setgcref(ir[LJ_GC64].gcr, o);
 289   ir->t.irt = (uint8_t)t;
 290   ir->o = IR_KGC;
 291   ir->prev = J->chain[IR_KGC];
 292   J->chain[IR_KGC] = (IRRef1)ref;
 293 found:
 294   return TREF(ref, t);
 295 }
 296 
 297 /* Allocate GCtrace constant placeholder (no interning). */
 298 TRef lj_ir_ktrace(jit_State *J)
 299 {
 300   IRRef ref = ir_nextkgc(J);
 301   IRIns *ir = IR(ref);
 302   lua_assert(irt_toitype_(IRT_P64) == LJ_TTRACE);
 303   ir->t.irt = IRT_P64;
 304   ir->o = LJ_GC64 ? IR_KNUM : IR_KNULL;  /* Not IR_KGC yet, but same size. */
 305   ir->op12 = 0;
 306   ir->prev = 0;
 307   return TREF(ref, IRT_P64);
 308 }
 309 
 310 /* Intern pointer constant. */
 311 TRef lj_ir_kptr_(jit_State *J, IROp op, void *ptr)
 312 {
 313   IRIns *ir, *cir = J->cur.ir;
 314   IRRef ref;
 315 #if LJ_64 && !LJ_GC64
 316   lua_assert((void *)(uintptr_t)u32ptr(ptr) == ptr);
 317 #endif
 318   for (ref = J->chain[op]; ref; ref = cir[ref].prev)
 319     if (ir_kptr(&cir[ref]) == ptr)
 320       goto found;
 321 #if LJ_GC64
 322   ref = ir_nextk64(J);
 323 #else
 324   ref = ir_nextk(J);
 325 #endif
 326   ir = IR(ref);
 327   ir->op12 = 0;
 328   setmref(ir[LJ_GC64].ptr, ptr);
 329   ir->t.irt = IRT_PGC;
 330   ir->o = op;
 331   ir->prev = J->chain[op];
 332   J->chain[op] = (IRRef1)ref;
 333 found:
 334   return TREF(ref, IRT_PGC);
 335 }
 336 
 337 /* Intern typed NULL constant. */
 338 TRef lj_ir_knull(jit_State *J, IRType t)
 339 {
 340   IRIns *ir, *cir = J->cur.ir;
 341   IRRef ref;
 342   for (ref = J->chain[IR_KNULL]; ref; ref = cir[ref].prev)
 343     if (irt_t(cir[ref].t) == t)
 344       goto found;
 345   ref = ir_nextk(J);
 346   ir = IR(ref);
 347   ir->i = 0;
 348   ir->t.irt = (uint8_t)t;
 349   ir->o = IR_KNULL;
 350   ir->prev = J->chain[IR_KNULL];
 351   J->chain[IR_KNULL] = (IRRef1)ref;
 352 found:
 353   return TREF(ref, t);
 354 }
 355 
 356 /* Intern key slot. */
 357 TRef lj_ir_kslot(jit_State *J, TRef key, IRRef slot)
 358 {
 359   IRIns *ir, *cir = J->cur.ir;
 360   IRRef2 op12 = IRREF2((IRRef1)key, (IRRef1)slot);
 361   IRRef ref;
 362   /* Const part is not touched by CSE/DCE, so 0-65535 is ok for IRMlit here. */
 363   lua_assert(tref_isk(key) && slot == (IRRef)(IRRef1)slot);
 364   for (ref = J->chain[IR_KSLOT]; ref; ref = cir[ref].prev)
 365     if (cir[ref].op12 == op12)
 366       goto found;
 367   ref = ir_nextk(J);
 368   ir = IR(ref);
 369   ir->op12 = op12;
 370   ir->t.irt = IRT_P32;
 371   ir->o = IR_KSLOT;
 372   ir->prev = J->chain[IR_KSLOT];
 373   J->chain[IR_KSLOT] = (IRRef1)ref;
 374 found:
 375   return TREF(ref, IRT_P32);
 376 }
 377 
 378 /* -- Access to IR constants ---------------------------------------------- */
 379 
 380 /* Copy value of IR constant. */
 381 void lj_ir_kvalue(lua_State *L, TValue *tv, const IRIns *ir)
 382 {
 383   UNUSED(L);
 384   lua_assert(ir->o != IR_KSLOT);  /* Common mistake. */
 385   switch (ir->o) {
 386   case IR_KPRI: setpriV(tv, irt_toitype(ir->t)); break;
 387   case IR_KINT: setintV(tv, ir->i); break;
 388   case IR_KGC: setgcV(L, tv, ir_kgc(ir), irt_toitype(ir->t)); break;
 389   case IR_KPTR: case IR_KKPTR: setlightudV(tv, ir_kptr(ir)); break;
 390   case IR_KNULL: setlightudV(tv, NULL); break;
 391   case IR_KNUM: setnumV(tv, ir_knum(ir)->n); break;
 392 #if LJ_HASFFI
 393   case IR_KINT64: {
 394     GCcdata *cd = lj_cdata_new_(L, CTID_INT64, 8);
 395     *(uint64_t *)cdataptr(cd) = ir_kint64(ir)->u64;
 396     setcdataV(L, tv, cd);
 397     break;
 398     }
 399 #endif
 400   default: lua_assert(0); break;
 401   }
 402 }
 403 
 404 /* -- Convert IR operand types -------------------------------------------- */
 405 
 406 /* Convert from string to number. */
 407 TRef LJ_FASTCALL lj_ir_tonumber(jit_State *J, TRef tr)
 408 {
 409   if (!tref_isnumber(tr)) {
 410     if (tref_isstr(tr))
 411       tr = emitir(IRTG(IR_STRTO, IRT_NUM), tr, 0);
 412     else
 413       lj_trace_err(J, LJ_TRERR_BADTYPE);
 414   }
 415   return tr;
 416 }
 417 
 418 /* Convert from integer or string to number. */
 419 TRef LJ_FASTCALL lj_ir_tonum(jit_State *J, TRef tr)
 420 {
 421   if (!tref_isnum(tr)) {
 422     if (tref_isinteger(tr))
 423       tr = emitir(IRTN(IR_CONV), tr, IRCONV_NUM_INT);
 424     else if (tref_isstr(tr))
 425       tr = emitir(IRTG(IR_STRTO, IRT_NUM), tr, 0);
 426     else
 427       lj_trace_err(J, LJ_TRERR_BADTYPE);
 428   }
 429   return tr;
 430 }
 431 
 432 /* Convert from integer or number to string. */
 433 TRef LJ_FASTCALL lj_ir_tostr(jit_State *J, TRef tr)
 434 {
 435   if (!tref_isstr(tr)) {
 436     if (!tref_isnumber(tr))
 437       lj_trace_err(J, LJ_TRERR_BADTYPE);
 438     tr = emitir(IRT(IR_TOSTR, IRT_STR), tr,
 439                 tref_isnum(tr) ? IRTOSTR_NUM : IRTOSTR_INT);
 440   }
 441   return tr;
 442 }
 443 
 444 /* -- Miscellaneous IR ops ------------------------------------------------ */
 445 
 446 /* Evaluate numeric comparison. */
 447 int lj_ir_numcmp(lua_Number a, lua_Number b, IROp op)
 448 {
 449   switch (op) {
 450   case IR_EQ: return (a == b);
 451   case IR_NE: return (a != b);
 452   case IR_LT: return (a < b);
 453   case IR_GE: return (a >= b);
 454   case IR_LE: return (a <= b);
 455   case IR_GT: return (a > b);
 456   case IR_ULT: return !(a >= b);
 457   case IR_UGE: return !(a < b);
 458   case IR_ULE: return !(a > b);
 459   case IR_UGT: return !(a <= b);
 460   default: lua_assert(0); return 0;
 461   }
 462 }
 463 
 464 /* Evaluate string comparison. */
 465 int lj_ir_strcmp(GCstr *a, GCstr *b, IROp op)
 466 {
 467   int res = lj_str_cmp(a, b);
 468   switch (op) {
 469   case IR_LT: return (res < 0);
 470   case IR_GE: return (res >= 0);
 471   case IR_LE: return (res <= 0);
 472   case IR_GT: return (res > 0);
 473   default: lua_assert(0); return 0;
 474   }
 475 }
 476 
 477 /* Rollback IR to previous state. */
 478 void lj_ir_rollback(jit_State *J, IRRef ref)
 479 {
 480   IRRef nins = J->cur.nins;
 481   while (nins > ref) {
 482     IRIns *ir;
 483     nins--;
 484     ir = IR(nins);
 485     J->chain[ir->o] = ir->prev;
 486   }
 487   J->cur.nins = nins;
 488 }
 489 
 490 #undef IR
 491 #undef fins
 492 #undef emitir
 493 
 494 #endif

/* [<][>][^][v][top][bottom][index][help] */