1/* 2 * Stack-less Just-In-Time compiler 3 * 4 * Copyright 2009-2012 Zoltan Herczeg (hzmester@freemail.hu). All rights reserved. 5 * 6 * Redistribution and use in source and binary forms, with or without modification, are 7 * permitted provided that the following conditions are met: 8 * 9 * 1. Redistributions of source code must retain the above copyright notice, this list of 10 * conditions and the following disclaimer. 11 * 12 * 2. Redistributions in binary form must reproduce the above copyright notice, this list 13 * of conditions and the following disclaimer in the documentation and/or other materials 14 * provided with the distribution. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER(S) AND CONTRIBUTORS ``AS IS'' AND ANY 17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 18 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT 19 * SHALL THE COPYRIGHT HOLDER(S) OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 20 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 21 * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR 22 * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 23 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN 24 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 25 */ 26 27#include "sljitLir.h" 28 29#define CHECK_ERROR() \ 30 do { \ 31 if (SLJIT_UNLIKELY(compiler->error)) \ 32 return compiler->error; \ 33 } while (0) 34 35#define CHECK_ERROR_PTR() \ 36 do { \ 37 if (SLJIT_UNLIKELY(compiler->error)) \ 38 return NULL; \ 39 } while (0) 40 41#define CHECK_ERROR_VOID() \ 42 do { \ 43 if (SLJIT_UNLIKELY(compiler->error)) \ 44 return; \ 45 } while (0) 46 47#define FAIL_IF(expr) \ 48 do { \ 49 if (SLJIT_UNLIKELY(expr)) \ 50 return compiler->error; \ 51 } while (0) 52 53#define PTR_FAIL_IF(expr) \ 54 do { \ 55 if (SLJIT_UNLIKELY(expr)) \ 56 return NULL; \ 57 } while (0) 58 59#define FAIL_IF_NULL(ptr) \ 60 do { \ 61 if (SLJIT_UNLIKELY(!(ptr))) { \ 62 compiler->error = SLJIT_ERR_ALLOC_FAILED; \ 63 return SLJIT_ERR_ALLOC_FAILED; \ 64 } \ 65 } while (0) 66 67#define PTR_FAIL_IF_NULL(ptr) \ 68 do { \ 69 if (SLJIT_UNLIKELY(!(ptr))) { \ 70 compiler->error = SLJIT_ERR_ALLOC_FAILED; \ 71 return NULL; \ 72 } \ 73 } while (0) 74 75#define PTR_FAIL_WITH_EXEC_IF(ptr) \ 76 do { \ 77 if (SLJIT_UNLIKELY(!(ptr))) { \ 78 compiler->error = SLJIT_ERR_EX_ALLOC_FAILED; \ 79 return NULL; \ 80 } \ 81 } while (0) 82 83#if !(defined SLJIT_CONFIG_UNSUPPORTED && SLJIT_CONFIG_UNSUPPORTED) 84 85#define GET_OPCODE(op) \ 86 ((op) & ~(SLJIT_INT_OP | SLJIT_SET_E | SLJIT_SET_U | SLJIT_SET_S | SLJIT_SET_O | SLJIT_SET_C | SLJIT_KEEP_FLAGS)) 87 88#define GET_FLAGS(op) \ 89 ((op) & (SLJIT_SET_E | SLJIT_SET_U | SLJIT_SET_S | SLJIT_SET_O | SLJIT_SET_C)) 90 91#define GET_ALL_FLAGS(op) \ 92 ((op) & (SLJIT_INT_OP | SLJIT_SET_E | SLJIT_SET_U | SLJIT_SET_S | SLJIT_SET_O | SLJIT_SET_C | SLJIT_KEEP_FLAGS)) 93 94#define TYPE_CAST_NEEDED(op) \ 95 (((op) >= SLJIT_MOV_UB && (op) <= SLJIT_MOV_SH) || ((op) >= SLJIT_MOVU_UB && (op) <= SLJIT_MOVU_SH)) 96 97#define BUF_SIZE 4096 98 99#if (defined SLJIT_32BIT_ARCHITECTURE && SLJIT_32BIT_ARCHITECTURE) 100#define ABUF_SIZE 2048 101#else 102#define ABUF_SIZE 4096 103#endif 104 105/* Parameter parsing. */ 106#define REG_MASK 0x3f 107#define OFFS_REG(reg) (((reg) >> 8) & REG_MASK) 108#define OFFS_REG_MASK (REG_MASK << 8) 109#define TO_OFFS_REG(reg) ((reg) << 8) 110/* When reg cannot be unused. */ 111#define FAST_IS_REG(reg) ((reg) <= REG_MASK) 112/* When reg can be unused. */ 113#define SLOW_IS_REG(reg) ((reg) > 0 && (reg) <= REG_MASK) 114 115/* Jump flags. */ 116#define JUMP_LABEL 0x1 117#define JUMP_ADDR 0x2 118/* SLJIT_REWRITABLE_JUMP is 0x1000. */ 119 120#if (defined SLJIT_CONFIG_X86 && SLJIT_CONFIG_X86) 121# define PATCH_MB 0x4 122# define PATCH_MW 0x8 123#if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64) 124# define PATCH_MD 0x10 125#endif 126#endif 127 128#if (defined SLJIT_CONFIG_ARM_V5 && SLJIT_CONFIG_ARM_V5) || (defined SLJIT_CONFIG_ARM_V7 && SLJIT_CONFIG_ARM_V7) 129# define IS_BL 0x4 130# define PATCH_B 0x8 131#endif 132 133#if (defined SLJIT_CONFIG_ARM_V5 && SLJIT_CONFIG_ARM_V5) 134# define CPOOL_SIZE 512 135#endif 136 137#if (defined SLJIT_CONFIG_ARM_THUMB2 && SLJIT_CONFIG_ARM_THUMB2) 138# define IS_COND 0x04 139# define IS_BL 0x08 140 /* conditional + imm8 */ 141# define PATCH_TYPE1 0x10 142 /* conditional + imm20 */ 143# define PATCH_TYPE2 0x20 144 /* IT + imm24 */ 145# define PATCH_TYPE3 0x30 146 /* imm11 */ 147# define PATCH_TYPE4 0x40 148 /* imm24 */ 149# define PATCH_TYPE5 0x50 150 /* BL + imm24 */ 151# define PATCH_BL 0x60 152 /* 0xf00 cc code for branches */ 153#endif 154 155#if (defined SLJIT_CONFIG_ARM_64 && SLJIT_CONFIG_ARM_64) 156# define IS_COND 0x004 157# define IS_CBZ 0x008 158# define IS_BL 0x010 159# define PATCH_B 0x020 160# define PATCH_COND 0x040 161# define PATCH_ABS48 0x080 162# define PATCH_ABS64 0x100 163#endif 164 165#if (defined SLJIT_CONFIG_PPC && SLJIT_CONFIG_PPC) 166# define IS_COND 0x004 167# define IS_CALL 0x008 168# define PATCH_B 0x010 169# define PATCH_ABS_B 0x020 170#if (defined SLJIT_CONFIG_PPC_64 && SLJIT_CONFIG_PPC_64) 171# define PATCH_ABS32 0x040 172# define PATCH_ABS48 0x080 173#endif 174# define REMOVE_COND 0x100 175#endif 176 177#if (defined SLJIT_CONFIG_MIPS && SLJIT_CONFIG_MIPS) 178# define IS_MOVABLE 0x004 179# define IS_JAL 0x008 180# define IS_CALL 0x010 181# define IS_BIT26_COND 0x020 182# define IS_BIT16_COND 0x040 183 184# define IS_COND (IS_BIT26_COND | IS_BIT16_COND) 185 186# define PATCH_B 0x080 187# define PATCH_J 0x100 188 189#if (defined SLJIT_CONFIG_MIPS_64 && SLJIT_CONFIG_MIPS_64) 190# define PATCH_ABS32 0x200 191# define PATCH_ABS48 0x400 192#endif 193 194 /* instruction types */ 195# define MOVABLE_INS 0 196 /* 1 - 31 last destination register */ 197 /* no destination (i.e: store) */ 198# define UNMOVABLE_INS 32 199 /* FPU status register */ 200# define FCSR_FCC 33 201#endif 202 203#if (defined SLJIT_CONFIG_TILEGX && SLJIT_CONFIG_TILEGX) 204# define IS_JAL 0x04 205# define IS_COND 0x08 206 207# define PATCH_B 0x10 208# define PATCH_J 0x20 209#endif 210 211#if (defined SLJIT_CONFIG_SPARC_32 && SLJIT_CONFIG_SPARC_32) 212# define IS_MOVABLE 0x04 213# define IS_COND 0x08 214# define IS_CALL 0x10 215 216# define PATCH_B 0x20 217# define PATCH_CALL 0x40 218 219 /* instruction types */ 220# define MOVABLE_INS 0 221 /* 1 - 31 last destination register */ 222 /* no destination (i.e: store) */ 223# define UNMOVABLE_INS 32 224 225# define DST_INS_MASK 0xff 226 227 /* ICC_SET is the same as SET_FLAGS. */ 228# define ICC_IS_SET (1 << 23) 229# define FCC_IS_SET (1 << 24) 230#endif 231 232/* Stack management. */ 233 234#define GET_SAVED_REGISTERS_SIZE(scratches, saveds, extra) \ 235 (((scratches < SLJIT_NUMBER_OF_SCRATCH_REGISTERS ? 0 : (scratches - SLJIT_NUMBER_OF_SCRATCH_REGISTERS)) + \ 236 (saveds < SLJIT_NUMBER_OF_SAVED_REGISTERS ? saveds : SLJIT_NUMBER_OF_SAVED_REGISTERS) + \ 237 extra) * sizeof(sljit_sw)) 238 239#if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32) 240#define SLJIT_HAS_FIXED_LOCALS_OFFSET 1 241 242#if (defined SLJIT_X86_32_FASTCALL && SLJIT_X86_32_FASTCALL) 243#define FIXED_LOCALS_OFFSET ((2 + 4) * sizeof(sljit_sw)) 244#else 245/* Maximum 3 arguments are passed on the stack. */ 246#define FIXED_LOCALS_OFFSET ((3 + 4) * sizeof(sljit_sw)) 247#endif 248 249#endif /* SLJIT_CONFIG_X86_32 */ 250 251#if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64) 252#define SLJIT_HAS_FIXED_LOCALS_OFFSET 1 253#ifdef _WIN64 254#define FIXED_LOCALS_OFFSET ((4 + 2) * sizeof(sljit_sw)) 255#else 256#define FIXED_LOCALS_OFFSET (sizeof(sljit_sw)) 257#endif 258#endif 259 260#if (defined SLJIT_CONFIG_ARM_64 && SLJIT_CONFIG_ARM_64) 261#define SLJIT_HAS_VARIABLE_LOCALS_OFFSET 1 262#endif 263 264#if (defined SLJIT_CONFIG_PPC_32 && SLJIT_CONFIG_PPC_32) 265#define SLJIT_HAS_FIXED_LOCALS_OFFSET 1 266#ifdef _AIX 267#define FIXED_LOCALS_OFFSET ((6 + 8) * sizeof(sljit_sw)) 268#else 269#define FIXED_LOCALS_OFFSET (3 * sizeof(sljit_sw)) 270#endif 271#endif 272 273#if (defined SLJIT_CONFIG_PPC_64 && SLJIT_CONFIG_PPC_64) 274#define SLJIT_HAS_FIXED_LOCALS_OFFSET 1 275#define FIXED_LOCALS_OFFSET ((6 + 8) * sizeof(sljit_sw)) 276#endif 277 278#if (defined SLJIT_CONFIG_MIPS_32 && SLJIT_CONFIG_MIPS_32) 279#define SLJIT_HAS_FIXED_LOCALS_OFFSET 1 280#define FIXED_LOCALS_OFFSET (4 * sizeof(sljit_sw)) 281#endif 282 283#if (defined SLJIT_CONFIG_MIPS_64 && SLJIT_CONFIG_MIPS_64) 284#define SLJIT_HAS_FIXED_LOCALS_OFFSET 1 285#define FIXED_LOCALS_OFFSET 0 286#endif 287 288#if (defined SLJIT_CONFIG_SPARC_32 && SLJIT_CONFIG_SPARC_32) 289#define SLJIT_HAS_FIXED_LOCALS_OFFSET 1 290#define FIXED_LOCALS_OFFSET (23 * sizeof(sljit_sw)) 291#endif 292 293#if (defined SLJIT_HAS_VARIABLE_LOCALS_OFFSET && SLJIT_HAS_VARIABLE_LOCALS_OFFSET) 294 295#define ADJUST_LOCAL_OFFSET(p, i) \ 296 if ((p) == (SLJIT_MEM1(SLJIT_SP))) \ 297 (i) += compiler->locals_offset; 298 299#elif (defined SLJIT_HAS_FIXED_LOCALS_OFFSET && SLJIT_HAS_FIXED_LOCALS_OFFSET) 300 301#define ADJUST_LOCAL_OFFSET(p, i) \ 302 if ((p) == (SLJIT_MEM1(SLJIT_SP))) \ 303 (i) += FIXED_LOCALS_OFFSET; 304 305#else 306 307#define ADJUST_LOCAL_OFFSET(p, i) 308 309#endif 310 311#endif /* !(defined SLJIT_CONFIG_UNSUPPORTED && SLJIT_CONFIG_UNSUPPORTED) */ 312 313/* Utils can still be used even if SLJIT_CONFIG_UNSUPPORTED is set. */ 314#include "sljitUtils.c" 315 316#if !(defined SLJIT_CONFIG_UNSUPPORTED && SLJIT_CONFIG_UNSUPPORTED) 317 318#if (defined SLJIT_EXECUTABLE_ALLOCATOR && SLJIT_EXECUTABLE_ALLOCATOR) 319#include "sljitExecAllocator.c" 320#endif 321 322/* --------------------------------------------------------------------- */ 323/* Public functions */ 324/* --------------------------------------------------------------------- */ 325 326#if (defined SLJIT_CONFIG_ARM_V5 && SLJIT_CONFIG_ARM_V5) || (defined SLJIT_CONFIG_X86 && SLJIT_CONFIG_X86) 327#define SLJIT_NEEDS_COMPILER_INIT 1 328static sljit_si compiler_initialized = 0; 329/* A thread safe initialization. */ 330static void init_compiler(void); 331#endif 332 333SLJIT_API_FUNC_ATTRIBUTE struct sljit_compiler* sljit_create_compiler(void) 334{ 335 struct sljit_compiler *compiler = (struct sljit_compiler*)SLJIT_MALLOC(sizeof(struct sljit_compiler)); 336 if (!compiler) 337 return NULL; 338 SLJIT_ZEROMEM(compiler, sizeof(struct sljit_compiler)); 339 340 SLJIT_COMPILE_ASSERT( 341 sizeof(sljit_sb) == 1 && sizeof(sljit_ub) == 1 342 && sizeof(sljit_sh) == 2 && sizeof(sljit_uh) == 2 343 && sizeof(sljit_si) == 4 && sizeof(sljit_ui) == 4 344 && (sizeof(sljit_p) == 4 || sizeof(sljit_p) == 8) 345 && sizeof(sljit_p) <= sizeof(sljit_sw) 346 && (sizeof(sljit_sw) == 4 || sizeof(sljit_sw) == 8) 347 && (sizeof(sljit_uw) == 4 || sizeof(sljit_uw) == 8), 348 invalid_integer_types); 349 SLJIT_COMPILE_ASSERT(SLJIT_INT_OP == SLJIT_SINGLE_OP, 350 int_op_and_single_op_must_be_the_same); 351 SLJIT_COMPILE_ASSERT(SLJIT_REWRITABLE_JUMP != SLJIT_SINGLE_OP, 352 rewritable_jump_and_single_op_must_not_be_the_same); 353 354 /* Only the non-zero members must be set. */ 355 compiler->error = SLJIT_SUCCESS; 356 357 compiler->buf = (struct sljit_memory_fragment*)SLJIT_MALLOC(BUF_SIZE); 358 compiler->abuf = (struct sljit_memory_fragment*)SLJIT_MALLOC(ABUF_SIZE); 359 360 if (!compiler->buf || !compiler->abuf) { 361 if (compiler->buf) 362 SLJIT_FREE(compiler->buf); 363 if (compiler->abuf) 364 SLJIT_FREE(compiler->abuf); 365 SLJIT_FREE(compiler); 366 return NULL; 367 } 368 369 compiler->buf->next = NULL; 370 compiler->buf->used_size = 0; 371 compiler->abuf->next = NULL; 372 compiler->abuf->used_size = 0; 373 374 compiler->scratches = -1; 375 compiler->saveds = -1; 376 compiler->fscratches = -1; 377 compiler->fsaveds = -1; 378 379#if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32) 380 compiler->args = -1; 381#endif 382 383#if (defined SLJIT_CONFIG_ARM_V5 && SLJIT_CONFIG_ARM_V5) 384 compiler->cpool = (sljit_uw*)SLJIT_MALLOC(CPOOL_SIZE * sizeof(sljit_uw) + CPOOL_SIZE * sizeof(sljit_ub)); 385 if (!compiler->cpool) { 386 SLJIT_FREE(compiler->buf); 387 SLJIT_FREE(compiler->abuf); 388 SLJIT_FREE(compiler); 389 return NULL; 390 } 391 compiler->cpool_unique = (sljit_ub*)(compiler->cpool + CPOOL_SIZE); 392 compiler->cpool_diff = 0xffffffff; 393#endif 394 395#if (defined SLJIT_CONFIG_MIPS && SLJIT_CONFIG_MIPS) 396 compiler->delay_slot = UNMOVABLE_INS; 397#endif 398 399#if (defined SLJIT_CONFIG_SPARC_32 && SLJIT_CONFIG_SPARC_32) 400 compiler->delay_slot = UNMOVABLE_INS; 401#endif 402 403#if (defined SLJIT_NEEDS_COMPILER_INIT && SLJIT_NEEDS_COMPILER_INIT) 404 if (!compiler_initialized) { 405 init_compiler(); 406 compiler_initialized = 1; 407 } 408#endif 409 410 return compiler; 411} 412 413SLJIT_API_FUNC_ATTRIBUTE void sljit_free_compiler(struct sljit_compiler *compiler) 414{ 415 struct sljit_memory_fragment *buf; 416 struct sljit_memory_fragment *curr; 417 418 buf = compiler->buf; 419 while (buf) { 420 curr = buf; 421 buf = buf->next; 422 SLJIT_FREE(curr); 423 } 424 425 buf = compiler->abuf; 426 while (buf) { 427 curr = buf; 428 buf = buf->next; 429 SLJIT_FREE(curr); 430 } 431 432#if (defined SLJIT_CONFIG_ARM_V5 && SLJIT_CONFIG_ARM_V5) 433 SLJIT_FREE(compiler->cpool); 434#endif 435 SLJIT_FREE(compiler); 436} 437 438#if (defined SLJIT_CONFIG_ARM_THUMB2 && SLJIT_CONFIG_ARM_THUMB2) 439SLJIT_API_FUNC_ATTRIBUTE void sljit_free_code(void* code) 440{ 441 /* Remove thumb mode flag. */ 442 SLJIT_FREE_EXEC((void*)((sljit_uw)code & ~0x1)); 443} 444#elif (defined SLJIT_INDIRECT_CALL && SLJIT_INDIRECT_CALL) 445SLJIT_API_FUNC_ATTRIBUTE void sljit_free_code(void* code) 446{ 447 /* Resolve indirection. */ 448 code = (void*)(*(sljit_uw*)code); 449 SLJIT_FREE_EXEC(code); 450} 451#else 452SLJIT_API_FUNC_ATTRIBUTE void sljit_free_code(void* code) 453{ 454 SLJIT_FREE_EXEC(code); 455} 456#endif 457 458SLJIT_API_FUNC_ATTRIBUTE void sljit_set_label(struct sljit_jump *jump, struct sljit_label* label) 459{ 460 if (SLJIT_LIKELY(!!jump) && SLJIT_LIKELY(!!label)) { 461 jump->flags &= ~JUMP_ADDR; 462 jump->flags |= JUMP_LABEL; 463 jump->u.label = label; 464 } 465} 466 467SLJIT_API_FUNC_ATTRIBUTE void sljit_set_target(struct sljit_jump *jump, sljit_uw target) 468{ 469 if (SLJIT_LIKELY(!!jump)) { 470 jump->flags &= ~JUMP_LABEL; 471 jump->flags |= JUMP_ADDR; 472 jump->u.target = target; 473 } 474} 475 476/* --------------------------------------------------------------------- */ 477/* Private functions */ 478/* --------------------------------------------------------------------- */ 479 480static void* ensure_buf(struct sljit_compiler *compiler, sljit_uw size) 481{ 482 sljit_ub *ret; 483 struct sljit_memory_fragment *new_frag; 484 485 SLJIT_ASSERT(size <= 256); 486 if (compiler->buf->used_size + size <= (BUF_SIZE - (sljit_uw)SLJIT_OFFSETOF(struct sljit_memory_fragment, memory))) { 487 ret = compiler->buf->memory + compiler->buf->used_size; 488 compiler->buf->used_size += size; 489 return ret; 490 } 491 new_frag = (struct sljit_memory_fragment*)SLJIT_MALLOC(BUF_SIZE); 492 PTR_FAIL_IF_NULL(new_frag); 493 new_frag->next = compiler->buf; 494 compiler->buf = new_frag; 495 new_frag->used_size = size; 496 return new_frag->memory; 497} 498 499static void* ensure_abuf(struct sljit_compiler *compiler, sljit_uw size) 500{ 501 sljit_ub *ret; 502 struct sljit_memory_fragment *new_frag; 503 504 SLJIT_ASSERT(size <= 256); 505 if (compiler->abuf->used_size + size <= (ABUF_SIZE - (sljit_uw)SLJIT_OFFSETOF(struct sljit_memory_fragment, memory))) { 506 ret = compiler->abuf->memory + compiler->abuf->used_size; 507 compiler->abuf->used_size += size; 508 return ret; 509 } 510 new_frag = (struct sljit_memory_fragment*)SLJIT_MALLOC(ABUF_SIZE); 511 PTR_FAIL_IF_NULL(new_frag); 512 new_frag->next = compiler->abuf; 513 compiler->abuf = new_frag; 514 new_frag->used_size = size; 515 return new_frag->memory; 516} 517 518SLJIT_API_FUNC_ATTRIBUTE void* sljit_alloc_memory(struct sljit_compiler *compiler, sljit_si size) 519{ 520 CHECK_ERROR_PTR(); 521 522#if (defined SLJIT_64BIT_ARCHITECTURE && SLJIT_64BIT_ARCHITECTURE) 523 if (size <= 0 || size > 128) 524 return NULL; 525 size = (size + 7) & ~7; 526#else 527 if (size <= 0 || size > 64) 528 return NULL; 529 size = (size + 3) & ~3; 530#endif 531 return ensure_abuf(compiler, size); 532} 533 534static SLJIT_INLINE void reverse_buf(struct sljit_compiler *compiler) 535{ 536 struct sljit_memory_fragment *buf = compiler->buf; 537 struct sljit_memory_fragment *prev = NULL; 538 struct sljit_memory_fragment *tmp; 539 540 do { 541 tmp = buf->next; 542 buf->next = prev; 543 prev = buf; 544 buf = tmp; 545 } while (buf != NULL); 546 547 compiler->buf = prev; 548} 549 550static SLJIT_INLINE void set_label(struct sljit_label *label, struct sljit_compiler *compiler) 551{ 552 label->next = NULL; 553 label->size = compiler->size; 554 if (compiler->last_label) 555 compiler->last_label->next = label; 556 else 557 compiler->labels = label; 558 compiler->last_label = label; 559} 560 561static SLJIT_INLINE void set_jump(struct sljit_jump *jump, struct sljit_compiler *compiler, sljit_si flags) 562{ 563 jump->next = NULL; 564 jump->flags = flags; 565 if (compiler->last_jump) 566 compiler->last_jump->next = jump; 567 else 568 compiler->jumps = jump; 569 compiler->last_jump = jump; 570} 571 572static SLJIT_INLINE void set_const(struct sljit_const *const_, struct sljit_compiler *compiler) 573{ 574 const_->next = NULL; 575 const_->addr = compiler->size; 576 if (compiler->last_const) 577 compiler->last_const->next = const_; 578 else 579 compiler->consts = const_; 580 compiler->last_const = const_; 581} 582 583#define ADDRESSING_DEPENDS_ON(exp, reg) \ 584 (((exp) & SLJIT_MEM) && (((exp) & REG_MASK) == reg || OFFS_REG(exp) == reg)) 585 586#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 587#define FUNCTION_CHECK_OP() \ 588 SLJIT_ASSERT(!GET_FLAGS(op) || !(op & SLJIT_KEEP_FLAGS)); \ 589 switch (GET_OPCODE(op)) { \ 590 case SLJIT_NOT: \ 591 case SLJIT_CLZ: \ 592 case SLJIT_AND: \ 593 case SLJIT_OR: \ 594 case SLJIT_XOR: \ 595 case SLJIT_SHL: \ 596 case SLJIT_LSHR: \ 597 case SLJIT_ASHR: \ 598 SLJIT_ASSERT(!(op & (SLJIT_SET_U | SLJIT_SET_S | SLJIT_SET_O | SLJIT_SET_C))); \ 599 break; \ 600 case SLJIT_NEG: \ 601 SLJIT_ASSERT(!(op & (SLJIT_SET_U | SLJIT_SET_S | SLJIT_SET_C))); \ 602 break; \ 603 case SLJIT_MUL: \ 604 SLJIT_ASSERT(!(op & (SLJIT_SET_E | SLJIT_SET_U | SLJIT_SET_S | SLJIT_SET_C))); \ 605 break; \ 606 case SLJIT_ADD: \ 607 SLJIT_ASSERT(!(op & (SLJIT_SET_U | SLJIT_SET_S))); \ 608 break; \ 609 case SLJIT_SUB: \ 610 break; \ 611 case SLJIT_ADDC: \ 612 case SLJIT_SUBC: \ 613 SLJIT_ASSERT(!(op & (SLJIT_SET_E | SLJIT_SET_U | SLJIT_SET_S | SLJIT_SET_O))); \ 614 break; \ 615 case SLJIT_BREAKPOINT: \ 616 case SLJIT_NOP: \ 617 case SLJIT_UMUL: \ 618 case SLJIT_SMUL: \ 619 case SLJIT_MOV: \ 620 case SLJIT_MOV_UI: \ 621 case SLJIT_MOV_P: \ 622 case SLJIT_MOVU: \ 623 case SLJIT_MOVU_UI: \ 624 case SLJIT_MOVU_P: \ 625 /* Nothing allowed */ \ 626 SLJIT_ASSERT(!(op & (SLJIT_INT_OP | SLJIT_SET_E | SLJIT_SET_U | SLJIT_SET_S | SLJIT_SET_O | SLJIT_SET_C | SLJIT_KEEP_FLAGS))); \ 627 break; \ 628 default: \ 629 /* Only SLJIT_INT_OP or SLJIT_SINGLE_OP is allowed. */ \ 630 SLJIT_ASSERT(!(op & (SLJIT_SET_E | SLJIT_SET_U | SLJIT_SET_S | SLJIT_SET_O | SLJIT_SET_C | SLJIT_KEEP_FLAGS))); \ 631 break; \ 632 } 633 634#define FUNCTION_CHECK_FOP() \ 635 SLJIT_ASSERT(!GET_FLAGS(op) || !(op & SLJIT_KEEP_FLAGS)); \ 636 switch (GET_OPCODE(op)) { \ 637 case SLJIT_CMPD: \ 638 SLJIT_ASSERT(!(op & (SLJIT_SET_U | SLJIT_SET_O | SLJIT_SET_C | SLJIT_KEEP_FLAGS))); \ 639 SLJIT_ASSERT((op & (SLJIT_SET_E | SLJIT_SET_S))); \ 640 break; \ 641 default: \ 642 /* Only SLJIT_INT_OP or SLJIT_SINGLE_OP is allowed. */ \ 643 SLJIT_ASSERT(!(op & (SLJIT_SET_E | SLJIT_SET_U | SLJIT_SET_S | SLJIT_SET_O | SLJIT_SET_C | SLJIT_KEEP_FLAGS))); \ 644 break; \ 645 } 646 647#define FUNCTION_CHECK_IS_REG(r) \ 648 ((r) == SLJIT_UNUSED || \ 649 ((r) >= SLJIT_R0 && (r) < (SLJIT_R0 + compiler->scratches)) || \ 650 ((r) > (SLJIT_S0 - compiler->saveds) && (r) <= SLJIT_S0)) 651 652#if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32) 653#define FUNCTION_ASSERT_IF_VIRTUAL(p) \ 654 SLJIT_ASSERT((p) < SLJIT_R3 || (p) > SLJIT_R6); 655#else 656#define FUNCTION_ASSERT_IF_VIRTUAL(p) 657#endif 658 659#define FUNCTION_CHECK_SRC(p, i) \ 660 SLJIT_ASSERT(compiler->scratches != -1 && compiler->saveds != -1); \ 661 if (FUNCTION_CHECK_IS_REG(p)) \ 662 SLJIT_ASSERT((i) == 0 && (p) != SLJIT_UNUSED); \ 663 else if ((p) == SLJIT_IMM) \ 664 ; \ 665 else if ((p) == (SLJIT_MEM1(SLJIT_SP))) \ 666 SLJIT_ASSERT((i) >= 0 && (i) < compiler->logical_local_size); \ 667 else if ((p) & SLJIT_MEM) { \ 668 SLJIT_ASSERT(FUNCTION_CHECK_IS_REG((p) & REG_MASK)); \ 669 FUNCTION_ASSERT_IF_VIRTUAL((p) & REG_MASK); \ 670 if ((p) & OFFS_REG_MASK) { \ 671 SLJIT_ASSERT(FUNCTION_CHECK_IS_REG(OFFS_REG(p))); \ 672 FUNCTION_ASSERT_IF_VIRTUAL(OFFS_REG(p)); \ 673 SLJIT_ASSERT(!((i) & ~0x3)); \ 674 } \ 675 SLJIT_ASSERT(!((p) & ~(SLJIT_MEM | SLJIT_IMM | REG_MASK | OFFS_REG_MASK))); \ 676 } \ 677 else \ 678 SLJIT_ASSERT_STOP(); 679 680#define FUNCTION_CHECK_DST(p, i) \ 681 SLJIT_ASSERT(compiler->scratches != -1 && compiler->saveds != -1); \ 682 if (FUNCTION_CHECK_IS_REG(p)) \ 683 SLJIT_ASSERT((i) == 0); \ 684 else if ((p) == (SLJIT_MEM1(SLJIT_SP))) \ 685 SLJIT_ASSERT((i) >= 0 && (i) < compiler->logical_local_size); \ 686 else if ((p) & SLJIT_MEM) { \ 687 SLJIT_ASSERT(FUNCTION_CHECK_IS_REG((p) & REG_MASK)); \ 688 FUNCTION_ASSERT_IF_VIRTUAL((p) & REG_MASK); \ 689 if ((p) & OFFS_REG_MASK) { \ 690 SLJIT_ASSERT(FUNCTION_CHECK_IS_REG(OFFS_REG(p))); \ 691 FUNCTION_ASSERT_IF_VIRTUAL(OFFS_REG(p)); \ 692 SLJIT_ASSERT(!((i) & ~0x3)); \ 693 } \ 694 SLJIT_ASSERT(!((p) & ~(SLJIT_MEM | SLJIT_IMM | REG_MASK | OFFS_REG_MASK))); \ 695 } \ 696 else \ 697 SLJIT_ASSERT_STOP(); 698 699#define FUNCTION_FCHECK(p, i) \ 700 SLJIT_ASSERT(compiler->fscratches != -1 && compiler->fsaveds != -1); \ 701 if (((p) >= SLJIT_FR0 && (p) < (SLJIT_FR0 + compiler->fscratches)) || \ 702 ((p) > (SLJIT_FS0 - compiler->fsaveds) && (p) <= SLJIT_FS0)) \ 703 SLJIT_ASSERT(i == 0); \ 704 else if ((p) == (SLJIT_MEM1(SLJIT_SP))) \ 705 SLJIT_ASSERT((i) >= 0 && (i) < compiler->logical_local_size); \ 706 else if ((p) & SLJIT_MEM) { \ 707 SLJIT_ASSERT(FUNCTION_CHECK_IS_REG((p) & REG_MASK)); \ 708 FUNCTION_ASSERT_IF_VIRTUAL((p) & REG_MASK); \ 709 if ((p) & OFFS_REG_MASK) { \ 710 SLJIT_ASSERT(FUNCTION_CHECK_IS_REG(OFFS_REG(p))); \ 711 FUNCTION_ASSERT_IF_VIRTUAL(OFFS_REG(p)); \ 712 SLJIT_ASSERT(((p) & OFFS_REG_MASK) != TO_OFFS_REG(SLJIT_SP) && !(i & ~0x3)); \ 713 } else \ 714 SLJIT_ASSERT(OFFS_REG(p) == 0); \ 715 SLJIT_ASSERT(!((p) & ~(SLJIT_MEM | SLJIT_IMM | REG_MASK | OFFS_REG_MASK))); \ 716 } \ 717 else \ 718 SLJIT_ASSERT_STOP(); 719 720#define FUNCTION_CHECK_OP1() \ 721 if (GET_OPCODE(op) >= SLJIT_MOVU && GET_OPCODE(op) <= SLJIT_MOVU_P) { \ 722 SLJIT_ASSERT(!(src & SLJIT_MEM) || (src & REG_MASK) != SLJIT_SP); \ 723 SLJIT_ASSERT(!(dst & SLJIT_MEM) || (dst & REG_MASK) != SLJIT_SP); \ 724 if ((src & SLJIT_MEM) && (src & REG_MASK)) \ 725 SLJIT_ASSERT((dst & REG_MASK) != (src & REG_MASK) && OFFS_REG(dst) != (src & REG_MASK)); \ 726 } 727 728#endif 729 730#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 731 732SLJIT_API_FUNC_ATTRIBUTE void sljit_compiler_verbose(struct sljit_compiler *compiler, FILE* verbose) 733{ 734 compiler->verbose = verbose; 735} 736 737#if (defined SLJIT_64BIT_ARCHITECTURE && SLJIT_64BIT_ARCHITECTURE) 738#ifdef _WIN64 739# define SLJIT_PRINT_D "I64" 740#else 741# define SLJIT_PRINT_D "l" 742#endif 743#else 744# define SLJIT_PRINT_D "" 745#endif 746 747#define sljit_verbose_reg(compiler, r) \ 748 do { \ 749 if ((r) < (SLJIT_R0 + compiler->scratches)) \ 750 fprintf(compiler->verbose, "r%d", (r) - SLJIT_R0); \ 751 else \ 752 fprintf(compiler->verbose, "s%d", SLJIT_NUMBER_OF_REGISTERS - (r)); \ 753 } while (0) 754 755#define sljit_verbose_param(compiler, p, i) \ 756 if ((p) & SLJIT_IMM) \ 757 fprintf(compiler->verbose, "#%" SLJIT_PRINT_D "d", (i)); \ 758 else if ((p) & SLJIT_MEM) { \ 759 if ((p) & REG_MASK) { \ 760 fputc('[', compiler->verbose); \ 761 sljit_verbose_reg(compiler, (p) & REG_MASK); \ 762 if ((p) & OFFS_REG_MASK) { \ 763 fprintf(compiler->verbose, " + "); \ 764 sljit_verbose_reg(compiler, OFFS_REG(p)); \ 765 if (i) \ 766 fprintf(compiler->verbose, " * %d", 1 << (i)); \ 767 } \ 768 else if (i) \ 769 fprintf(compiler->verbose, " + %" SLJIT_PRINT_D "d", (i)); \ 770 fputc(']', compiler->verbose); \ 771 } \ 772 else \ 773 fprintf(compiler->verbose, "[#%" SLJIT_PRINT_D "d]", (i)); \ 774 } else if (p) \ 775 sljit_verbose_reg(compiler, p); \ 776 else \ 777 fprintf(compiler->verbose, "unused"); 778 779#define sljit_verbose_fparam(compiler, p, i) \ 780 if ((p) & SLJIT_MEM) { \ 781 if ((p) & REG_MASK) { \ 782 fputc('[', compiler->verbose); \ 783 sljit_verbose_reg(compiler, (p) & REG_MASK); \ 784 if ((p) & OFFS_REG_MASK) { \ 785 fprintf(compiler->verbose, " + "); \ 786 sljit_verbose_reg(compiler, OFFS_REG(p)); \ 787 if (i) \ 788 fprintf(compiler->verbose, "%d", 1 << (i)); \ 789 } \ 790 else if (i) \ 791 fprintf(compiler->verbose, "%" SLJIT_PRINT_D "d", (i)); \ 792 fputc(']', compiler->verbose); \ 793 } \ 794 else \ 795 fprintf(compiler->verbose, "[#%" SLJIT_PRINT_D "d]", (i)); \ 796 } \ 797 else { \ 798 if ((p) < (SLJIT_FR0 + compiler->fscratches)) \ 799 fprintf(compiler->verbose, "fr%d", (p) - SLJIT_FR0); \ 800 else \ 801 fprintf(compiler->verbose, "fs%d", SLJIT_NUMBER_OF_FLOAT_REGISTERS - (p)); \ 802 } 803 804static SLJIT_CONST char* op0_names[] = { 805 (char*)"breakpoint", (char*)"nop", 806 (char*)"umul", (char*)"smul", (char*)"udiv", (char*)"sdiv", 807}; 808 809static SLJIT_CONST char* op1_names[] = { 810 (char*)"mov", (char*)"mov.ub", (char*)"mov.sb", (char*)"mov.uh", 811 (char*)"mov.sh", (char*)"mov.ui", (char*)"mov.si", (char*)"mov.p", 812 (char*)"movu", (char*)"movu.ub", (char*)"movu.sb", (char*)"movu.uh", 813 (char*)"movu.sh", (char*)"movu.ui", (char*)"movu.si", (char*)"movu.p", 814 (char*)"not", (char*)"neg", (char*)"clz", 815}; 816 817static SLJIT_CONST char* op2_names[] = { 818 (char*)"add", (char*)"addc", (char*)"sub", (char*)"subc", 819 (char*)"mul", (char*)"and", (char*)"or", (char*)"xor", 820 (char*)"shl", (char*)"lshr", (char*)"ashr", 821}; 822 823static SLJIT_CONST char* fop1_names[] = { 824 (char*)"mov", (char*)"conv", (char*)"conv", (char*)"conv", 825 (char*)"conv", (char*)"conv", (char*)"cmp", (char*)"neg", 826 (char*)"abs", 827}; 828 829static SLJIT_CONST char* fop2_names[] = { 830 (char*)"add", (char*)"sub", (char*)"mul", (char*)"div" 831}; 832 833static char* jump_names[] = { 834 (char*)"equal", (char*)"not_equal", 835 (char*)"less", (char*)"greater_equal", 836 (char*)"greater", (char*)"less_equal", 837 (char*)"sig_less", (char*)"sig_greater_equal", 838 (char*)"sig_greater", (char*)"sig_less_equal", 839 (char*)"overflow", (char*)"not_overflow", 840 (char*)"mul_overflow", (char*)"mul_not_overflow", 841 (char*)"float_equal", (char*)"float_not_equal", 842 (char*)"float_less", (char*)"float_greater_equal", 843 (char*)"float_greater", (char*)"float_less_equal", 844 (char*)"float_unordered", (char*)"float_ordered", 845 (char*)"jump", (char*)"fast_call", 846 (char*)"call0", (char*)"call1", (char*)"call2", (char*)"call3" 847}; 848 849#endif 850 851/* --------------------------------------------------------------------- */ 852/* Arch dependent */ 853/* --------------------------------------------------------------------- */ 854 855static SLJIT_INLINE void check_sljit_generate_code(struct sljit_compiler *compiler) 856{ 857#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 858 struct sljit_jump *jump; 859#endif 860 /* If debug and verbose are disabled, all arguments are unused. */ 861 SLJIT_UNUSED_ARG(compiler); 862 863 SLJIT_ASSERT(compiler->size > 0); 864#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 865 jump = compiler->jumps; 866 while (jump) { 867 /* All jumps have target. */ 868 SLJIT_ASSERT(jump->flags & (JUMP_LABEL | JUMP_ADDR)); 869 jump = jump->next; 870 } 871#endif 872} 873 874static SLJIT_INLINE void check_sljit_emit_enter(struct sljit_compiler *compiler, 875 sljit_si options, sljit_si args, sljit_si scratches, sljit_si saveds, 876 sljit_si fscratches, sljit_si fsaveds, sljit_si local_size) 877{ 878 /* If debug and verbose are disabled, all arguments are unused. */ 879 SLJIT_UNUSED_ARG(compiler); 880 SLJIT_UNUSED_ARG(options); 881 SLJIT_UNUSED_ARG(args); 882 SLJIT_UNUSED_ARG(scratches); 883 SLJIT_UNUSED_ARG(saveds); 884 SLJIT_UNUSED_ARG(fscratches); 885 SLJIT_UNUSED_ARG(fsaveds); 886 SLJIT_UNUSED_ARG(local_size); 887 888 SLJIT_ASSERT(options == 0); 889 SLJIT_ASSERT(args >= 0 && args <= 3); 890 SLJIT_ASSERT(scratches >= 0 && scratches <= SLJIT_NUMBER_OF_REGISTERS); 891 SLJIT_ASSERT(saveds >= 0 && saveds <= SLJIT_NUMBER_OF_REGISTERS); 892 SLJIT_ASSERT(scratches + saveds <= SLJIT_NUMBER_OF_REGISTERS); 893 SLJIT_ASSERT(args <= saveds); 894 SLJIT_ASSERT(fscratches >= 0 && fscratches <= SLJIT_NUMBER_OF_FLOAT_REGISTERS); 895 SLJIT_ASSERT(fsaveds >= 0 && fsaveds <= SLJIT_NUMBER_OF_FLOAT_REGISTERS); 896 SLJIT_ASSERT(fscratches + fsaveds <= SLJIT_NUMBER_OF_FLOAT_REGISTERS); 897 SLJIT_ASSERT(local_size >= 0 && local_size <= SLJIT_MAX_LOCAL_SIZE); 898#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 899 if (SLJIT_UNLIKELY(!!compiler->verbose)) 900 fprintf(compiler->verbose, " enter options:none args:%d scratches:%d saveds:%d fscratches:%d fsaveds:%d local_size:%d\n", 901 args, scratches, saveds, fscratches, fsaveds, local_size); 902#endif 903} 904 905static SLJIT_INLINE void check_sljit_set_context(struct sljit_compiler *compiler, 906 sljit_si options, sljit_si args, sljit_si scratches, sljit_si saveds, 907 sljit_si fscratches, sljit_si fsaveds, sljit_si local_size) 908{ 909 /* If debug and verbose are disabled, all arguments are unused. */ 910 SLJIT_UNUSED_ARG(compiler); 911 SLJIT_UNUSED_ARG(options); 912 SLJIT_UNUSED_ARG(args); 913 SLJIT_UNUSED_ARG(scratches); 914 SLJIT_UNUSED_ARG(saveds); 915 SLJIT_UNUSED_ARG(fscratches); 916 SLJIT_UNUSED_ARG(fsaveds); 917 SLJIT_UNUSED_ARG(local_size); 918 919#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 920 if (SLJIT_UNLIKELY(compiler->skip_checks)) { 921 compiler->skip_checks = 0; 922 return; 923 } 924#endif 925 926 SLJIT_ASSERT(options == 0); 927 SLJIT_ASSERT(args >= 0 && args <= 3); 928 SLJIT_ASSERT(scratches >= 0 && scratches <= SLJIT_NUMBER_OF_REGISTERS); 929 SLJIT_ASSERT(saveds >= 0 && saveds <= SLJIT_NUMBER_OF_REGISTERS); 930 SLJIT_ASSERT(scratches + saveds <= SLJIT_NUMBER_OF_REGISTERS); 931 SLJIT_ASSERT(args <= saveds); 932 SLJIT_ASSERT(fscratches >= 0 && fscratches <= SLJIT_NUMBER_OF_FLOAT_REGISTERS); 933 SLJIT_ASSERT(fsaveds >= 0 && fsaveds <= SLJIT_NUMBER_OF_FLOAT_REGISTERS); 934 SLJIT_ASSERT(fscratches + fsaveds <= SLJIT_NUMBER_OF_FLOAT_REGISTERS); 935 SLJIT_ASSERT(local_size >= 0 && local_size <= SLJIT_MAX_LOCAL_SIZE); 936#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 937 if (SLJIT_UNLIKELY(!!compiler->verbose)) 938 fprintf(compiler->verbose, " set_context options:none args:%d scratches:%d saveds:%d fscratches:%d fsaveds:%d local_size:%d\n", 939 args, scratches, saveds, fscratches, fsaveds, local_size); 940#endif 941} 942 943static SLJIT_INLINE void check_sljit_emit_return(struct sljit_compiler *compiler, sljit_si op, sljit_si src, sljit_sw srcw) 944{ 945 /* If debug and verbose are disabled, all arguments are unused. */ 946 SLJIT_UNUSED_ARG(compiler); 947 SLJIT_UNUSED_ARG(op); 948 SLJIT_UNUSED_ARG(src); 949 SLJIT_UNUSED_ARG(srcw); 950 951#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 952 if (op != SLJIT_UNUSED) { 953 SLJIT_ASSERT(op >= SLJIT_MOV && op <= SLJIT_MOV_P); 954 FUNCTION_CHECK_SRC(src, srcw); 955 } 956 else 957 SLJIT_ASSERT(src == 0 && srcw == 0); 958#endif 959#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 960 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 961 if (op == SLJIT_UNUSED) 962 fprintf(compiler->verbose, " return\n"); 963 else { 964 fprintf(compiler->verbose, " return.%s ", op1_names[op - SLJIT_OP1_BASE]); 965 sljit_verbose_param(compiler, src, srcw); 966 fprintf(compiler->verbose, "\n"); 967 } 968 } 969#endif 970} 971 972static SLJIT_INLINE void check_sljit_emit_fast_enter(struct sljit_compiler *compiler, sljit_si dst, sljit_sw dstw) 973{ 974 /* If debug and verbose are disabled, all arguments are unused. */ 975 SLJIT_UNUSED_ARG(compiler); 976 SLJIT_UNUSED_ARG(dst); 977 SLJIT_UNUSED_ARG(dstw); 978 979#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 980 FUNCTION_CHECK_DST(dst, dstw); 981#endif 982#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 983 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 984 fprintf(compiler->verbose, " fast_enter "); 985 sljit_verbose_param(compiler, dst, dstw); 986 fprintf(compiler->verbose, "\n"); 987 } 988#endif 989} 990 991static SLJIT_INLINE void check_sljit_emit_fast_return(struct sljit_compiler *compiler, sljit_si src, sljit_sw srcw) 992{ 993 /* If debug and verbose are disabled, all arguments are unused. */ 994 SLJIT_UNUSED_ARG(compiler); 995 SLJIT_UNUSED_ARG(src); 996 SLJIT_UNUSED_ARG(srcw); 997 998#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 999 FUNCTION_CHECK_SRC(src, srcw); 1000#endif 1001#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1002 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1003 fprintf(compiler->verbose, " fast_return "); 1004 sljit_verbose_param(compiler, src, srcw); 1005 fprintf(compiler->verbose, "\n"); 1006 } 1007#endif 1008} 1009 1010static SLJIT_INLINE void check_sljit_emit_op0(struct sljit_compiler *compiler, sljit_si op) 1011{ 1012 /* If debug and verbose are disabled, all arguments are unused. */ 1013 SLJIT_UNUSED_ARG(compiler); 1014 SLJIT_UNUSED_ARG(op); 1015 1016 SLJIT_ASSERT((op >= SLJIT_BREAKPOINT && op <= SLJIT_SMUL) 1017 || ((op & ~SLJIT_INT_OP) >= SLJIT_UDIV && (op & ~SLJIT_INT_OP) <= SLJIT_SDIV)); 1018 SLJIT_ASSERT(op < SLJIT_UMUL || compiler->scratches >= 2); 1019#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1020 if (SLJIT_UNLIKELY(!!compiler->verbose)) 1021 fprintf(compiler->verbose, " %s%s\n", !(op & SLJIT_INT_OP) ? "" : "i", op0_names[GET_OPCODE(op) - SLJIT_OP0_BASE]); 1022#endif 1023} 1024 1025static SLJIT_INLINE void check_sljit_emit_op1(struct sljit_compiler *compiler, sljit_si op, 1026 sljit_si dst, sljit_sw dstw, 1027 sljit_si src, sljit_sw srcw) 1028{ 1029 /* If debug and verbose are disabled, all arguments are unused. */ 1030 SLJIT_UNUSED_ARG(compiler); 1031 SLJIT_UNUSED_ARG(op); 1032 SLJIT_UNUSED_ARG(dst); 1033 SLJIT_UNUSED_ARG(dstw); 1034 SLJIT_UNUSED_ARG(src); 1035 SLJIT_UNUSED_ARG(srcw); 1036 1037#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1038 if (SLJIT_UNLIKELY(compiler->skip_checks)) { 1039 compiler->skip_checks = 0; 1040 return; 1041 } 1042#endif 1043 1044 SLJIT_ASSERT(GET_OPCODE(op) >= SLJIT_MOV && GET_OPCODE(op) <= SLJIT_CLZ); 1045#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 1046 FUNCTION_CHECK_OP(); 1047 FUNCTION_CHECK_SRC(src, srcw); 1048 FUNCTION_CHECK_DST(dst, dstw); 1049 FUNCTION_CHECK_OP1(); 1050#endif 1051#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1052 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1053 fprintf(compiler->verbose, " %s%s%s%s%s%s%s%s ", !(op & SLJIT_INT_OP) ? "" : "i", op1_names[GET_OPCODE(op) - SLJIT_OP1_BASE], 1054 !(op & SLJIT_SET_E) ? "" : ".e", !(op & SLJIT_SET_U) ? "" : ".u", !(op & SLJIT_SET_S) ? "" : ".s", 1055 !(op & SLJIT_SET_O) ? "" : ".o", !(op & SLJIT_SET_C) ? "" : ".c", !(op & SLJIT_KEEP_FLAGS) ? "" : ".k"); 1056 sljit_verbose_param(compiler, dst, dstw); 1057 fprintf(compiler->verbose, ", "); 1058 sljit_verbose_param(compiler, src, srcw); 1059 fprintf(compiler->verbose, "\n"); 1060 } 1061#endif 1062} 1063 1064static SLJIT_INLINE void check_sljit_emit_op2(struct sljit_compiler *compiler, sljit_si op, 1065 sljit_si dst, sljit_sw dstw, 1066 sljit_si src1, sljit_sw src1w, 1067 sljit_si src2, sljit_sw src2w) 1068{ 1069 /* If debug and verbose are disabled, all arguments are unused. */ 1070 SLJIT_UNUSED_ARG(compiler); 1071 SLJIT_UNUSED_ARG(op); 1072 SLJIT_UNUSED_ARG(dst); 1073 SLJIT_UNUSED_ARG(dstw); 1074 SLJIT_UNUSED_ARG(src1); 1075 SLJIT_UNUSED_ARG(src1w); 1076 SLJIT_UNUSED_ARG(src2); 1077 SLJIT_UNUSED_ARG(src2w); 1078 1079#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1080 if (SLJIT_UNLIKELY(compiler->skip_checks)) { 1081 compiler->skip_checks = 0; 1082 return; 1083 } 1084#endif 1085 1086 SLJIT_ASSERT(GET_OPCODE(op) >= SLJIT_ADD && GET_OPCODE(op) <= SLJIT_ASHR); 1087#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 1088 FUNCTION_CHECK_OP(); 1089 FUNCTION_CHECK_SRC(src1, src1w); 1090 FUNCTION_CHECK_SRC(src2, src2w); 1091 FUNCTION_CHECK_DST(dst, dstw); 1092#endif 1093#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1094 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1095 fprintf(compiler->verbose, " %s%s%s%s%s%s%s%s ", !(op & SLJIT_INT_OP) ? "" : "i", op2_names[GET_OPCODE(op) - SLJIT_OP2_BASE], 1096 !(op & SLJIT_SET_E) ? "" : ".e", !(op & SLJIT_SET_U) ? "" : ".u", !(op & SLJIT_SET_S) ? "" : ".s", 1097 !(op & SLJIT_SET_O) ? "" : ".o", !(op & SLJIT_SET_C) ? "" : ".c", !(op & SLJIT_KEEP_FLAGS) ? "" : ".k"); 1098 sljit_verbose_param(compiler, dst, dstw); 1099 fprintf(compiler->verbose, ", "); 1100 sljit_verbose_param(compiler, src1, src1w); 1101 fprintf(compiler->verbose, ", "); 1102 sljit_verbose_param(compiler, src2, src2w); 1103 fprintf(compiler->verbose, "\n"); 1104 } 1105#endif 1106} 1107 1108static SLJIT_INLINE void check_sljit_get_register_index(sljit_si reg) 1109{ 1110 SLJIT_UNUSED_ARG(reg); 1111 SLJIT_ASSERT(reg > 0 && reg <= SLJIT_NUMBER_OF_REGISTERS); 1112} 1113 1114static SLJIT_INLINE void check_sljit_get_float_register_index(sljit_si reg) 1115{ 1116 SLJIT_UNUSED_ARG(reg); 1117 SLJIT_ASSERT(reg > 0 && reg <= SLJIT_NUMBER_OF_FLOAT_REGISTERS); 1118} 1119 1120static SLJIT_INLINE void check_sljit_emit_op_custom(struct sljit_compiler *compiler, 1121 void *instruction, sljit_si size) 1122{ 1123 SLJIT_UNUSED_ARG(compiler); 1124 SLJIT_UNUSED_ARG(instruction); 1125 SLJIT_UNUSED_ARG(size); 1126 SLJIT_ASSERT(instruction); 1127} 1128 1129#define SELECT_FOP1_OPERATION_WITH_CHECKS(compiler, op, dst, dstw, src, srcw) \ 1130 SLJIT_ASSERT(sljit_is_fpu_available()); \ 1131 SLJIT_COMPILE_ASSERT(!(SLJIT_CONVW_FROMD & 0x1) && !(SLJIT_CONVD_FROMW & 0x1), \ 1132 invalid_float_opcodes); \ 1133 if (GET_OPCODE(op) >= SLJIT_CONVW_FROMD && GET_OPCODE(op) <= SLJIT_CMPD) { \ 1134 if (GET_OPCODE(op) == SLJIT_CMPD) { \ 1135 check_sljit_emit_fop1_cmp(compiler, op, dst, dstw, src, srcw); \ 1136 ADJUST_LOCAL_OFFSET(dst, dstw); \ 1137 ADJUST_LOCAL_OFFSET(src, srcw); \ 1138 return sljit_emit_fop1_cmp(compiler, op, dst, dstw, src, srcw); \ 1139 } \ 1140 if ((GET_OPCODE(op) | 0x1) == SLJIT_CONVI_FROMD) { \ 1141 check_sljit_emit_fop1_convw_fromd(compiler, op, dst, dstw, src, srcw); \ 1142 ADJUST_LOCAL_OFFSET(dst, dstw); \ 1143 ADJUST_LOCAL_OFFSET(src, srcw); \ 1144 return sljit_emit_fop1_convw_fromd(compiler, op, dst, dstw, src, srcw); \ 1145 } \ 1146 check_sljit_emit_fop1_convd_fromw(compiler, op, dst, dstw, src, srcw); \ 1147 ADJUST_LOCAL_OFFSET(dst, dstw); \ 1148 ADJUST_LOCAL_OFFSET(src, srcw); \ 1149 return sljit_emit_fop1_convd_fromw(compiler, op, dst, dstw, src, srcw); \ 1150 } \ 1151 check_sljit_emit_fop1(compiler, op, dst, dstw, src, srcw); \ 1152 ADJUST_LOCAL_OFFSET(dst, dstw); \ 1153 ADJUST_LOCAL_OFFSET(src, srcw); 1154 1155static SLJIT_INLINE void check_sljit_emit_fop1(struct sljit_compiler *compiler, sljit_si op, 1156 sljit_si dst, sljit_sw dstw, 1157 sljit_si src, sljit_sw srcw) 1158{ 1159 /* If debug and verbose are disabled, all arguments are unused. */ 1160 SLJIT_UNUSED_ARG(compiler); 1161 SLJIT_UNUSED_ARG(op); 1162 SLJIT_UNUSED_ARG(dst); 1163 SLJIT_UNUSED_ARG(dstw); 1164 SLJIT_UNUSED_ARG(src); 1165 SLJIT_UNUSED_ARG(srcw); 1166 1167#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1168 if (SLJIT_UNLIKELY(compiler->skip_checks)) { 1169 compiler->skip_checks = 0; 1170 return; 1171 } 1172#endif 1173 1174 SLJIT_ASSERT(GET_OPCODE(op) >= SLJIT_MOVD && GET_OPCODE(op) <= SLJIT_ABSD); 1175#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 1176 FUNCTION_CHECK_FOP(); 1177 FUNCTION_FCHECK(src, srcw); 1178 FUNCTION_FCHECK(dst, dstw); 1179#endif 1180#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1181 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1182 fprintf(compiler->verbose, " %s%s ", fop1_names[GET_OPCODE(op) - SLJIT_FOP1_BASE], 1183 (GET_OPCODE(op) == SLJIT_CONVD_FROMS) 1184 ? ((op & SLJIT_SINGLE_OP) ? "s.fromd" : "d.froms") 1185 : ((op & SLJIT_SINGLE_OP) ? "s" : "d")); 1186 sljit_verbose_fparam(compiler, dst, dstw); 1187 fprintf(compiler->verbose, ", "); 1188 sljit_verbose_fparam(compiler, src, srcw); 1189 fprintf(compiler->verbose, "\n"); 1190 } 1191#endif 1192} 1193 1194static SLJIT_INLINE void check_sljit_emit_fop1_cmp(struct sljit_compiler *compiler, sljit_si op, 1195 sljit_si src1, sljit_sw src1w, 1196 sljit_si src2, sljit_sw src2w) 1197{ 1198 /* If debug and verbose are disabled, all arguments are unused. */ 1199 SLJIT_UNUSED_ARG(compiler); 1200 SLJIT_UNUSED_ARG(op); 1201 SLJIT_UNUSED_ARG(src1); 1202 SLJIT_UNUSED_ARG(src1w); 1203 SLJIT_UNUSED_ARG(src2); 1204 SLJIT_UNUSED_ARG(src2w); 1205 1206#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1207 if (SLJIT_UNLIKELY(compiler->skip_checks)) { 1208 compiler->skip_checks = 0; 1209 return; 1210 } 1211#endif 1212 1213 SLJIT_ASSERT(GET_OPCODE(op) == SLJIT_CMPD); 1214#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 1215 FUNCTION_CHECK_FOP(); 1216 FUNCTION_FCHECK(src1, src1w); 1217 FUNCTION_FCHECK(src2, src2w); 1218#endif 1219#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1220 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1221 fprintf(compiler->verbose, " %s%s%s%s ", fop1_names[GET_OPCODE(op) - SLJIT_FOP1_BASE], (op & SLJIT_SINGLE_OP) ? "s" : "d", 1222 !(op & SLJIT_SET_E) ? "" : ".e", !(op & SLJIT_SET_S) ? "" : ".s"); 1223 sljit_verbose_fparam(compiler, src1, src1w); 1224 fprintf(compiler->verbose, ", "); 1225 sljit_verbose_fparam(compiler, src2, src2w); 1226 fprintf(compiler->verbose, "\n"); 1227 } 1228#endif 1229} 1230 1231static SLJIT_INLINE void check_sljit_emit_fop1_convw_fromd(struct sljit_compiler *compiler, sljit_si op, 1232 sljit_si dst, sljit_sw dstw, 1233 sljit_si src, sljit_sw srcw) 1234{ 1235 /* If debug and verbose are disabled, all arguments are unused. */ 1236 SLJIT_UNUSED_ARG(compiler); 1237 SLJIT_UNUSED_ARG(op); 1238 SLJIT_UNUSED_ARG(dst); 1239 SLJIT_UNUSED_ARG(dstw); 1240 SLJIT_UNUSED_ARG(src); 1241 SLJIT_UNUSED_ARG(srcw); 1242 1243#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1244 if (SLJIT_UNLIKELY(compiler->skip_checks)) { 1245 compiler->skip_checks = 0; 1246 return; 1247 } 1248#endif 1249 1250 SLJIT_ASSERT(GET_OPCODE(op) >= SLJIT_CONVW_FROMD && GET_OPCODE(op) <= SLJIT_CONVI_FROMD); 1251#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 1252 FUNCTION_CHECK_FOP(); 1253 FUNCTION_FCHECK(src, srcw); 1254 FUNCTION_CHECK_DST(dst, dstw); 1255#endif 1256#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1257 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1258 fprintf(compiler->verbose, " %s%s.from%s ", fop1_names[GET_OPCODE(op) - SLJIT_FOP1_BASE], 1259 (GET_OPCODE(op) == SLJIT_CONVI_FROMD) ? "i" : "w", 1260 (op & SLJIT_SINGLE_OP) ? "s" : "d"); 1261 sljit_verbose_param(compiler, dst, dstw); 1262 fprintf(compiler->verbose, ", "); 1263 sljit_verbose_fparam(compiler, src, srcw); 1264 fprintf(compiler->verbose, "\n"); 1265 } 1266#endif 1267} 1268 1269static SLJIT_INLINE void check_sljit_emit_fop1_convd_fromw(struct sljit_compiler *compiler, sljit_si op, 1270 sljit_si dst, sljit_sw dstw, 1271 sljit_si src, sljit_sw srcw) 1272{ 1273 /* If debug and verbose are disabled, all arguments are unused. */ 1274 SLJIT_UNUSED_ARG(compiler); 1275 SLJIT_UNUSED_ARG(op); 1276 SLJIT_UNUSED_ARG(dst); 1277 SLJIT_UNUSED_ARG(dstw); 1278 SLJIT_UNUSED_ARG(src); 1279 SLJIT_UNUSED_ARG(srcw); 1280 1281#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1282 if (SLJIT_UNLIKELY(compiler->skip_checks)) { 1283 compiler->skip_checks = 0; 1284 return; 1285 } 1286#endif 1287 1288 SLJIT_ASSERT(GET_OPCODE(op) >= SLJIT_CONVD_FROMW && GET_OPCODE(op) <= SLJIT_CONVD_FROMI); 1289#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 1290 FUNCTION_CHECK_FOP(); 1291 FUNCTION_CHECK_SRC(src, srcw); 1292 FUNCTION_FCHECK(dst, dstw); 1293#endif 1294#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1295 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1296 fprintf(compiler->verbose, " %s%s.from%s ", fop1_names[GET_OPCODE(op) - SLJIT_FOP1_BASE], 1297 (op & SLJIT_SINGLE_OP) ? "s" : "d", 1298 (GET_OPCODE(op) == SLJIT_CONVD_FROMI) ? "i" : "w"); 1299 sljit_verbose_fparam(compiler, dst, dstw); 1300 fprintf(compiler->verbose, ", "); 1301 sljit_verbose_param(compiler, src, srcw); 1302 fprintf(compiler->verbose, "\n"); 1303 } 1304#endif 1305} 1306 1307static SLJIT_INLINE void check_sljit_emit_fop2(struct sljit_compiler *compiler, sljit_si op, 1308 sljit_si dst, sljit_sw dstw, 1309 sljit_si src1, sljit_sw src1w, 1310 sljit_si src2, sljit_sw src2w) 1311{ 1312 /* If debug and verbose are disabled, all arguments are unused. */ 1313 SLJIT_UNUSED_ARG(compiler); 1314 SLJIT_UNUSED_ARG(op); 1315 SLJIT_UNUSED_ARG(dst); 1316 SLJIT_UNUSED_ARG(dstw); 1317 SLJIT_UNUSED_ARG(src1); 1318 SLJIT_UNUSED_ARG(src1w); 1319 SLJIT_UNUSED_ARG(src2); 1320 SLJIT_UNUSED_ARG(src2w); 1321 1322 SLJIT_ASSERT(sljit_is_fpu_available()); 1323 SLJIT_ASSERT(GET_OPCODE(op) >= SLJIT_ADDD && GET_OPCODE(op) <= SLJIT_DIVD); 1324#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 1325 FUNCTION_CHECK_FOP(); 1326 FUNCTION_FCHECK(src1, src1w); 1327 FUNCTION_FCHECK(src2, src2w); 1328 FUNCTION_FCHECK(dst, dstw); 1329#endif 1330#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1331 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1332 fprintf(compiler->verbose, " %s%s ", fop2_names[GET_OPCODE(op) - SLJIT_FOP2_BASE], (op & SLJIT_SINGLE_OP) ? "s" : "d"); 1333 sljit_verbose_fparam(compiler, dst, dstw); 1334 fprintf(compiler->verbose, ", "); 1335 sljit_verbose_fparam(compiler, src1, src1w); 1336 fprintf(compiler->verbose, ", "); 1337 sljit_verbose_fparam(compiler, src2, src2w); 1338 fprintf(compiler->verbose, "\n"); 1339 } 1340#endif 1341} 1342 1343static SLJIT_INLINE void check_sljit_emit_label(struct sljit_compiler *compiler) 1344{ 1345 /* If debug and verbose are disabled, all arguments are unused. */ 1346 SLJIT_UNUSED_ARG(compiler); 1347 1348#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1349 if (SLJIT_UNLIKELY(!!compiler->verbose)) 1350 fprintf(compiler->verbose, "label:\n"); 1351#endif 1352} 1353 1354static SLJIT_INLINE void check_sljit_emit_jump(struct sljit_compiler *compiler, sljit_si type) 1355{ 1356 /* If debug and verbose are disabled, all arguments are unused. */ 1357 SLJIT_UNUSED_ARG(compiler); 1358 SLJIT_UNUSED_ARG(type); 1359 1360#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1361 if (SLJIT_UNLIKELY(compiler->skip_checks)) { 1362 compiler->skip_checks = 0; 1363 return; 1364 } 1365#endif 1366 1367 SLJIT_ASSERT(!(type & ~(0xff | SLJIT_REWRITABLE_JUMP))); 1368 SLJIT_ASSERT((type & 0xff) >= SLJIT_C_EQUAL && (type & 0xff) <= SLJIT_CALL3); 1369#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1370 if (SLJIT_UNLIKELY(!!compiler->verbose)) 1371 fprintf(compiler->verbose, " jump%s.%s\n", !(type & SLJIT_REWRITABLE_JUMP) ? "" : ".r", jump_names[type & 0xff]); 1372#endif 1373} 1374 1375static SLJIT_INLINE void check_sljit_emit_cmp(struct sljit_compiler *compiler, sljit_si type, 1376 sljit_si src1, sljit_sw src1w, 1377 sljit_si src2, sljit_sw src2w) 1378{ 1379 SLJIT_UNUSED_ARG(compiler); 1380 SLJIT_UNUSED_ARG(type); 1381 SLJIT_UNUSED_ARG(src1); 1382 SLJIT_UNUSED_ARG(src1w); 1383 SLJIT_UNUSED_ARG(src2); 1384 SLJIT_UNUSED_ARG(src2w); 1385 1386 SLJIT_ASSERT(!(type & ~(0xff | SLJIT_REWRITABLE_JUMP | SLJIT_INT_OP))); 1387 SLJIT_ASSERT((type & 0xff) >= SLJIT_C_EQUAL && (type & 0xff) <= SLJIT_C_SIG_LESS_EQUAL); 1388#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 1389 FUNCTION_CHECK_SRC(src1, src1w); 1390 FUNCTION_CHECK_SRC(src2, src2w); 1391#endif 1392#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1393 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1394 fprintf(compiler->verbose, " %scmp%s.%s ", !(type & SLJIT_INT_OP) ? "" : "i", !(type & SLJIT_REWRITABLE_JUMP) ? "" : ".r", jump_names[type & 0xff]); 1395 sljit_verbose_param(compiler, src1, src1w); 1396 fprintf(compiler->verbose, ", "); 1397 sljit_verbose_param(compiler, src2, src2w); 1398 fprintf(compiler->verbose, "\n"); 1399 } 1400#endif 1401} 1402 1403static SLJIT_INLINE void check_sljit_emit_fcmp(struct sljit_compiler *compiler, sljit_si type, 1404 sljit_si src1, sljit_sw src1w, 1405 sljit_si src2, sljit_sw src2w) 1406{ 1407 SLJIT_UNUSED_ARG(compiler); 1408 SLJIT_UNUSED_ARG(type); 1409 SLJIT_UNUSED_ARG(src1); 1410 SLJIT_UNUSED_ARG(src1w); 1411 SLJIT_UNUSED_ARG(src2); 1412 SLJIT_UNUSED_ARG(src2w); 1413 1414 SLJIT_ASSERT(sljit_is_fpu_available()); 1415 SLJIT_ASSERT(!(type & ~(0xff | SLJIT_REWRITABLE_JUMP | SLJIT_SINGLE_OP))); 1416 SLJIT_ASSERT((type & 0xff) >= SLJIT_C_FLOAT_EQUAL && (type & 0xff) <= SLJIT_C_FLOAT_ORDERED); 1417#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 1418 FUNCTION_FCHECK(src1, src1w); 1419 FUNCTION_FCHECK(src2, src2w); 1420#endif 1421#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1422 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1423 fprintf(compiler->verbose, " %scmp%s.%s ", (type & SLJIT_SINGLE_OP) ? "s" : "d", 1424 !(type & SLJIT_REWRITABLE_JUMP) ? "" : ".r", jump_names[type & 0xff]); 1425 sljit_verbose_fparam(compiler, src1, src1w); 1426 fprintf(compiler->verbose, ", "); 1427 sljit_verbose_fparam(compiler, src2, src2w); 1428 fprintf(compiler->verbose, "\n"); 1429 } 1430#endif 1431} 1432 1433static SLJIT_INLINE void check_sljit_emit_ijump(struct sljit_compiler *compiler, sljit_si type, sljit_si src, sljit_sw srcw) 1434{ 1435 /* If debug and verbose are disabled, all arguments are unused. */ 1436 SLJIT_UNUSED_ARG(compiler); 1437 SLJIT_UNUSED_ARG(type); 1438 SLJIT_UNUSED_ARG(src); 1439 SLJIT_UNUSED_ARG(srcw); 1440 1441#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1442 if (SLJIT_UNLIKELY(compiler->skip_checks)) { 1443 compiler->skip_checks = 0; 1444 return; 1445 } 1446#endif 1447 1448 SLJIT_ASSERT(type >= SLJIT_JUMP && type <= SLJIT_CALL3); 1449#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 1450 FUNCTION_CHECK_SRC(src, srcw); 1451#endif 1452#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1453 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1454 fprintf(compiler->verbose, " ijump.%s ", jump_names[type]); 1455 sljit_verbose_param(compiler, src, srcw); 1456 fprintf(compiler->verbose, "\n"); 1457 } 1458#endif 1459} 1460 1461static SLJIT_INLINE void check_sljit_emit_op_flags(struct sljit_compiler *compiler, sljit_si op, 1462 sljit_si dst, sljit_sw dstw, 1463 sljit_si src, sljit_sw srcw, 1464 sljit_si type) 1465{ 1466 /* If debug and verbose are disabled, all arguments are unused. */ 1467 SLJIT_UNUSED_ARG(compiler); 1468 SLJIT_UNUSED_ARG(op); 1469 SLJIT_UNUSED_ARG(dst); 1470 SLJIT_UNUSED_ARG(dstw); 1471 SLJIT_UNUSED_ARG(src); 1472 SLJIT_UNUSED_ARG(srcw); 1473 SLJIT_UNUSED_ARG(type); 1474 1475 SLJIT_ASSERT(type >= SLJIT_C_EQUAL && type < SLJIT_JUMP); 1476 SLJIT_ASSERT(op == SLJIT_MOV || GET_OPCODE(op) == SLJIT_MOV_UI || GET_OPCODE(op) == SLJIT_MOV_SI 1477 || (GET_OPCODE(op) >= SLJIT_AND && GET_OPCODE(op) <= SLJIT_XOR)); 1478 SLJIT_ASSERT((op & (SLJIT_SET_U | SLJIT_SET_S | SLJIT_SET_O | SLJIT_SET_C)) == 0); 1479 SLJIT_ASSERT((op & (SLJIT_SET_E | SLJIT_KEEP_FLAGS)) != (SLJIT_SET_E | SLJIT_KEEP_FLAGS)); 1480#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 1481 if (GET_OPCODE(op) < SLJIT_ADD) { 1482 SLJIT_ASSERT(src == SLJIT_UNUSED && srcw == 0); 1483 } else { 1484 SLJIT_ASSERT(src == dst && srcw == dstw); 1485 } 1486 FUNCTION_CHECK_DST(dst, dstw); 1487#endif 1488#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1489 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1490 fprintf(compiler->verbose, " %sflags.%s%s%s ", !(op & SLJIT_INT_OP) ? "" : "i", 1491 GET_OPCODE(op) >= SLJIT_OP2_BASE ? op2_names[GET_OPCODE(op) - SLJIT_OP2_BASE] : op1_names[GET_OPCODE(op) - SLJIT_OP1_BASE], 1492 !(op & SLJIT_SET_E) ? "" : ".e", !(op & SLJIT_KEEP_FLAGS) ? "" : ".k"); 1493 sljit_verbose_param(compiler, dst, dstw); 1494 if (src != SLJIT_UNUSED) { 1495 fprintf(compiler->verbose, ", "); 1496 sljit_verbose_param(compiler, src, srcw); 1497 } 1498 fprintf(compiler->verbose, ", %s\n", jump_names[type]); 1499 } 1500#endif 1501} 1502 1503static SLJIT_INLINE void check_sljit_get_local_base(struct sljit_compiler *compiler, sljit_si dst, sljit_sw dstw, sljit_sw offset) 1504{ 1505 SLJIT_UNUSED_ARG(compiler); 1506 SLJIT_UNUSED_ARG(dst); 1507 SLJIT_UNUSED_ARG(dstw); 1508 SLJIT_UNUSED_ARG(offset); 1509 1510#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 1511 FUNCTION_CHECK_DST(dst, dstw); 1512#endif 1513#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1514 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1515 fprintf(compiler->verbose, " local_base "); 1516 sljit_verbose_param(compiler, dst, dstw); 1517 fprintf(compiler->verbose, ", #%" SLJIT_PRINT_D "d\n", offset); 1518 } 1519#endif 1520} 1521 1522static SLJIT_INLINE void check_sljit_emit_const(struct sljit_compiler *compiler, sljit_si dst, sljit_sw dstw, sljit_sw init_value) 1523{ 1524 /* If debug and verbose are disabled, all arguments are unused. */ 1525 SLJIT_UNUSED_ARG(compiler); 1526 SLJIT_UNUSED_ARG(dst); 1527 SLJIT_UNUSED_ARG(dstw); 1528 SLJIT_UNUSED_ARG(init_value); 1529 1530#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 1531 FUNCTION_CHECK_DST(dst, dstw); 1532#endif 1533#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1534 if (SLJIT_UNLIKELY(!!compiler->verbose)) { 1535 fprintf(compiler->verbose, " const "); 1536 sljit_verbose_param(compiler, dst, dstw); 1537 fprintf(compiler->verbose, ", #%" SLJIT_PRINT_D "d\n", init_value); 1538 } 1539#endif 1540} 1541 1542static SLJIT_INLINE sljit_si emit_mov_before_return(struct sljit_compiler *compiler, sljit_si op, sljit_si src, sljit_sw srcw) 1543{ 1544 /* Return if don't need to do anything. */ 1545 if (op == SLJIT_UNUSED) 1546 return SLJIT_SUCCESS; 1547 1548#if (defined SLJIT_64BIT_ARCHITECTURE && SLJIT_64BIT_ARCHITECTURE) 1549 /* At the moment the pointer size is always equal to sljit_sw. May be changed in the future. */ 1550 if (src == SLJIT_RETURN_REG && (op == SLJIT_MOV || op == SLJIT_MOV_P)) 1551 return SLJIT_SUCCESS; 1552#else 1553 if (src == SLJIT_RETURN_REG && (op == SLJIT_MOV || op == SLJIT_MOV_UI || op == SLJIT_MOV_SI || op == SLJIT_MOV_P)) 1554 return SLJIT_SUCCESS; 1555#endif 1556 1557#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1558 compiler->skip_checks = 1; 1559#endif 1560 return sljit_emit_op1(compiler, op, SLJIT_RETURN_REG, 0, src, srcw); 1561} 1562 1563/* CPU description section */ 1564 1565#if (defined SLJIT_32BIT_ARCHITECTURE && SLJIT_32BIT_ARCHITECTURE) 1566#define SLJIT_CPUINFO_PART1 " 32bit (" 1567#elif (defined SLJIT_64BIT_ARCHITECTURE && SLJIT_64BIT_ARCHITECTURE) 1568#define SLJIT_CPUINFO_PART1 " 64bit (" 1569#else 1570#error "Internal error: CPU type info missing" 1571#endif 1572 1573#if (defined SLJIT_LITTLE_ENDIAN && SLJIT_LITTLE_ENDIAN) 1574#define SLJIT_CPUINFO_PART2 "little endian + " 1575#elif (defined SLJIT_BIG_ENDIAN && SLJIT_BIG_ENDIAN) 1576#define SLJIT_CPUINFO_PART2 "big endian + " 1577#else 1578#error "Internal error: CPU type info missing" 1579#endif 1580 1581#if (defined SLJIT_UNALIGNED && SLJIT_UNALIGNED) 1582#define SLJIT_CPUINFO_PART3 "unaligned)" 1583#else 1584#define SLJIT_CPUINFO_PART3 "aligned)" 1585#endif 1586 1587#define SLJIT_CPUINFO SLJIT_CPUINFO_PART1 SLJIT_CPUINFO_PART2 SLJIT_CPUINFO_PART3 1588 1589#if (defined SLJIT_CONFIG_X86 && SLJIT_CONFIG_X86) 1590# include "sljitNativeX86_common.c" 1591#elif (defined SLJIT_CONFIG_ARM_V5 && SLJIT_CONFIG_ARM_V5) 1592# include "sljitNativeARM_32.c" 1593#elif (defined SLJIT_CONFIG_ARM_V7 && SLJIT_CONFIG_ARM_V7) 1594# include "sljitNativeARM_32.c" 1595#elif (defined SLJIT_CONFIG_ARM_THUMB2 && SLJIT_CONFIG_ARM_THUMB2) 1596# include "sljitNativeARM_T2_32.c" 1597#elif (defined SLJIT_CONFIG_ARM_64 && SLJIT_CONFIG_ARM_64) 1598# include "sljitNativeARM_64.c" 1599#elif (defined SLJIT_CONFIG_PPC && SLJIT_CONFIG_PPC) 1600# include "sljitNativePPC_common.c" 1601#elif (defined SLJIT_CONFIG_MIPS && SLJIT_CONFIG_MIPS) 1602# include "sljitNativeMIPS_common.c" 1603#elif (defined SLJIT_CONFIG_SPARC && SLJIT_CONFIG_SPARC) 1604# include "sljitNativeSPARC_common.c" 1605#elif (defined SLJIT_CONFIG_TILEGX && SLJIT_CONFIG_TILEGX) 1606# include "sljitNativeTILEGX_64.c" 1607#endif 1608 1609#if !(defined SLJIT_CONFIG_MIPS && SLJIT_CONFIG_MIPS) 1610 1611SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_cmp(struct sljit_compiler *compiler, sljit_si type, 1612 sljit_si src1, sljit_sw src1w, 1613 sljit_si src2, sljit_sw src2w) 1614{ 1615 /* Default compare for most architectures. */ 1616 sljit_si flags, tmp_src, condition; 1617 sljit_sw tmp_srcw; 1618 1619 CHECK_ERROR_PTR(); 1620 check_sljit_emit_cmp(compiler, type, src1, src1w, src2, src2w); 1621 1622 condition = type & 0xff; 1623#if (defined SLJIT_CONFIG_ARM_64 && SLJIT_CONFIG_ARM_64) 1624 if ((condition == SLJIT_C_EQUAL || condition == SLJIT_C_NOT_EQUAL)) { 1625 if ((src1 & SLJIT_IMM) && !src1w) { 1626 src1 = src2; 1627 src1w = src2w; 1628 src2 = SLJIT_IMM; 1629 src2w = 0; 1630 } 1631 if ((src2 & SLJIT_IMM) && !src2w) 1632 return emit_cmp_to0(compiler, type, src1, src1w); 1633 } 1634#endif 1635 1636 if (SLJIT_UNLIKELY((src1 & SLJIT_IMM) && !(src2 & SLJIT_IMM))) { 1637 /* Immediate is prefered as second argument by most architectures. */ 1638 switch (condition) { 1639 case SLJIT_C_LESS: 1640 condition = SLJIT_C_GREATER; 1641 break; 1642 case SLJIT_C_GREATER_EQUAL: 1643 condition = SLJIT_C_LESS_EQUAL; 1644 break; 1645 case SLJIT_C_GREATER: 1646 condition = SLJIT_C_LESS; 1647 break; 1648 case SLJIT_C_LESS_EQUAL: 1649 condition = SLJIT_C_GREATER_EQUAL; 1650 break; 1651 case SLJIT_C_SIG_LESS: 1652 condition = SLJIT_C_SIG_GREATER; 1653 break; 1654 case SLJIT_C_SIG_GREATER_EQUAL: 1655 condition = SLJIT_C_SIG_LESS_EQUAL; 1656 break; 1657 case SLJIT_C_SIG_GREATER: 1658 condition = SLJIT_C_SIG_LESS; 1659 break; 1660 case SLJIT_C_SIG_LESS_EQUAL: 1661 condition = SLJIT_C_SIG_GREATER_EQUAL; 1662 break; 1663 } 1664 type = condition | (type & (SLJIT_INT_OP | SLJIT_REWRITABLE_JUMP)); 1665 tmp_src = src1; 1666 src1 = src2; 1667 src2 = tmp_src; 1668 tmp_srcw = src1w; 1669 src1w = src2w; 1670 src2w = tmp_srcw; 1671 } 1672 1673 if (condition <= SLJIT_C_NOT_ZERO) 1674 flags = SLJIT_SET_E; 1675 else if (condition <= SLJIT_C_LESS_EQUAL) 1676 flags = SLJIT_SET_U; 1677 else 1678 flags = SLJIT_SET_S; 1679 1680#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1681 compiler->skip_checks = 1; 1682#endif 1683 PTR_FAIL_IF(sljit_emit_op2(compiler, SLJIT_SUB | flags | (type & SLJIT_INT_OP), 1684 SLJIT_UNUSED, 0, src1, src1w, src2, src2w)); 1685#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1686 compiler->skip_checks = 1; 1687#endif 1688 return sljit_emit_jump(compiler, condition | (type & SLJIT_REWRITABLE_JUMP)); 1689} 1690 1691SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_fcmp(struct sljit_compiler *compiler, sljit_si type, 1692 sljit_si src1, sljit_sw src1w, 1693 sljit_si src2, sljit_sw src2w) 1694{ 1695 sljit_si flags, condition; 1696 1697 check_sljit_emit_fcmp(compiler, type, src1, src1w, src2, src2w); 1698 1699 condition = type & 0xff; 1700 flags = (condition <= SLJIT_C_FLOAT_NOT_EQUAL) ? SLJIT_SET_E : SLJIT_SET_S; 1701 if (type & SLJIT_SINGLE_OP) 1702 flags |= SLJIT_SINGLE_OP; 1703 1704#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1705 compiler->skip_checks = 1; 1706#endif 1707 sljit_emit_fop1(compiler, SLJIT_CMPD | flags, src1, src1w, src2, src2w); 1708 1709#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1710 compiler->skip_checks = 1; 1711#endif 1712 return sljit_emit_jump(compiler, condition | (type & SLJIT_REWRITABLE_JUMP)); 1713} 1714 1715#endif 1716 1717#if !(defined SLJIT_CONFIG_X86 && SLJIT_CONFIG_X86) 1718 1719SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_get_local_base(struct sljit_compiler *compiler, sljit_si dst, sljit_sw dstw, sljit_sw offset) 1720{ 1721 CHECK_ERROR(); 1722 check_sljit_get_local_base(compiler, dst, dstw, offset); 1723 1724 ADJUST_LOCAL_OFFSET(SLJIT_MEM1(SLJIT_SP), offset); 1725#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG) 1726 compiler->skip_checks = 1; 1727#endif 1728 if (offset != 0) 1729 return sljit_emit_op2(compiler, SLJIT_ADD | SLJIT_KEEP_FLAGS, dst, dstw, SLJIT_SP, 0, SLJIT_IMM, offset); 1730 return sljit_emit_op1(compiler, SLJIT_MOV, dst, dstw, SLJIT_SP, 0); 1731} 1732 1733#endif 1734 1735#else /* SLJIT_CONFIG_UNSUPPORTED */ 1736 1737/* Empty function bodies for those machines, which are not (yet) supported. */ 1738 1739SLJIT_API_FUNC_ATTRIBUTE SLJIT_CONST char* sljit_get_platform_name(void) 1740{ 1741 return "unsupported"; 1742} 1743 1744SLJIT_API_FUNC_ATTRIBUTE struct sljit_compiler* sljit_create_compiler(void) 1745{ 1746 SLJIT_ASSERT_STOP(); 1747 return NULL; 1748} 1749 1750SLJIT_API_FUNC_ATTRIBUTE void sljit_free_compiler(struct sljit_compiler *compiler) 1751{ 1752 SLJIT_UNUSED_ARG(compiler); 1753 SLJIT_ASSERT_STOP(); 1754} 1755 1756SLJIT_API_FUNC_ATTRIBUTE void* sljit_alloc_memory(struct sljit_compiler *compiler, sljit_si size) 1757{ 1758 SLJIT_UNUSED_ARG(compiler); 1759 SLJIT_UNUSED_ARG(size); 1760 SLJIT_ASSERT_STOP(); 1761 return NULL; 1762} 1763 1764#if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) 1765SLJIT_API_FUNC_ATTRIBUTE void sljit_compiler_verbose(struct sljit_compiler *compiler, FILE* verbose) 1766{ 1767 SLJIT_UNUSED_ARG(compiler); 1768 SLJIT_UNUSED_ARG(verbose); 1769 SLJIT_ASSERT_STOP(); 1770} 1771#endif 1772 1773SLJIT_API_FUNC_ATTRIBUTE void* sljit_generate_code(struct sljit_compiler *compiler) 1774{ 1775 SLJIT_UNUSED_ARG(compiler); 1776 SLJIT_ASSERT_STOP(); 1777 return NULL; 1778} 1779 1780SLJIT_API_FUNC_ATTRIBUTE void sljit_free_code(void* code) 1781{ 1782 SLJIT_UNUSED_ARG(code); 1783 SLJIT_ASSERT_STOP(); 1784} 1785 1786SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_enter(struct sljit_compiler *compiler, 1787 sljit_si options, sljit_si args, sljit_si scratches, sljit_si saveds, 1788 sljit_si fscratches, sljit_si fsaveds, sljit_si local_size) 1789{ 1790 SLJIT_UNUSED_ARG(compiler); 1791 SLJIT_UNUSED_ARG(options); 1792 SLJIT_UNUSED_ARG(args); 1793 SLJIT_UNUSED_ARG(scratches); 1794 SLJIT_UNUSED_ARG(saveds); 1795 SLJIT_UNUSED_ARG(fscratches); 1796 SLJIT_UNUSED_ARG(fsaveds); 1797 SLJIT_UNUSED_ARG(local_size); 1798 SLJIT_ASSERT_STOP(); 1799 return SLJIT_ERR_UNSUPPORTED; 1800} 1801 1802SLJIT_API_FUNC_ATTRIBUTE void sljit_set_context(struct sljit_compiler *compiler, 1803 sljit_si options, sljit_si args, sljit_si scratches, sljit_si saveds, 1804 sljit_si fscratches, sljit_si fsaveds, sljit_si local_size) 1805{ 1806 SLJIT_UNUSED_ARG(compiler); 1807 SLJIT_UNUSED_ARG(options); 1808 SLJIT_UNUSED_ARG(args); 1809 SLJIT_UNUSED_ARG(scratches); 1810 SLJIT_UNUSED_ARG(saveds); 1811 SLJIT_UNUSED_ARG(fscratches); 1812 SLJIT_UNUSED_ARG(fsaveds); 1813 SLJIT_UNUSED_ARG(local_size); 1814 SLJIT_ASSERT_STOP(); 1815} 1816 1817SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_return(struct sljit_compiler *compiler, sljit_si op, sljit_si src, sljit_sw srcw) 1818{ 1819 SLJIT_UNUSED_ARG(compiler); 1820 SLJIT_UNUSED_ARG(op); 1821 SLJIT_UNUSED_ARG(src); 1822 SLJIT_UNUSED_ARG(srcw); 1823 SLJIT_ASSERT_STOP(); 1824 return SLJIT_ERR_UNSUPPORTED; 1825} 1826 1827SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_fast_enter(struct sljit_compiler *compiler, sljit_si dst, sljit_sw dstw) 1828{ 1829 SLJIT_UNUSED_ARG(compiler); 1830 SLJIT_UNUSED_ARG(dst); 1831 SLJIT_UNUSED_ARG(dstw); 1832 SLJIT_ASSERT_STOP(); 1833 return SLJIT_ERR_UNSUPPORTED; 1834} 1835 1836SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_fast_return(struct sljit_compiler *compiler, sljit_si src, sljit_sw srcw) 1837{ 1838 SLJIT_UNUSED_ARG(compiler); 1839 SLJIT_UNUSED_ARG(src); 1840 SLJIT_UNUSED_ARG(srcw); 1841 SLJIT_ASSERT_STOP(); 1842 return SLJIT_ERR_UNSUPPORTED; 1843} 1844 1845SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_op0(struct sljit_compiler *compiler, sljit_si op) 1846{ 1847 SLJIT_UNUSED_ARG(compiler); 1848 SLJIT_UNUSED_ARG(op); 1849 SLJIT_ASSERT_STOP(); 1850 return SLJIT_ERR_UNSUPPORTED; 1851} 1852 1853SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_op1(struct sljit_compiler *compiler, sljit_si op, 1854 sljit_si dst, sljit_sw dstw, 1855 sljit_si src, sljit_sw srcw) 1856{ 1857 SLJIT_UNUSED_ARG(compiler); 1858 SLJIT_UNUSED_ARG(op); 1859 SLJIT_UNUSED_ARG(dst); 1860 SLJIT_UNUSED_ARG(dstw); 1861 SLJIT_UNUSED_ARG(src); 1862 SLJIT_UNUSED_ARG(srcw); 1863 SLJIT_ASSERT_STOP(); 1864 return SLJIT_ERR_UNSUPPORTED; 1865} 1866 1867SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_op2(struct sljit_compiler *compiler, sljit_si op, 1868 sljit_si dst, sljit_sw dstw, 1869 sljit_si src1, sljit_sw src1w, 1870 sljit_si src2, sljit_sw src2w) 1871{ 1872 SLJIT_UNUSED_ARG(compiler); 1873 SLJIT_UNUSED_ARG(op); 1874 SLJIT_UNUSED_ARG(dst); 1875 SLJIT_UNUSED_ARG(dstw); 1876 SLJIT_UNUSED_ARG(src1); 1877 SLJIT_UNUSED_ARG(src1w); 1878 SLJIT_UNUSED_ARG(src2); 1879 SLJIT_UNUSED_ARG(src2w); 1880 SLJIT_ASSERT_STOP(); 1881 return SLJIT_ERR_UNSUPPORTED; 1882} 1883 1884SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_get_register_index(sljit_si reg) 1885{ 1886 SLJIT_ASSERT_STOP(); 1887 return reg; 1888} 1889 1890SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_op_custom(struct sljit_compiler *compiler, 1891 void *instruction, sljit_si size) 1892{ 1893 SLJIT_UNUSED_ARG(compiler); 1894 SLJIT_UNUSED_ARG(instruction); 1895 SLJIT_UNUSED_ARG(size); 1896 SLJIT_ASSERT_STOP(); 1897 return SLJIT_ERR_UNSUPPORTED; 1898} 1899 1900SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_is_fpu_available(void) 1901{ 1902 SLJIT_ASSERT_STOP(); 1903 return 0; 1904} 1905 1906SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_fop1(struct sljit_compiler *compiler, sljit_si op, 1907 sljit_si dst, sljit_sw dstw, 1908 sljit_si src, sljit_sw srcw) 1909{ 1910 SLJIT_UNUSED_ARG(compiler); 1911 SLJIT_UNUSED_ARG(op); 1912 SLJIT_UNUSED_ARG(dst); 1913 SLJIT_UNUSED_ARG(dstw); 1914 SLJIT_UNUSED_ARG(src); 1915 SLJIT_UNUSED_ARG(srcw); 1916 SLJIT_ASSERT_STOP(); 1917 return SLJIT_ERR_UNSUPPORTED; 1918} 1919 1920SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_fop2(struct sljit_compiler *compiler, sljit_si op, 1921 sljit_si dst, sljit_sw dstw, 1922 sljit_si src1, sljit_sw src1w, 1923 sljit_si src2, sljit_sw src2w) 1924{ 1925 SLJIT_UNUSED_ARG(compiler); 1926 SLJIT_UNUSED_ARG(op); 1927 SLJIT_UNUSED_ARG(dst); 1928 SLJIT_UNUSED_ARG(dstw); 1929 SLJIT_UNUSED_ARG(src1); 1930 SLJIT_UNUSED_ARG(src1w); 1931 SLJIT_UNUSED_ARG(src2); 1932 SLJIT_UNUSED_ARG(src2w); 1933 SLJIT_ASSERT_STOP(); 1934 return SLJIT_ERR_UNSUPPORTED; 1935} 1936 1937SLJIT_API_FUNC_ATTRIBUTE struct sljit_label* sljit_emit_label(struct sljit_compiler *compiler) 1938{ 1939 SLJIT_UNUSED_ARG(compiler); 1940 SLJIT_ASSERT_STOP(); 1941 return NULL; 1942} 1943 1944SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_jump(struct sljit_compiler *compiler, sljit_si type) 1945{ 1946 SLJIT_UNUSED_ARG(compiler); 1947 SLJIT_UNUSED_ARG(type); 1948 SLJIT_ASSERT_STOP(); 1949 return NULL; 1950} 1951 1952SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_cmp(struct sljit_compiler *compiler, sljit_si type, 1953 sljit_si src1, sljit_sw src1w, 1954 sljit_si src2, sljit_sw src2w) 1955{ 1956 SLJIT_UNUSED_ARG(compiler); 1957 SLJIT_UNUSED_ARG(type); 1958 SLJIT_UNUSED_ARG(src1); 1959 SLJIT_UNUSED_ARG(src1w); 1960 SLJIT_UNUSED_ARG(src2); 1961 SLJIT_UNUSED_ARG(src2w); 1962 SLJIT_ASSERT_STOP(); 1963 return NULL; 1964} 1965 1966SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_fcmp(struct sljit_compiler *compiler, sljit_si type, 1967 sljit_si src1, sljit_sw src1w, 1968 sljit_si src2, sljit_sw src2w) 1969{ 1970 SLJIT_UNUSED_ARG(compiler); 1971 SLJIT_UNUSED_ARG(type); 1972 SLJIT_UNUSED_ARG(src1); 1973 SLJIT_UNUSED_ARG(src1w); 1974 SLJIT_UNUSED_ARG(src2); 1975 SLJIT_UNUSED_ARG(src2w); 1976 SLJIT_ASSERT_STOP(); 1977 return NULL; 1978} 1979 1980SLJIT_API_FUNC_ATTRIBUTE void sljit_set_label(struct sljit_jump *jump, struct sljit_label* label) 1981{ 1982 SLJIT_UNUSED_ARG(jump); 1983 SLJIT_UNUSED_ARG(label); 1984 SLJIT_ASSERT_STOP(); 1985} 1986 1987SLJIT_API_FUNC_ATTRIBUTE void sljit_set_target(struct sljit_jump *jump, sljit_uw target) 1988{ 1989 SLJIT_UNUSED_ARG(jump); 1990 SLJIT_UNUSED_ARG(target); 1991 SLJIT_ASSERT_STOP(); 1992} 1993 1994SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_ijump(struct sljit_compiler *compiler, sljit_si type, sljit_si src, sljit_sw srcw) 1995{ 1996 SLJIT_UNUSED_ARG(compiler); 1997 SLJIT_UNUSED_ARG(type); 1998 SLJIT_UNUSED_ARG(src); 1999 SLJIT_UNUSED_ARG(srcw); 2000 SLJIT_ASSERT_STOP(); 2001 return SLJIT_ERR_UNSUPPORTED; 2002} 2003 2004SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_op_flags(struct sljit_compiler *compiler, sljit_si op, 2005 sljit_si dst, sljit_sw dstw, 2006 sljit_si src, sljit_sw srcw, 2007 sljit_si type) 2008{ 2009 SLJIT_UNUSED_ARG(compiler); 2010 SLJIT_UNUSED_ARG(op); 2011 SLJIT_UNUSED_ARG(dst); 2012 SLJIT_UNUSED_ARG(dstw); 2013 SLJIT_UNUSED_ARG(src); 2014 SLJIT_UNUSED_ARG(srcw); 2015 SLJIT_UNUSED_ARG(type); 2016 SLJIT_ASSERT_STOP(); 2017 return SLJIT_ERR_UNSUPPORTED; 2018} 2019 2020SLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_get_local_base(struct sljit_compiler *compiler, sljit_si dst, sljit_sw dstw, sljit_sw offset) 2021{ 2022 SLJIT_UNUSED_ARG(compiler); 2023 SLJIT_UNUSED_ARG(dst); 2024 SLJIT_UNUSED_ARG(dstw); 2025 SLJIT_UNUSED_ARG(offset); 2026 SLJIT_ASSERT_STOP(); 2027 return SLJIT_ERR_UNSUPPORTED; 2028} 2029 2030SLJIT_API_FUNC_ATTRIBUTE struct sljit_const* sljit_emit_const(struct sljit_compiler *compiler, sljit_si dst, sljit_sw dstw, sljit_sw initval) 2031{ 2032 SLJIT_UNUSED_ARG(compiler); 2033 SLJIT_UNUSED_ARG(dst); 2034 SLJIT_UNUSED_ARG(dstw); 2035 SLJIT_UNUSED_ARG(initval); 2036 SLJIT_ASSERT_STOP(); 2037 return NULL; 2038} 2039 2040SLJIT_API_FUNC_ATTRIBUTE void sljit_set_jump_addr(sljit_uw addr, sljit_uw new_addr) 2041{ 2042 SLJIT_UNUSED_ARG(addr); 2043 SLJIT_UNUSED_ARG(new_addr); 2044 SLJIT_ASSERT_STOP(); 2045} 2046 2047SLJIT_API_FUNC_ATTRIBUTE void sljit_set_const(sljit_uw addr, sljit_sw new_constant) 2048{ 2049 SLJIT_UNUSED_ARG(addr); 2050 SLJIT_UNUSED_ARG(new_constant); 2051 SLJIT_ASSERT_STOP(); 2052} 2053 2054#endif 2055