File:  [ELWIX - Embedded LightWeight unIX -] / embedaddon / pcre / sljit / sljitNativeX86_common.c
Revision 1.1.1.2 (vendor branch): download - view: text, annotated - select for diffs - revision graph
Tue Feb 21 23:50:25 2012 UTC (12 years, 4 months ago) by misho
Branches: pcre, MAIN
CVS tags: v8_30, HEAD
pcre

    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: SLJIT_API_FUNC_ATTRIBUTE SLJIT_CONST char* sljit_get_platform_name()
   28: {
   29: 	return "x86" SLJIT_CPUINFO;
   30: }
   31: 
   32: /*
   33:    32b register indexes:
   34:      0 - EAX
   35:      1 - ECX
   36:      2 - EDX
   37:      3 - EBX
   38:      4 - none
   39:      5 - EBP
   40:      6 - ESI
   41:      7 - EDI
   42: */
   43: 
   44: /*
   45:    64b register indexes:
   46:      0 - RAX
   47:      1 - RCX
   48:      2 - RDX
   49:      3 - RBX
   50:      4 - none
   51:      5 - RBP
   52:      6 - RSI
   53:      7 - RDI
   54:      8 - R8   - From now on REX prefix is required
   55:      9 - R9
   56:     10 - R10
   57:     11 - R11
   58:     12 - R12
   59:     13 - R13
   60:     14 - R14
   61:     15 - R15
   62: */
   63: 
   64: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
   65: 
   66: /* Last register + 1. */
   67: #define TMP_REGISTER	(SLJIT_NO_REGISTERS + 1)
   68: 
   69: static SLJIT_CONST sljit_ub reg_map[SLJIT_NO_REGISTERS + 2] = {
   70:   0, 0, 2, 1, 0, 0, 3, 6, 7, 0, 0, 4, 5
   71: };
   72: 
   73: #define CHECK_EXTRA_REGS(p, w, do) \
   74: 	if (p >= SLJIT_TEMPORARY_EREG1 && p <= SLJIT_TEMPORARY_EREG2) { \
   75: 		w = compiler->temporaries_start + (p - SLJIT_TEMPORARY_EREG1) * sizeof(sljit_w); \
   76: 		p = SLJIT_MEM1(SLJIT_LOCALS_REG); \
   77: 		do; \
   78: 	} \
   79: 	else if (p >= SLJIT_SAVED_EREG1 && p <= SLJIT_SAVED_EREG2) { \
   80: 		w = compiler->saveds_start + (p - SLJIT_SAVED_EREG1) * sizeof(sljit_w); \
   81: 		p = SLJIT_MEM1(SLJIT_LOCALS_REG); \
   82: 		do; \
   83: 	}
   84: 
   85: #else /* SLJIT_CONFIG_X86_32 */
   86: 
   87: /* Last register + 1. */
   88: #define TMP_REGISTER	(SLJIT_NO_REGISTERS + 1)
   89: #define TMP_REG2	(SLJIT_NO_REGISTERS + 2)
   90: #define TMP_REG3	(SLJIT_NO_REGISTERS + 3)
   91: 
   92: /* Note: r12 & 0x7 == 0b100, which decoded as SIB byte present
   93:    Note: avoid to use r12 and r13 for memory addessing
   94:    therefore r12 is better for SAVED_EREG than SAVED_REG. */
   95: #ifndef _WIN64
   96: /* 1st passed in rdi, 2nd argument passed in rsi, 3rd in rdx. */
   97: static SLJIT_CONST sljit_ub reg_map[SLJIT_NO_REGISTERS + 4] = {
   98:   0, 0, 6, 1, 8, 11, 3, 15, 14, 13, 12, 4, 2, 7, 9
   99: };
  100: /* low-map. reg_map & 0x7. */
  101: static SLJIT_CONST sljit_ub reg_lmap[SLJIT_NO_REGISTERS + 4] = {
  102:   0, 0, 6, 1, 0, 3,  3, 7,  6,  5,  4,  4, 2, 7, 1
  103: };
  104: #else
  105: /* 1st passed in rcx, 2nd argument passed in rdx, 3rd in r8. */
  106: static SLJIT_CONST sljit_ub reg_map[SLJIT_NO_REGISTERS + 4] = {
  107:   0, 0, 2, 1, 11, 13, 3, 6, 7, 14, 12, 15, 10, 8, 9
  108: };
  109: /* low-map. reg_map & 0x7. */
  110: static SLJIT_CONST sljit_ub reg_lmap[SLJIT_NO_REGISTERS + 4] = {
  111:   0, 0, 2, 1, 3,  5,  3, 6, 7,  6,  4,  7, 2,  0, 1
  112: };
  113: #endif
  114: 
  115: #define REX_W		0x48
  116: #define REX_R		0x44
  117: #define REX_X		0x42
  118: #define REX_B		0x41
  119: #define REX		0x40
  120: 
  121: typedef unsigned int sljit_uhw;
  122: typedef int sljit_hw;
  123: 
  124: #define IS_HALFWORD(x)		((x) <= 0x7fffffffll && (x) >= -0x80000000ll)
  125: #define NOT_HALFWORD(x)		((x) > 0x7fffffffll || (x) < -0x80000000ll)
  126: 
  127: #define CHECK_EXTRA_REGS(p, w, do)
  128: 
  129: #endif /* SLJIT_CONFIG_X86_32 */
  130: 
  131: #if (defined SLJIT_SSE2 && SLJIT_SSE2)
  132: #define TMP_FREG	(SLJIT_FLOAT_REG4 + 1)
  133: #endif
  134: 
  135: /* Size flags for emit_x86_instruction: */
  136: #define EX86_BIN_INS		0x0010
  137: #define EX86_SHIFT_INS		0x0020
  138: #define EX86_REX		0x0040
  139: #define EX86_NO_REXW		0x0080
  140: #define EX86_BYTE_ARG		0x0100
  141: #define EX86_HALF_ARG		0x0200
  142: #define EX86_PREF_66		0x0400
  143: 
  144: #if (defined SLJIT_SSE2 && SLJIT_SSE2)
  145: #define EX86_PREF_F2		0x0800
  146: #define EX86_SSE2		0x1000
  147: #endif
  148: 
  149: #define INC_SIZE(s)			(*buf++ = (s), compiler->size += (s))
  150: #define INC_CSIZE(s)			(*code++ = (s), compiler->size += (s))
  151: 
  152: #define PUSH_REG(r)			(*buf++ = (0x50 + (r)))
  153: #define POP_REG(r)			(*buf++ = (0x58 + (r)))
  154: #define RET()				(*buf++ = (0xc3))
  155: #define RETN(n)				(*buf++ = (0xc2), *buf++ = n, *buf++ = 0)
  156: /* r32, r/m32 */
  157: #define MOV_RM(mod, reg, rm)		(*buf++ = (0x8b), *buf++ = (mod) << 6 | (reg) << 3 | (rm))
  158: 
  159: static sljit_ub get_jump_code(int type)
  160: {
  161: 	switch (type) {
  162: 	case SLJIT_C_EQUAL:
  163: 	case SLJIT_C_FLOAT_EQUAL:
  164: 		return 0x84;
  165: 
  166: 	case SLJIT_C_NOT_EQUAL:
  167: 	case SLJIT_C_FLOAT_NOT_EQUAL:
  168: 		return 0x85;
  169: 
  170: 	case SLJIT_C_LESS:
  171: 	case SLJIT_C_FLOAT_LESS:
  172: 		return 0x82;
  173: 
  174: 	case SLJIT_C_GREATER_EQUAL:
  175: 	case SLJIT_C_FLOAT_GREATER_EQUAL:
  176: 		return 0x83;
  177: 
  178: 	case SLJIT_C_GREATER:
  179: 	case SLJIT_C_FLOAT_GREATER:
  180: 		return 0x87;
  181: 
  182: 	case SLJIT_C_LESS_EQUAL:
  183: 	case SLJIT_C_FLOAT_LESS_EQUAL:
  184: 		return 0x86;
  185: 
  186: 	case SLJIT_C_SIG_LESS:
  187: 		return 0x8c;
  188: 
  189: 	case SLJIT_C_SIG_GREATER_EQUAL:
  190: 		return 0x8d;
  191: 
  192: 	case SLJIT_C_SIG_GREATER:
  193: 		return 0x8f;
  194: 
  195: 	case SLJIT_C_SIG_LESS_EQUAL:
  196: 		return 0x8e;
  197: 
  198: 	case SLJIT_C_OVERFLOW:
  199: 	case SLJIT_C_MUL_OVERFLOW:
  200: 		return 0x80;
  201: 
  202: 	case SLJIT_C_NOT_OVERFLOW:
  203: 	case SLJIT_C_MUL_NOT_OVERFLOW:
  204: 		return 0x81;
  205: 
  206: 	case SLJIT_C_FLOAT_NAN:
  207: 		return 0x8a;
  208: 
  209: 	case SLJIT_C_FLOAT_NOT_NAN:
  210: 		return 0x8b;
  211: 	}
  212: 	return 0;
  213: }
  214: 
  215: static sljit_ub* generate_far_jump_code(struct sljit_jump *jump, sljit_ub *code_ptr, int type);
  216: 
  217: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
  218: static sljit_ub* generate_fixed_jump(sljit_ub *code_ptr, sljit_w addr, int type);
  219: #endif
  220: 
  221: static sljit_ub* generate_near_jump_code(struct sljit_jump *jump, sljit_ub *code_ptr, sljit_ub *code, int type)
  222: {
  223: 	int short_jump;
  224: 	sljit_uw label_addr;
  225: 
  226: 	if (jump->flags & JUMP_LABEL)
  227: 		label_addr = (sljit_uw)(code + jump->u.label->size);
  228: 	else
  229: 		label_addr = jump->u.target;
  230: 	short_jump = (sljit_w)(label_addr - (jump->addr + 2)) >= -128 && (sljit_w)(label_addr - (jump->addr + 2)) <= 127;
  231: 
  232: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
  233: 	if ((sljit_w)(label_addr - (jump->addr + 1)) > 0x7fffffffll || (sljit_w)(label_addr - (jump->addr + 1)) < -0x80000000ll)
  234: 		return generate_far_jump_code(jump, code_ptr, type);
  235: #endif
  236: 
  237: 	if (type == SLJIT_JUMP) {
  238: 		if (short_jump)
  239: 			*code_ptr++ = 0xeb;
  240: 		else
  241: 			*code_ptr++ = 0xe9;
  242: 		jump->addr++;
  243: 	}
  244: 	else if (type >= SLJIT_FAST_CALL) {
  245: 		short_jump = 0;
  246: 		*code_ptr++ = 0xe8;
  247: 		jump->addr++;
  248: 	}
  249: 	else if (short_jump) {
  250: 		*code_ptr++ = get_jump_code(type) - 0x10;
  251: 		jump->addr++;
  252: 	}
  253: 	else {
  254: 		*code_ptr++ = 0x0f;
  255: 		*code_ptr++ = get_jump_code(type);
  256: 		jump->addr += 2;
  257: 	}
  258: 
  259: 	if (short_jump) {
  260: 		jump->flags |= PATCH_MB;
  261: 		code_ptr += sizeof(sljit_b);
  262: 	} else {
  263: 		jump->flags |= PATCH_MW;
  264: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  265: 		code_ptr += sizeof(sljit_w);
  266: #else
  267: 		code_ptr += sizeof(sljit_hw);
  268: #endif
  269: 	}
  270: 
  271: 	return code_ptr;
  272: }
  273: 
  274: SLJIT_API_FUNC_ATTRIBUTE void* sljit_generate_code(struct sljit_compiler *compiler)
  275: {
  276: 	struct sljit_memory_fragment *buf;
  277: 	sljit_ub *code;
  278: 	sljit_ub *code_ptr;
  279: 	sljit_ub *buf_ptr;
  280: 	sljit_ub *buf_end;
  281: 	sljit_ub len;
  282: 
  283: 	struct sljit_label *label;
  284: 	struct sljit_jump *jump;
  285: 	struct sljit_const *const_;
  286: 
  287: 	CHECK_ERROR_PTR();
  288: 	check_sljit_generate_code(compiler);
  289: 	reverse_buf(compiler);
  290: 
  291: 	/* Second code generation pass. */
  292: 	code = (sljit_ub*)SLJIT_MALLOC_EXEC(compiler->size);
  293: 	PTR_FAIL_WITH_EXEC_IF(code);
  294: 	buf = compiler->buf;
  295: 
  296: 	code_ptr = code;
  297: 	label = compiler->labels;
  298: 	jump = compiler->jumps;
  299: 	const_ = compiler->consts;
  300: 	do {
  301: 		buf_ptr = buf->memory;
  302: 		buf_end = buf_ptr + buf->used_size;
  303: 		do {
  304: 			len = *buf_ptr++;
  305: 			if (len > 0) {
  306: 				/* The code is already generated. */
  307: 				SLJIT_MEMMOVE(code_ptr, buf_ptr, len);
  308: 				code_ptr += len;
  309: 				buf_ptr += len;
  310: 			}
  311: 			else {
  312: 				if (*buf_ptr >= 4) {
  313: 					jump->addr = (sljit_uw)code_ptr;
  314: 					if (!(jump->flags & SLJIT_REWRITABLE_JUMP))
  315: 						code_ptr = generate_near_jump_code(jump, code_ptr, code, *buf_ptr - 4);
  316: 					else
  317: 						code_ptr = generate_far_jump_code(jump, code_ptr, *buf_ptr - 4);
  318: 					jump = jump->next;
  319: 				}
  320: 				else if (*buf_ptr == 0) {
  321: 					label->addr = (sljit_uw)code_ptr;
  322: 					label->size = code_ptr - code;
  323: 					label = label->next;
  324: 				}
  325: 				else if (*buf_ptr == 1) {
  326: 					const_->addr = ((sljit_uw)code_ptr) - sizeof(sljit_w);
  327: 					const_ = const_->next;
  328: 				}
  329: 				else {
  330: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  331: 					*code_ptr++ = (*buf_ptr == 2) ? 0xe8 /* call */ : 0xe9 /* jmp */;
  332: 					buf_ptr++;
  333: 					*(sljit_w*)code_ptr = *(sljit_w*)buf_ptr - ((sljit_w)code_ptr + sizeof(sljit_w));
  334: 					code_ptr += sizeof(sljit_w);
  335: 					buf_ptr += sizeof(sljit_w) - 1;
  336: #else
  337: 					code_ptr = generate_fixed_jump(code_ptr, *(sljit_w*)(buf_ptr + 1), *buf_ptr);
  338: 					buf_ptr += sizeof(sljit_w);
  339: #endif
  340: 				}
  341: 				buf_ptr++;
  342: 			}
  343: 		} while (buf_ptr < buf_end);
  344: 		SLJIT_ASSERT(buf_ptr == buf_end);
  345: 		buf = buf->next;
  346: 	} while (buf);
  347: 
  348: 	SLJIT_ASSERT(!label);
  349: 	SLJIT_ASSERT(!jump);
  350: 	SLJIT_ASSERT(!const_);
  351: 
  352: 	jump = compiler->jumps;
  353: 	while (jump) {
  354: 		if (jump->flags & PATCH_MB) {
  355: 			SLJIT_ASSERT((sljit_w)(jump->u.label->addr - (jump->addr + sizeof(sljit_b))) >= -128 && (sljit_w)(jump->u.label->addr - (jump->addr + sizeof(sljit_b))) <= 127);
  356: 			*(sljit_ub*)jump->addr = (sljit_ub)(jump->u.label->addr - (jump->addr + sizeof(sljit_b)));
  357: 		} else if (jump->flags & PATCH_MW) {
  358: 			if (jump->flags & JUMP_LABEL) {
  359: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  360: 				*(sljit_w*)jump->addr = (sljit_w)(jump->u.label->addr - (jump->addr + sizeof(sljit_w)));
  361: #else
  362: 				SLJIT_ASSERT((sljit_w)(jump->u.label->addr - (jump->addr + sizeof(sljit_hw))) >= -0x80000000ll && (sljit_w)(jump->u.label->addr - (jump->addr + sizeof(sljit_hw))) <= 0x7fffffffll);
  363: 				*(sljit_hw*)jump->addr = (sljit_hw)(jump->u.label->addr - (jump->addr + sizeof(sljit_hw)));
  364: #endif
  365: 			}
  366: 			else {
  367: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  368: 				*(sljit_w*)jump->addr = (sljit_w)(jump->u.target - (jump->addr + sizeof(sljit_w)));
  369: #else
  370: 				SLJIT_ASSERT((sljit_w)(jump->u.target - (jump->addr + sizeof(sljit_hw))) >= -0x80000000ll && (sljit_w)(jump->u.target - (jump->addr + sizeof(sljit_hw))) <= 0x7fffffffll);
  371: 				*(sljit_hw*)jump->addr = (sljit_hw)(jump->u.target - (jump->addr + sizeof(sljit_hw)));
  372: #endif
  373: 			}
  374: 		}
  375: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
  376: 		else if (jump->flags & PATCH_MD)
  377: 			*(sljit_w*)jump->addr = jump->u.label->addr;
  378: #endif
  379: 
  380: 		jump = jump->next;
  381: 	}
  382: 
  383: 	/* Maybe we waste some space because of short jumps. */
  384: 	SLJIT_ASSERT(code_ptr <= code + compiler->size);
  385: 	compiler->error = SLJIT_ERR_COMPILED;
  386: 	compiler->executable_size = compiler->size;
  387: 	return (void*)code;
  388: }
  389: 
  390: /* --------------------------------------------------------------------- */
  391: /*  Operators                                                            */
  392: /* --------------------------------------------------------------------- */
  393: 
  394: static int emit_cum_binary(struct sljit_compiler *compiler,
  395: 	sljit_ub op_rm, sljit_ub op_mr, sljit_ub op_imm, sljit_ub op_eax_imm,
  396: 	int dst, sljit_w dstw,
  397: 	int src1, sljit_w src1w,
  398: 	int src2, sljit_w src2w);
  399: 
  400: static int emit_non_cum_binary(struct sljit_compiler *compiler,
  401: 	sljit_ub op_rm, sljit_ub op_mr, sljit_ub op_imm, sljit_ub op_eax_imm,
  402: 	int dst, sljit_w dstw,
  403: 	int src1, sljit_w src1w,
  404: 	int src2, sljit_w src2w);
  405: 
  406: static int emit_mov(struct sljit_compiler *compiler,
  407: 	int dst, sljit_w dstw,
  408: 	int src, sljit_w srcw);
  409: 
  410: static SLJIT_INLINE int emit_save_flags(struct sljit_compiler *compiler)
  411: {
  412: 	sljit_ub *buf;
  413: 
  414: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  415: 	buf = (sljit_ub*)ensure_buf(compiler, 1 + 5);
  416: 	FAIL_IF(!buf);
  417: 	INC_SIZE(5);
  418: 	*buf++ = 0x9c; /* pushfd */
  419: #else
  420: 	buf = (sljit_ub*)ensure_buf(compiler, 1 + 6);
  421: 	FAIL_IF(!buf);
  422: 	INC_SIZE(6);
  423: 	*buf++ = 0x9c; /* pushfq */
  424: 	*buf++ = 0x48;
  425: #endif
  426: 	*buf++ = 0x8d; /* lea esp/rsp, [esp/rsp + sizeof(sljit_w)] */
  427: 	*buf++ = 0x64;
  428: 	*buf++ = 0x24;
  429: 	*buf++ = sizeof(sljit_w);
  430: 	compiler->flags_saved = 1;
  431: 	return SLJIT_SUCCESS;
  432: }
  433: 
  434: static SLJIT_INLINE int emit_restore_flags(struct sljit_compiler *compiler, int keep_flags)
  435: {
  436: 	sljit_ub *buf;
  437: 
  438: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  439: 	buf = (sljit_ub*)ensure_buf(compiler, 1 + 5);
  440: 	FAIL_IF(!buf);
  441: 	INC_SIZE(5);
  442: #else
  443: 	buf = (sljit_ub*)ensure_buf(compiler, 1 + 6);
  444: 	FAIL_IF(!buf);
  445: 	INC_SIZE(6);
  446: 	*buf++ = 0x48;
  447: #endif
  448: 	*buf++ = 0x8d; /* lea esp/rsp, [esp/rsp - sizeof(sljit_w)] */
  449: 	*buf++ = 0x64;
  450: 	*buf++ = 0x24;
  451: 	*buf++ = (sljit_ub)-(int)sizeof(sljit_w);
  452: 	*buf++ = 0x9d; /* popfd / popfq */
  453: 	compiler->flags_saved = keep_flags;
  454: 	return SLJIT_SUCCESS;
  455: }
  456: 
  457: #ifdef _WIN32
  458: #include <malloc.h>
  459: 
  460: static void SLJIT_CALL sljit_touch_stack(sljit_w local_size)
  461: {
  462: 	/* Workaround for calling _chkstk. */
  463: 	alloca(local_size);
  464: }
  465: #endif
  466: 
  467: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  468: #include "sljitNativeX86_32.c"
  469: #else
  470: #include "sljitNativeX86_64.c"
  471: #endif
  472: 
  473: static int emit_mov(struct sljit_compiler *compiler,
  474: 	int dst, sljit_w dstw,
  475: 	int src, sljit_w srcw)
  476: {
  477: 	sljit_ub* code;
  478: 
  479: 	if (dst == SLJIT_UNUSED) {
  480: 		/* No destination, doesn't need to setup flags. */
  481: 		if (src & SLJIT_MEM) {
  482: 			code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, src, srcw);
  483: 			FAIL_IF(!code);
  484: 			*code = 0x8b;
  485: 		}
  486: 		return SLJIT_SUCCESS;
  487: 	}
  488: 	if (src >= SLJIT_TEMPORARY_REG1 && src <= TMP_REGISTER) {
  489: 		code = emit_x86_instruction(compiler, 1, src, 0, dst, dstw);
  490: 		FAIL_IF(!code);
  491: 		*code = 0x89;
  492: 		return SLJIT_SUCCESS;
  493: 	}
  494: 	if (src & SLJIT_IMM) {
  495: 		if (dst >= SLJIT_TEMPORARY_REG1 && dst <= TMP_REGISTER) {
  496: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  497: 			return emit_do_imm(compiler, 0xb8 + reg_map[dst], srcw);
  498: #else
  499: 			if (!compiler->mode32) {
  500: 				if (NOT_HALFWORD(srcw))
  501: 					return emit_load_imm64(compiler, dst, srcw);
  502: 			}
  503: 			else
  504: 				return emit_do_imm32(compiler, (reg_map[dst] >= 8) ? REX_B : 0, 0xb8 + reg_lmap[dst], srcw);
  505: #endif
  506: 		}
  507: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
  508: 		if (!compiler->mode32 && NOT_HALFWORD(srcw)) {
  509: 			FAIL_IF(emit_load_imm64(compiler, TMP_REG2, srcw));
  510: 			code = emit_x86_instruction(compiler, 1, TMP_REG2, 0, dst, dstw);
  511: 			FAIL_IF(!code);
  512: 			*code = 0x89;
  513: 			return SLJIT_SUCCESS;
  514: 		}
  515: #endif
  516: 		code = emit_x86_instruction(compiler, 1, SLJIT_IMM, srcw, dst, dstw);
  517: 		FAIL_IF(!code);
  518: 		*code = 0xc7;
  519: 		return SLJIT_SUCCESS;
  520: 	}
  521: 	if (dst >= SLJIT_TEMPORARY_REG1 && dst <= TMP_REGISTER) {
  522: 		code = emit_x86_instruction(compiler, 1, dst, 0, src, srcw);
  523: 		FAIL_IF(!code);
  524: 		*code = 0x8b;
  525: 		return SLJIT_SUCCESS;
  526: 	}
  527: 
  528: 	/* Memory to memory move. Requires two instruction. */
  529: 	code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, src, srcw);
  530: 	FAIL_IF(!code);
  531: 	*code = 0x8b;
  532: 	code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, dst, dstw);
  533: 	FAIL_IF(!code);
  534: 	*code = 0x89;
  535: 	return SLJIT_SUCCESS;
  536: }
  537: 
  538: #define EMIT_MOV(compiler, dst, dstw, src, srcw) \
  539: 	FAIL_IF(emit_mov(compiler, dst, dstw, src, srcw));
  540: 
  541: SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_op0(struct sljit_compiler *compiler, int op)
  542: {
  543: 	sljit_ub *buf;
  544: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
  545: 	int size;
  546: #endif
  547: 
  548: 	CHECK_ERROR();
  549: 	check_sljit_emit_op0(compiler, op);
  550: 
  551: 	switch (GET_OPCODE(op)) {
  552: 	case SLJIT_BREAKPOINT:
  553: 		buf = (sljit_ub*)ensure_buf(compiler, 1 + 1);
  554: 		FAIL_IF(!buf);
  555: 		INC_SIZE(1);
  556: 		*buf = 0xcc;
  557: 		break;
  558: 	case SLJIT_NOP:
  559: 		buf = (sljit_ub*)ensure_buf(compiler, 1 + 1);
  560: 		FAIL_IF(!buf);
  561: 		INC_SIZE(1);
  562: 		*buf = 0x90;
  563: 		break;
  564: 	case SLJIT_UMUL:
  565: 	case SLJIT_SMUL:
  566: 	case SLJIT_UDIV:
  567: 	case SLJIT_SDIV:
  568: 		compiler->flags_saved = 0;
  569: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
  570: #ifdef _WIN64
  571: 		SLJIT_COMPILE_ASSERT(
  572: 			reg_map[SLJIT_TEMPORARY_REG1] == 0
  573: 			&& reg_map[SLJIT_TEMPORARY_REG2] == 2
  574: 			&& reg_map[TMP_REGISTER] > 7,
  575: 			invalid_register_assignment_for_div_mul);
  576: #else
  577: 		SLJIT_COMPILE_ASSERT(
  578: 			reg_map[SLJIT_TEMPORARY_REG1] == 0
  579: 			&& reg_map[SLJIT_TEMPORARY_REG2] < 7
  580: 			&& reg_map[TMP_REGISTER] == 2,
  581: 			invalid_register_assignment_for_div_mul);
  582: #endif
  583: 		compiler->mode32 = op & SLJIT_INT_OP;
  584: #endif
  585: 
  586: 		op = GET_OPCODE(op);
  587: 		if (op == SLJIT_UDIV) {
  588: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32) || defined(_WIN64)
  589: 			EMIT_MOV(compiler, TMP_REGISTER, 0, SLJIT_TEMPORARY_REG2, 0);
  590: 			buf = emit_x86_instruction(compiler, 1, SLJIT_TEMPORARY_REG2, 0, SLJIT_TEMPORARY_REG2, 0);
  591: #else
  592: 			buf = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, TMP_REGISTER, 0);
  593: #endif
  594: 			FAIL_IF(!buf);
  595: 			*buf = 0x33;
  596: 		}
  597: 
  598: 		if (op == SLJIT_SDIV) {
  599: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32) || defined(_WIN64)
  600: 			EMIT_MOV(compiler, TMP_REGISTER, 0, SLJIT_TEMPORARY_REG2, 0);
  601: #endif
  602: 
  603: 			/* CDQ instruction */
  604: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  605: 			buf = (sljit_ub*)ensure_buf(compiler, 1 + 1);
  606: 			FAIL_IF(!buf);
  607: 			INC_SIZE(1);
  608: 			*buf = 0x99;
  609: #else
  610: 			if (compiler->mode32) {
  611: 				buf = (sljit_ub*)ensure_buf(compiler, 1 + 1);
  612: 				FAIL_IF(!buf);
  613: 				INC_SIZE(1);
  614: 				*buf = 0x99;
  615: 			} else {
  616: 				buf = (sljit_ub*)ensure_buf(compiler, 1 + 2);
  617: 				FAIL_IF(!buf);
  618: 				INC_SIZE(2);
  619: 				*buf++ = REX_W;
  620: 				*buf = 0x99;
  621: 			}
  622: #endif
  623: 		}
  624: 
  625: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  626: 		buf = (sljit_ub*)ensure_buf(compiler, 1 + 2);
  627: 		FAIL_IF(!buf);
  628: 		INC_SIZE(2);
  629: 		*buf++ = 0xf7;
  630: 		*buf = 0xc0 | ((op >= SLJIT_UDIV) ? reg_map[TMP_REGISTER] : reg_map[SLJIT_TEMPORARY_REG2]);
  631: #else
  632: #ifdef _WIN64
  633: 		size = (!compiler->mode32 || op >= SLJIT_UDIV) ? 3 : 2;
  634: #else
  635: 		size = (!compiler->mode32) ? 3 : 2;
  636: #endif
  637: 		buf = (sljit_ub*)ensure_buf(compiler, 1 + size);
  638: 		FAIL_IF(!buf);
  639: 		INC_SIZE(size);
  640: #ifdef _WIN64
  641: 		if (!compiler->mode32)
  642: 			*buf++ = REX_W | ((op >= SLJIT_UDIV) ? REX_B : 0);
  643: 		else if (op >= SLJIT_UDIV)
  644: 			*buf++ = REX_B;
  645: 		*buf++ = 0xf7;
  646: 		*buf = 0xc0 | ((op >= SLJIT_UDIV) ? reg_lmap[TMP_REGISTER] : reg_lmap[SLJIT_TEMPORARY_REG2]);
  647: #else
  648: 		if (!compiler->mode32)
  649: 			*buf++ = REX_W;
  650: 		*buf++ = 0xf7;
  651: 		*buf = 0xc0 | reg_map[SLJIT_TEMPORARY_REG2];
  652: #endif
  653: #endif
  654: 		switch (op) {
  655: 		case SLJIT_UMUL:
  656: 			*buf |= 4 << 3;
  657: 			break;
  658: 		case SLJIT_SMUL:
  659: 			*buf |= 5 << 3;
  660: 			break;
  661: 		case SLJIT_UDIV:
  662: 			*buf |= 6 << 3;
  663: 			break;
  664: 		case SLJIT_SDIV:
  665: 			*buf |= 7 << 3;
  666: 			break;
  667: 		}
  668: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64) && !defined(_WIN64)
  669: 		EMIT_MOV(compiler, SLJIT_TEMPORARY_REG2, 0, TMP_REGISTER, 0);
  670: #endif
  671: 		break;
  672: 	}
  673: 
  674: 	return SLJIT_SUCCESS;
  675: }
  676: 
  677: #define ENCODE_PREFIX(prefix) \
  678: 	do { \
  679: 		code = (sljit_ub*)ensure_buf(compiler, 1 + 1); \
  680: 		FAIL_IF(!code); \
  681: 		INC_CSIZE(1); \
  682: 		*code = (prefix); \
  683: 	} while (0)
  684: 
  685: static int emit_mov_byte(struct sljit_compiler *compiler, int sign,
  686: 	int dst, sljit_w dstw,
  687: 	int src, sljit_w srcw)
  688: {
  689: 	sljit_ub* code;
  690: 	int dst_r;
  691: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  692: 	int work_r;
  693: #endif
  694: 
  695: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
  696: 	compiler->mode32 = 0;
  697: #endif
  698: 
  699: 	if (dst == SLJIT_UNUSED && !(src & SLJIT_MEM))
  700: 		return SLJIT_SUCCESS; /* Empty instruction. */
  701: 
  702: 	if (src & SLJIT_IMM) {
  703: 		if (dst >= SLJIT_TEMPORARY_REG1 && dst <= TMP_REGISTER) {
  704: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  705: 			return emit_do_imm(compiler, 0xb8 + reg_map[dst], srcw);
  706: #else
  707: 			return emit_load_imm64(compiler, dst, srcw);
  708: #endif
  709: 		}
  710: 		code = emit_x86_instruction(compiler, 1 | EX86_BYTE_ARG | EX86_NO_REXW, SLJIT_IMM, srcw, dst, dstw);
  711: 		FAIL_IF(!code);
  712: 		*code = 0xc6;
  713: 		return SLJIT_SUCCESS;
  714: 	}
  715: 
  716: 	dst_r = (dst >= SLJIT_TEMPORARY_REG1 && dst <= TMP_REGISTER) ? dst : TMP_REGISTER;
  717: 
  718: 	if ((dst & SLJIT_MEM) && src >= SLJIT_TEMPORARY_REG1 && src <= SLJIT_NO_REGISTERS) {
  719: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  720: 		if (reg_map[src] >= 4) {
  721: 			SLJIT_ASSERT(dst_r == TMP_REGISTER);
  722: 			EMIT_MOV(compiler, TMP_REGISTER, 0, src, 0);
  723: 		} else
  724: 			dst_r = src;
  725: #else
  726: 		dst_r = src;
  727: #endif
  728: 	}
  729: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  730: 	else if (src >= SLJIT_TEMPORARY_REG1 && src <= SLJIT_NO_REGISTERS && reg_map[src] >= 4) {
  731: 		/* src, dst are registers. */
  732: 		SLJIT_ASSERT(dst >= SLJIT_TEMPORARY_REG1 && dst <= TMP_REGISTER);
  733: 		if (reg_map[dst] < 4) {
  734: 			if (dst != src)
  735: 				EMIT_MOV(compiler, dst, 0, src, 0);
  736: 			code = emit_x86_instruction(compiler, 2, dst, 0, dst, 0);
  737: 			FAIL_IF(!code);
  738: 			*code++ = 0x0f;
  739: 			*code = sign ? 0xbe : 0xb6;
  740: 		}
  741: 		else {
  742: 			if (dst != src)
  743: 				EMIT_MOV(compiler, dst, 0, src, 0);
  744: 			if (sign) {
  745: 				/* shl reg, 24 */
  746: 				code = emit_x86_instruction(compiler, 1 | EX86_SHIFT_INS, SLJIT_IMM, 24, dst, 0);
  747: 				FAIL_IF(!code);
  748: 				*code |= 0x4 << 3;
  749: 				code = emit_x86_instruction(compiler, 1 | EX86_SHIFT_INS, SLJIT_IMM, 24, dst, 0);
  750: 				FAIL_IF(!code);
  751: 				/* shr/sar reg, 24 */
  752: 				*code |= 0x7 << 3;
  753: 			}
  754: 			else {
  755: 				/* and dst, 0xff */
  756: 				code = emit_x86_instruction(compiler, 1 | EX86_BIN_INS, SLJIT_IMM, 255, dst, 0);
  757: 				FAIL_IF(!code);
  758: 				*(code + 1) |= 0x4 << 3;
  759: 			}
  760: 		}
  761: 		return SLJIT_SUCCESS;
  762: 	}
  763: #endif
  764: 	else {
  765: 		/* src can be memory addr or reg_map[src] < 4 on x86_32 architectures. */
  766: 		code = emit_x86_instruction(compiler, 2, dst_r, 0, src, srcw);
  767: 		FAIL_IF(!code);
  768: 		*code++ = 0x0f;
  769: 		*code = sign ? 0xbe : 0xb6;
  770: 	}
  771: 
  772: 	if (dst & SLJIT_MEM) {
  773: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  774: 		if (dst_r == TMP_REGISTER) {
  775: 			/* Find a non-used register, whose reg_map[src] < 4. */
  776: 			if ((dst & 0xf) == SLJIT_TEMPORARY_REG1) {
  777: 				if ((dst & 0xf0) == (SLJIT_TEMPORARY_REG2 << 4))
  778: 					work_r = SLJIT_TEMPORARY_REG3;
  779: 				else
  780: 					work_r = SLJIT_TEMPORARY_REG2;
  781: 			}
  782: 			else {
  783: 				if ((dst & 0xf0) != (SLJIT_TEMPORARY_REG1 << 4))
  784: 					work_r = SLJIT_TEMPORARY_REG1;
  785: 				else if ((dst & 0xf) == SLJIT_TEMPORARY_REG2)
  786: 					work_r = SLJIT_TEMPORARY_REG3;
  787: 				else
  788: 					work_r = SLJIT_TEMPORARY_REG2;
  789: 			}
  790: 
  791: 			if (work_r == SLJIT_TEMPORARY_REG1) {
  792: 				ENCODE_PREFIX(0x90 + reg_map[TMP_REGISTER]);
  793: 			}
  794: 			else {
  795: 				code = emit_x86_instruction(compiler, 1, work_r, 0, dst_r, 0);
  796: 				FAIL_IF(!code);
  797: 				*code = 0x87;
  798: 			}
  799: 
  800: 			code = emit_x86_instruction(compiler, 1, work_r, 0, dst, dstw);
  801: 			FAIL_IF(!code);
  802: 			*code = 0x88;
  803: 
  804: 			if (work_r == SLJIT_TEMPORARY_REG1) {
  805: 				ENCODE_PREFIX(0x90 + reg_map[TMP_REGISTER]);
  806: 			}
  807: 			else {
  808: 				code = emit_x86_instruction(compiler, 1, work_r, 0, dst_r, 0);
  809: 				FAIL_IF(!code);
  810: 				*code = 0x87;
  811: 			}
  812: 		}
  813: 		else {
  814: 			code = emit_x86_instruction(compiler, 1, dst_r, 0, dst, dstw);
  815: 			FAIL_IF(!code);
  816: 			*code = 0x88;
  817: 		}
  818: #else
  819: 		code = emit_x86_instruction(compiler, 1 | EX86_REX | EX86_NO_REXW, dst_r, 0, dst, dstw);
  820: 		FAIL_IF(!code);
  821: 		*code = 0x88;
  822: #endif
  823: 	}
  824: 
  825: 	return SLJIT_SUCCESS;
  826: }
  827: 
  828: static int emit_mov_half(struct sljit_compiler *compiler, int sign,
  829: 	int dst, sljit_w dstw,
  830: 	int src, sljit_w srcw)
  831: {
  832: 	sljit_ub* code;
  833: 	int dst_r;
  834: 
  835: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
  836: 	compiler->mode32 = 0;
  837: #endif
  838: 
  839: 	if (dst == SLJIT_UNUSED && !(src & SLJIT_MEM))
  840: 		return SLJIT_SUCCESS; /* Empty instruction. */
  841: 
  842: 	if (src & SLJIT_IMM) {
  843: 		if (dst >= SLJIT_TEMPORARY_REG1 && dst <= TMP_REGISTER) {
  844: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  845: 			return emit_do_imm(compiler, 0xb8 + reg_map[dst], srcw);
  846: #else
  847: 			return emit_load_imm64(compiler, dst, srcw);
  848: #endif
  849: 		}
  850: 		code = emit_x86_instruction(compiler, 1 | EX86_HALF_ARG | EX86_NO_REXW | EX86_PREF_66, SLJIT_IMM, srcw, dst, dstw);
  851: 		FAIL_IF(!code);
  852: 		*code = 0xc7;
  853: 		return SLJIT_SUCCESS;
  854: 	}
  855: 
  856: 	dst_r = (dst >= SLJIT_TEMPORARY_REG1 && dst <= TMP_REGISTER) ? dst : TMP_REGISTER;
  857: 
  858: 	if ((dst & SLJIT_MEM) && (src >= SLJIT_TEMPORARY_REG1 && src <= SLJIT_NO_REGISTERS))
  859: 		dst_r = src;
  860: 	else {
  861: 		code = emit_x86_instruction(compiler, 2, dst_r, 0, src, srcw);
  862: 		FAIL_IF(!code);
  863: 		*code++ = 0x0f;
  864: 		*code = sign ? 0xbf : 0xb7;
  865: 	}
  866: 
  867: 	if (dst & SLJIT_MEM) {
  868: 		code = emit_x86_instruction(compiler, 1 | EX86_NO_REXW | EX86_PREF_66, dst_r, 0, dst, dstw);
  869: 		FAIL_IF(!code);
  870: 		*code = 0x89;
  871: 	}
  872: 
  873: 	return SLJIT_SUCCESS;
  874: }
  875: 
  876: static int emit_unary(struct sljit_compiler *compiler, int un_index,
  877: 	int dst, sljit_w dstw,
  878: 	int src, sljit_w srcw)
  879: {
  880: 	sljit_ub* code;
  881: 
  882: 	if (dst == SLJIT_UNUSED) {
  883: 		EMIT_MOV(compiler, TMP_REGISTER, 0, src, srcw);
  884: 		code = emit_x86_instruction(compiler, 1, 0, 0, TMP_REGISTER, 0);
  885: 		FAIL_IF(!code);
  886: 		*code++ = 0xf7;
  887: 		*code |= (un_index) << 3;
  888: 		return SLJIT_SUCCESS;
  889: 	}
  890: 	if (dst == src && dstw == srcw) {
  891: 		/* Same input and output */
  892: 		code = emit_x86_instruction(compiler, 1, 0, 0, dst, dstw);
  893: 		FAIL_IF(!code);
  894: 		*code++ = 0xf7;
  895: 		*code |= (un_index) << 3;
  896: 		return SLJIT_SUCCESS;
  897: 	}
  898: 	if (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) {
  899: 		EMIT_MOV(compiler, dst, 0, src, srcw);
  900: 		code = emit_x86_instruction(compiler, 1, 0, 0, dst, dstw);
  901: 		FAIL_IF(!code);
  902: 		*code++ = 0xf7;
  903: 		*code |= (un_index) << 3;
  904: 		return SLJIT_SUCCESS;
  905: 	}
  906: 	EMIT_MOV(compiler, TMP_REGISTER, 0, src, srcw);
  907: 	code = emit_x86_instruction(compiler, 1, 0, 0, TMP_REGISTER, 0);
  908: 	FAIL_IF(!code);
  909: 	*code++ = 0xf7;
  910: 	*code |= (un_index) << 3;
  911: 	EMIT_MOV(compiler, dst, dstw, TMP_REGISTER, 0);
  912: 	return SLJIT_SUCCESS;
  913: }
  914: 
  915: static int emit_not_with_flags(struct sljit_compiler *compiler,
  916: 	int dst, sljit_w dstw,
  917: 	int src, sljit_w srcw)
  918: {
  919: 	sljit_ub* code;
  920: 
  921: 	if (dst == SLJIT_UNUSED) {
  922: 		EMIT_MOV(compiler, TMP_REGISTER, 0, src, srcw);
  923: 		code = emit_x86_instruction(compiler, 1, 0, 0, TMP_REGISTER, 0);
  924: 		FAIL_IF(!code);
  925: 		*code++ = 0xf7;
  926: 		*code |= 0x2 << 3;
  927: 		code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, TMP_REGISTER, 0);
  928: 		FAIL_IF(!code);
  929: 		*code = 0x0b;
  930: 		return SLJIT_SUCCESS;
  931: 	}
  932: 	if (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) {
  933: 		EMIT_MOV(compiler, dst, 0, src, srcw);
  934: 		code = emit_x86_instruction(compiler, 1, 0, 0, dst, dstw);
  935: 		FAIL_IF(!code);
  936: 		*code++ = 0xf7;
  937: 		*code |= 0x2 << 3;
  938: 		code = emit_x86_instruction(compiler, 1, dst, 0, dst, 0);
  939: 		FAIL_IF(!code);
  940: 		*code = 0x0b;
  941: 		return SLJIT_SUCCESS;
  942: 	}
  943: 	EMIT_MOV(compiler, TMP_REGISTER, 0, src, srcw);
  944: 	code = emit_x86_instruction(compiler, 1, 0, 0, TMP_REGISTER, 0);
  945: 	FAIL_IF(!code);
  946: 	*code++ = 0xf7;
  947: 	*code |= 0x2 << 3;
  948: 	code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, TMP_REGISTER, 0);
  949: 	FAIL_IF(!code);
  950: 	*code = 0x0b;
  951: 	EMIT_MOV(compiler, dst, dstw, TMP_REGISTER, 0);
  952: 	return SLJIT_SUCCESS;
  953: }
  954: 
  955: static int emit_clz(struct sljit_compiler *compiler, int op,
  956: 	int dst, sljit_w dstw,
  957: 	int src, sljit_w srcw)
  958: {
  959: 	sljit_ub* code;
  960: 	int dst_r;
  961: 
  962: 	SLJIT_UNUSED_ARG(op);
  963: 	if (SLJIT_UNLIKELY(dst == SLJIT_UNUSED)) {
  964: 		/* Just set the zero flag. */
  965: 		EMIT_MOV(compiler, TMP_REGISTER, 0, src, srcw);
  966: 		code = emit_x86_instruction(compiler, 1, 0, 0, TMP_REGISTER, 0);
  967: 		FAIL_IF(!code);
  968: 		*code++ = 0xf7;
  969: 		*code |= 0x2 << 3;
  970: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  971: 		code = emit_x86_instruction(compiler, 1 | EX86_SHIFT_INS, SLJIT_IMM, 31, TMP_REGISTER, 0);
  972: #else
  973: 		code = emit_x86_instruction(compiler, 1 | EX86_SHIFT_INS, SLJIT_IMM, !(op & SLJIT_INT_OP) ? 63 : 31, TMP_REGISTER, 0);
  974: #endif
  975: 		FAIL_IF(!code);
  976: 		*code |= 0x5 << 3;
  977: 		return SLJIT_SUCCESS;
  978: 	}
  979: 
  980: 	if (SLJIT_UNLIKELY(src & SLJIT_IMM)) {
  981: 		EMIT_MOV(compiler, TMP_REGISTER, 0, src, srcw);
  982: 		src = TMP_REGISTER;
  983: 		srcw = 0;
  984: 	}
  985: 
  986: 	code = emit_x86_instruction(compiler, 2, TMP_REGISTER, 0, src, srcw);
  987: 	FAIL_IF(!code);
  988: 	*code++ = 0x0f;
  989: 	*code = 0xbd;
  990: 
  991: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
  992: 	if (dst >= SLJIT_TEMPORARY_REG1 && dst <= TMP_REGISTER)
  993: 		dst_r = dst;
  994: 	else {
  995: 		/* Find an unused temporary register. */
  996: 		if ((dst & 0xf) != SLJIT_TEMPORARY_REG1 && (dst & 0xf0) != (SLJIT_TEMPORARY_REG1 << 4))
  997: 			dst_r = SLJIT_TEMPORARY_REG1;
  998: 		else if ((dst & 0xf) != SLJIT_TEMPORARY_REG2 && (dst & 0xf0) != (SLJIT_TEMPORARY_REG2 << 4))
  999: 			dst_r = SLJIT_TEMPORARY_REG2;
 1000: 		else
 1001: 			dst_r = SLJIT_TEMPORARY_REG3;
 1002: 		EMIT_MOV(compiler, dst, dstw, dst_r, 0);
 1003: 	}
 1004: 	EMIT_MOV(compiler, dst_r, 0, SLJIT_IMM, 32 + 31);
 1005: #else
 1006: 	dst_r = (dst >= SLJIT_TEMPORARY_REG1 && dst <= TMP_REGISTER) ? dst : TMP_REG2;
 1007: 	compiler->mode32 = 0;
 1008: 	EMIT_MOV(compiler, dst_r, 0, SLJIT_IMM, !(op & SLJIT_INT_OP) ? 64 + 63 : 32 + 31);
 1009: 	compiler->mode32 = op & SLJIT_INT_OP;
 1010: #endif
 1011: 
 1012: 	code = emit_x86_instruction(compiler, 2, dst_r, 0, TMP_REGISTER, 0);
 1013: 	FAIL_IF(!code);
 1014: 	*code++ = 0x0f;
 1015: 	*code = 0x45;
 1016: 
 1017: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 1018: 	code = emit_x86_instruction(compiler, 1 | EX86_BIN_INS, SLJIT_IMM, 31, dst_r, 0);
 1019: #else
 1020: 	code = emit_x86_instruction(compiler, 1 | EX86_BIN_INS, SLJIT_IMM, !(op & SLJIT_INT_OP) ? 63 : 31, dst_r, 0);
 1021: #endif
 1022: 	FAIL_IF(!code);
 1023: 	*(code + 1) |= 0x6 << 3;
 1024: 
 1025: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 1026: 	if (dst & SLJIT_MEM) {
 1027: 		code = emit_x86_instruction(compiler, 1, dst_r, 0, dst, dstw);
 1028: 		FAIL_IF(!code);
 1029: 		*code = 0x87;
 1030: 	}
 1031: #else
 1032: 	if (dst & SLJIT_MEM)
 1033: 		EMIT_MOV(compiler, dst, dstw, TMP_REG2, 0);
 1034: #endif
 1035: 	return SLJIT_SUCCESS;
 1036: }
 1037: 
 1038: SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_op1(struct sljit_compiler *compiler, int op,
 1039: 	int dst, sljit_w dstw,
 1040: 	int src, sljit_w srcw)
 1041: {
 1042: 	sljit_ub* code;
 1043: 	int update = 0;
 1044: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 1045: 	int dst_is_ereg = 0;
 1046: 	int src_is_ereg = 0;
 1047: #else
 1048: 	#define src_is_ereg 0
 1049: #endif
 1050: 
 1051: 	CHECK_ERROR();
 1052: 	check_sljit_emit_op1(compiler, op, dst, dstw, src, srcw);
 1053: 
 1054: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1055: 	compiler->mode32 = op & SLJIT_INT_OP;
 1056: #endif
 1057: 	CHECK_EXTRA_REGS(dst, dstw, dst_is_ereg = 1);
 1058: 	CHECK_EXTRA_REGS(src, srcw, src_is_ereg = 1);
 1059: 
 1060: 	if (GET_OPCODE(op) >= SLJIT_MOV && GET_OPCODE(op) <= SLJIT_MOVU_SI) {
 1061: 		op = GET_OPCODE(op);
 1062: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1063: 		compiler->mode32 = 0;
 1064: #endif
 1065: 
 1066: 		SLJIT_COMPILE_ASSERT(SLJIT_MOV + 7 == SLJIT_MOVU, movu_offset);
 1067: 		if (op >= SLJIT_MOVU) {
 1068: 			update = 1;
 1069: 			op -= 7;
 1070: 		}
 1071: 
 1072: 		if (src & SLJIT_IMM) {
 1073: 			switch (op) {
 1074: 			case SLJIT_MOV_UB:
 1075: 				srcw = (unsigned char)srcw;
 1076: 				break;
 1077: 			case SLJIT_MOV_SB:
 1078: 				srcw = (signed char)srcw;
 1079: 				break;
 1080: 			case SLJIT_MOV_UH:
 1081: 				srcw = (unsigned short)srcw;
 1082: 				break;
 1083: 			case SLJIT_MOV_SH:
 1084: 				srcw = (signed short)srcw;
 1085: 				break;
 1086: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1087: 			case SLJIT_MOV_UI:
 1088: 				srcw = (unsigned int)srcw;
 1089: 				break;
 1090: 			case SLJIT_MOV_SI:
 1091: 				srcw = (signed int)srcw;
 1092: 				break;
 1093: #endif
 1094: 			}
 1095: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 1096: 			if (SLJIT_UNLIKELY(dst_is_ereg))
 1097: 				return emit_mov(compiler, dst, dstw, src, srcw);
 1098: #endif
 1099: 		}
 1100: 
 1101: 		if (SLJIT_UNLIKELY(update) && (src & SLJIT_MEM) && !src_is_ereg && (src & 0xf) && (srcw != 0 || (src & 0xf0) != 0)) {
 1102: 			code = emit_x86_instruction(compiler, 1, src & 0xf, 0, src, srcw);
 1103: 			FAIL_IF(!code);
 1104: 			*code = 0x8d;
 1105: 			src &= SLJIT_MEM | 0xf;
 1106: 			srcw = 0;
 1107: 		}
 1108: 
 1109: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 1110: 		if (SLJIT_UNLIKELY(dst_is_ereg) && (!(op == SLJIT_MOV || op == SLJIT_MOV_UI || op == SLJIT_MOV_SI) || (src & SLJIT_MEM))) {
 1111: 			SLJIT_ASSERT(dst == SLJIT_MEM1(SLJIT_LOCALS_REG));
 1112: 			dst = TMP_REGISTER;
 1113: 		}
 1114: #endif
 1115: 
 1116: 		switch (op) {
 1117: 		case SLJIT_MOV:
 1118: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 1119: 		case SLJIT_MOV_UI:
 1120: 		case SLJIT_MOV_SI:
 1121: #endif
 1122: 			FAIL_IF(emit_mov(compiler, dst, dstw, src, srcw));
 1123: 			break;
 1124: 		case SLJIT_MOV_UB:
 1125: 			FAIL_IF(emit_mov_byte(compiler, 0, dst, dstw, src, (src & SLJIT_IMM) ? (unsigned char)srcw : srcw));
 1126: 			break;
 1127: 		case SLJIT_MOV_SB:
 1128: 			FAIL_IF(emit_mov_byte(compiler, 1, dst, dstw, src, (src & SLJIT_IMM) ? (signed char)srcw : srcw));
 1129: 			break;
 1130: 		case SLJIT_MOV_UH:
 1131: 			FAIL_IF(emit_mov_half(compiler, 0, dst, dstw, src, (src & SLJIT_IMM) ? (unsigned short)srcw : srcw));
 1132: 			break;
 1133: 		case SLJIT_MOV_SH:
 1134: 			FAIL_IF(emit_mov_half(compiler, 1, dst, dstw, src, (src & SLJIT_IMM) ? (signed short)srcw : srcw));
 1135: 			break;
 1136: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1137: 		case SLJIT_MOV_UI:
 1138: 			FAIL_IF(emit_mov_int(compiler, 0, dst, dstw, src, (src & SLJIT_IMM) ? (unsigned int)srcw : srcw));
 1139: 			break;
 1140: 		case SLJIT_MOV_SI:
 1141: 			FAIL_IF(emit_mov_int(compiler, 1, dst, dstw, src, (src & SLJIT_IMM) ? (signed int)srcw : srcw));
 1142: 			break;
 1143: #endif
 1144: 		}
 1145: 
 1146: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 1147: 		if (SLJIT_UNLIKELY(dst_is_ereg) && dst == TMP_REGISTER)
 1148: 			return emit_mov(compiler, SLJIT_MEM1(SLJIT_LOCALS_REG), dstw, TMP_REGISTER, 0);
 1149: #endif
 1150: 
 1151: 		if (SLJIT_UNLIKELY(update) && (dst & SLJIT_MEM) && (dst & 0xf) && (dstw != 0 || (dst & 0xf0) != 0)) {
 1152: 			code = emit_x86_instruction(compiler, 1, dst & 0xf, 0, dst, dstw);
 1153: 			FAIL_IF(!code);
 1154: 			*code = 0x8d;
 1155: 		}
 1156: 		return SLJIT_SUCCESS;
 1157: 	}
 1158: 
 1159: 	if (SLJIT_UNLIKELY(GET_FLAGS(op)))
 1160: 		compiler->flags_saved = 0;
 1161: 
 1162: 	switch (GET_OPCODE(op)) {
 1163: 	case SLJIT_NOT:
 1164: 		if (SLJIT_UNLIKELY(op & SLJIT_SET_E))
 1165: 			return emit_not_with_flags(compiler, dst, dstw, src, srcw);
 1166: 		return emit_unary(compiler, 0x2, dst, dstw, src, srcw);
 1167: 
 1168: 	case SLJIT_NEG:
 1169: 		if (SLJIT_UNLIKELY(op & SLJIT_KEEP_FLAGS) && !compiler->flags_saved)
 1170: 			FAIL_IF(emit_save_flags(compiler));
 1171: 		return emit_unary(compiler, 0x3, dst, dstw, src, srcw);
 1172: 
 1173: 	case SLJIT_CLZ:
 1174: 		if (SLJIT_UNLIKELY(op & SLJIT_KEEP_FLAGS) && !compiler->flags_saved)
 1175: 			FAIL_IF(emit_save_flags(compiler));
 1176: 		return emit_clz(compiler, op, dst, dstw, src, srcw);
 1177: 	}
 1178: 
 1179: 	return SLJIT_SUCCESS;
 1180: 
 1181: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1182: 	#undef src_is_ereg
 1183: #endif
 1184: }
 1185: 
 1186: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1187: 
 1188: #define BINARY_IMM(_op_imm_, _op_mr_, immw, arg, argw) \
 1189: 	if (IS_HALFWORD(immw) || compiler->mode32) { \
 1190: 		code = emit_x86_instruction(compiler, 1 | EX86_BIN_INS, SLJIT_IMM, immw, arg, argw); \
 1191: 		FAIL_IF(!code); \
 1192: 		*(code + 1) |= (_op_imm_); \
 1193: 	} \
 1194: 	else { \
 1195: 		FAIL_IF(emit_load_imm64(compiler, TMP_REG2, immw)); \
 1196: 		code = emit_x86_instruction(compiler, 1, TMP_REG2, 0, arg, argw); \
 1197: 		FAIL_IF(!code); \
 1198: 		*code = (_op_mr_); \
 1199: 	}
 1200: 
 1201: #define BINARY_EAX_IMM(_op_eax_imm_, immw) \
 1202: 	FAIL_IF(emit_do_imm32(compiler, (!compiler->mode32) ? REX_W : 0, (_op_eax_imm_), immw))
 1203: 
 1204: #else
 1205: 
 1206: #define BINARY_IMM(_op_imm_, _op_mr_, immw, arg, argw) \
 1207: 	code = emit_x86_instruction(compiler, 1 | EX86_BIN_INS, SLJIT_IMM, immw, arg, argw); \
 1208: 	FAIL_IF(!code); \
 1209: 	*(code + 1) |= (_op_imm_);
 1210: 
 1211: #define BINARY_EAX_IMM(_op_eax_imm_, immw) \
 1212: 	FAIL_IF(emit_do_imm(compiler, (_op_eax_imm_), immw))
 1213: 
 1214: #endif
 1215: 
 1216: static int emit_cum_binary(struct sljit_compiler *compiler,
 1217: 	sljit_ub op_rm, sljit_ub op_mr, sljit_ub op_imm, sljit_ub op_eax_imm,
 1218: 	int dst, sljit_w dstw,
 1219: 	int src1, sljit_w src1w,
 1220: 	int src2, sljit_w src2w)
 1221: {
 1222: 	sljit_ub* code;
 1223: 
 1224: 	if (dst == SLJIT_UNUSED) {
 1225: 		EMIT_MOV(compiler, TMP_REGISTER, 0, src1, src1w);
 1226: 		if (src2 & SLJIT_IMM) {
 1227: 			BINARY_IMM(op_imm, op_mr, src2w, TMP_REGISTER, 0);
 1228: 		}
 1229: 		else {
 1230: 			code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, src2, src2w);
 1231: 			FAIL_IF(!code);
 1232: 			*code = op_rm;
 1233: 		}
 1234: 		return SLJIT_SUCCESS;
 1235: 	}
 1236: 
 1237: 	if (dst == src1 && dstw == src1w) {
 1238: 		if (src2 & SLJIT_IMM) {
 1239: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1240: 			if ((dst == SLJIT_TEMPORARY_REG1) && (src2w > 127 || src2w < -128) && (compiler->mode32 || IS_HALFWORD(src2w))) {
 1241: #else
 1242: 			if ((dst == SLJIT_TEMPORARY_REG1) && (src2w > 127 || src2w < -128)) {
 1243: #endif
 1244: 				BINARY_EAX_IMM(op_eax_imm, src2w);
 1245: 			}
 1246: 			else {
 1247: 				BINARY_IMM(op_imm, op_mr, src2w, dst, dstw);
 1248: 			}
 1249: 		}
 1250: 		else if (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) {
 1251: 			code = emit_x86_instruction(compiler, 1, dst, dstw, src2, src2w);
 1252: 			FAIL_IF(!code);
 1253: 			*code = op_rm;
 1254: 		}
 1255: 		else if (src2 >= SLJIT_TEMPORARY_REG1 && src2 <= TMP_REGISTER) {
 1256: 			/* Special exception for sljit_emit_cond_value. */
 1257: 			code = emit_x86_instruction(compiler, 1, src2, src2w, dst, dstw);
 1258: 			FAIL_IF(!code);
 1259: 			*code = op_mr;
 1260: 		}
 1261: 		else {
 1262: 			EMIT_MOV(compiler, TMP_REGISTER, 0, src2, src2w);
 1263: 			code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, dst, dstw);
 1264: 			FAIL_IF(!code);
 1265: 			*code = op_mr;
 1266: 		}
 1267: 		return SLJIT_SUCCESS;
 1268: 	}
 1269: 
 1270: 	/* Only for cumulative operations. */
 1271: 	if (dst == src2 && dstw == src2w) {
 1272: 		if (src1 & SLJIT_IMM) {
 1273: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1274: 			if ((dst == SLJIT_TEMPORARY_REG1) && (src1w > 127 || src1w < -128) && (compiler->mode32 || IS_HALFWORD(src1w))) {
 1275: #else
 1276: 			if ((dst == SLJIT_TEMPORARY_REG1) && (src1w > 127 || src1w < -128)) {
 1277: #endif
 1278: 				BINARY_EAX_IMM(op_eax_imm, src1w);
 1279: 			}
 1280: 			else {
 1281: 				BINARY_IMM(op_imm, op_mr, src1w, dst, dstw);
 1282: 			}
 1283: 		}
 1284: 		else if (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) {
 1285: 			code = emit_x86_instruction(compiler, 1, dst, dstw, src1, src1w);
 1286: 			FAIL_IF(!code);
 1287: 			*code = op_rm;
 1288: 		}
 1289: 		else if (src1 >= SLJIT_TEMPORARY_REG1 && src1 <= SLJIT_NO_REGISTERS) {
 1290: 			code = emit_x86_instruction(compiler, 1, src1, src1w, dst, dstw);
 1291: 			FAIL_IF(!code);
 1292: 			*code = op_mr;
 1293: 		}
 1294: 		else {
 1295: 			EMIT_MOV(compiler, TMP_REGISTER, 0, src1, src1w);
 1296: 			code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, dst, dstw);
 1297: 			FAIL_IF(!code);
 1298: 			*code = op_mr;
 1299: 		}
 1300: 		return SLJIT_SUCCESS;
 1301: 	}
 1302: 
 1303: 	/* General version. */
 1304: 	if (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) {
 1305: 		EMIT_MOV(compiler, dst, 0, src1, src1w);
 1306: 		if (src2 & SLJIT_IMM) {
 1307: 			BINARY_IMM(op_imm, op_mr, src2w, dst, 0);
 1308: 		}
 1309: 		else {
 1310: 			code = emit_x86_instruction(compiler, 1, dst, 0, src2, src2w);
 1311: 			FAIL_IF(!code);
 1312: 			*code = op_rm;
 1313: 		}
 1314: 	}
 1315: 	else {
 1316: 		/* This version requires less memory writing. */
 1317: 		EMIT_MOV(compiler, TMP_REGISTER, 0, src1, src1w);
 1318: 		if (src2 & SLJIT_IMM) {
 1319: 			BINARY_IMM(op_imm, op_mr, src2w, TMP_REGISTER, 0);
 1320: 		}
 1321: 		else {
 1322: 			code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, src2, src2w);
 1323: 			FAIL_IF(!code);
 1324: 			*code = op_rm;
 1325: 		}
 1326: 		EMIT_MOV(compiler, dst, dstw, TMP_REGISTER, 0);
 1327: 	}
 1328: 
 1329: 	return SLJIT_SUCCESS;
 1330: }
 1331: 
 1332: static int emit_non_cum_binary(struct sljit_compiler *compiler,
 1333: 	sljit_ub op_rm, sljit_ub op_mr, sljit_ub op_imm, sljit_ub op_eax_imm,
 1334: 	int dst, sljit_w dstw,
 1335: 	int src1, sljit_w src1w,
 1336: 	int src2, sljit_w src2w)
 1337: {
 1338: 	sljit_ub* code;
 1339: 
 1340: 	if (dst == SLJIT_UNUSED) {
 1341: 		EMIT_MOV(compiler, TMP_REGISTER, 0, src1, src1w);
 1342: 		if (src2 & SLJIT_IMM) {
 1343: 			BINARY_IMM(op_imm, op_mr, src2w, TMP_REGISTER, 0);
 1344: 		}
 1345: 		else {
 1346: 			code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, src2, src2w);
 1347: 			FAIL_IF(!code);
 1348: 			*code = op_rm;
 1349: 		}
 1350: 		return SLJIT_SUCCESS;
 1351: 	}
 1352: 
 1353: 	if (dst == src1 && dstw == src1w) {
 1354: 		if (src2 & SLJIT_IMM) {
 1355: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1356: 			if ((dst == SLJIT_TEMPORARY_REG1) && (src2w > 127 || src2w < -128) && (compiler->mode32 || IS_HALFWORD(src2w))) {
 1357: #else
 1358: 			if ((dst == SLJIT_TEMPORARY_REG1) && (src2w > 127 || src2w < -128)) {
 1359: #endif
 1360: 				BINARY_EAX_IMM(op_eax_imm, src2w);
 1361: 			}
 1362: 			else {
 1363: 				BINARY_IMM(op_imm, op_mr, src2w, dst, dstw);
 1364: 			}
 1365: 		}
 1366: 		else if (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) {
 1367: 			code = emit_x86_instruction(compiler, 1, dst, dstw, src2, src2w);
 1368: 			FAIL_IF(!code);
 1369: 			*code = op_rm;
 1370: 		}
 1371: 		else if (src2 >= SLJIT_TEMPORARY_REG1 && src2 <= SLJIT_NO_REGISTERS) {
 1372: 			code = emit_x86_instruction(compiler, 1, src2, src2w, dst, dstw);
 1373: 			FAIL_IF(!code);
 1374: 			*code = op_mr;
 1375: 		}
 1376: 		else {
 1377: 			EMIT_MOV(compiler, TMP_REGISTER, 0, src2, src2w);
 1378: 			code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, dst, dstw);
 1379: 			FAIL_IF(!code);
 1380: 			*code = op_mr;
 1381: 		}
 1382: 		return SLJIT_SUCCESS;
 1383: 	}
 1384: 
 1385: 	/* General version. */
 1386: 	if ((dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) && dst != src2) {
 1387: 		EMIT_MOV(compiler, dst, 0, src1, src1w);
 1388: 		if (src2 & SLJIT_IMM) {
 1389: 			BINARY_IMM(op_imm, op_mr, src2w, dst, 0);
 1390: 		}
 1391: 		else {
 1392: 			code = emit_x86_instruction(compiler, 1, dst, 0, src2, src2w);
 1393: 			FAIL_IF(!code);
 1394: 			*code = op_rm;
 1395: 		}
 1396: 	}
 1397: 	else {
 1398: 		/* This version requires less memory writing. */
 1399: 		EMIT_MOV(compiler, TMP_REGISTER, 0, src1, src1w);
 1400: 		if (src2 & SLJIT_IMM) {
 1401: 			BINARY_IMM(op_imm, op_mr, src2w, TMP_REGISTER, 0);
 1402: 		}
 1403: 		else {
 1404: 			code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, src2, src2w);
 1405: 			FAIL_IF(!code);
 1406: 			*code = op_rm;
 1407: 		}
 1408: 		EMIT_MOV(compiler, dst, dstw, TMP_REGISTER, 0);
 1409: 	}
 1410: 
 1411: 	return SLJIT_SUCCESS;
 1412: }
 1413: 
 1414: static int emit_mul(struct sljit_compiler *compiler,
 1415: 	int dst, sljit_w dstw,
 1416: 	int src1, sljit_w src1w,
 1417: 	int src2, sljit_w src2w)
 1418: {
 1419: 	sljit_ub* code;
 1420: 	int dst_r;
 1421: 
 1422: 	dst_r = (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) ? dst : TMP_REGISTER;
 1423: 
 1424: 	/* Register destination. */
 1425: 	if (dst_r == src1 && !(src2 & SLJIT_IMM)) {
 1426: 		code = emit_x86_instruction(compiler, 2, dst_r, 0, src2, src2w);
 1427: 		FAIL_IF(!code);
 1428: 		*code++ = 0x0f;
 1429: 		*code = 0xaf;
 1430: 	}
 1431: 	else if (dst_r == src2 && !(src1 & SLJIT_IMM)) {
 1432: 		code = emit_x86_instruction(compiler, 2, dst_r, 0, src1, src1w);
 1433: 		FAIL_IF(!code);
 1434: 		*code++ = 0x0f;
 1435: 		*code = 0xaf;
 1436: 	}
 1437: 	else if (src1 & SLJIT_IMM) {
 1438: 		if (src2 & SLJIT_IMM) {
 1439: 			EMIT_MOV(compiler, dst_r, 0, SLJIT_IMM, src2w);
 1440: 			src2 = dst_r;
 1441: 			src2w = 0;
 1442: 		}
 1443: 
 1444: 		if (src1w <= 127 && src1w >= -128) {
 1445: 			code = emit_x86_instruction(compiler, 1, dst_r, 0, src2, src2w);
 1446: 			FAIL_IF(!code);
 1447: 			*code = 0x6b;
 1448: 			code = (sljit_ub*)ensure_buf(compiler, 1 + 1);
 1449: 			FAIL_IF(!code);
 1450: 			INC_CSIZE(1);
 1451: 			*code = (sljit_b)src1w;
 1452: 		}
 1453: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 1454: 		else {
 1455: 			code = emit_x86_instruction(compiler, 1, dst_r, 0, src2, src2w);
 1456: 			FAIL_IF(!code);
 1457: 			*code = 0x69;
 1458: 			code = (sljit_ub*)ensure_buf(compiler, 1 + 4);
 1459: 			FAIL_IF(!code);
 1460: 			INC_CSIZE(4);
 1461: 			*(sljit_w*)code = src1w;
 1462: 		}
 1463: #else
 1464: 		else if (IS_HALFWORD(src1w)) {
 1465: 			code = emit_x86_instruction(compiler, 1, dst_r, 0, src2, src2w);
 1466: 			FAIL_IF(!code);
 1467: 			*code = 0x69;
 1468: 			code = (sljit_ub*)ensure_buf(compiler, 1 + 4);
 1469: 			FAIL_IF(!code);
 1470: 			INC_CSIZE(4);
 1471: 			*(sljit_hw*)code = (sljit_hw)src1w;
 1472: 		}
 1473: 		else {
 1474: 			EMIT_MOV(compiler, TMP_REG2, 0, SLJIT_IMM, src1w);
 1475: 			if (dst_r != src2)
 1476: 				EMIT_MOV(compiler, dst_r, 0, src2, src2w);
 1477: 			code = emit_x86_instruction(compiler, 2, dst_r, 0, TMP_REG2, 0);
 1478: 			FAIL_IF(!code);
 1479: 			*code++ = 0x0f;
 1480: 			*code = 0xaf;
 1481: 		}
 1482: #endif
 1483: 	}
 1484: 	else if (src2 & SLJIT_IMM) {
 1485: 		/* Note: src1 is NOT immediate. */
 1486: 
 1487: 		if (src2w <= 127 && src2w >= -128) {
 1488: 			code = emit_x86_instruction(compiler, 1, dst_r, 0, src1, src1w);
 1489: 			FAIL_IF(!code);
 1490: 			*code = 0x6b;
 1491: 			code = (sljit_ub*)ensure_buf(compiler, 1 + 1);
 1492: 			FAIL_IF(!code);
 1493: 			INC_CSIZE(1);
 1494: 			*code = (sljit_b)src2w;
 1495: 		}
 1496: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 1497: 		else {
 1498: 			code = emit_x86_instruction(compiler, 1, dst_r, 0, src1, src1w);
 1499: 			FAIL_IF(!code);
 1500: 			*code = 0x69;
 1501: 			code = (sljit_ub*)ensure_buf(compiler, 1 + 4);
 1502: 			FAIL_IF(!code);
 1503: 			INC_CSIZE(4);
 1504: 			*(sljit_w*)code = src2w;
 1505: 		}
 1506: #else
 1507: 		else if (IS_HALFWORD(src2w)) {
 1508: 			code = emit_x86_instruction(compiler, 1, dst_r, 0, src1, src1w);
 1509: 			FAIL_IF(!code);
 1510: 			*code = 0x69;
 1511: 			code = (sljit_ub*)ensure_buf(compiler, 1 + 4);
 1512: 			FAIL_IF(!code);
 1513: 			INC_CSIZE(4);
 1514: 			*(sljit_hw*)code = (sljit_hw)src2w;
 1515: 		}
 1516: 		else {
 1517: 			EMIT_MOV(compiler, TMP_REG2, 0, SLJIT_IMM, src1w);
 1518: 			if (dst_r != src1)
 1519: 				EMIT_MOV(compiler, dst_r, 0, src1, src1w);
 1520: 			code = emit_x86_instruction(compiler, 2, dst_r, 0, TMP_REG2, 0);
 1521: 			FAIL_IF(!code);
 1522: 			*code++ = 0x0f;
 1523: 			*code = 0xaf;
 1524: 		}
 1525: #endif
 1526: 	}
 1527: 	else {
 1528: 		/* Neither argument is immediate. */
 1529: 		if (ADDRESSING_DEPENDS_ON(src2, dst_r))
 1530: 			dst_r = TMP_REGISTER;
 1531: 		EMIT_MOV(compiler, dst_r, 0, src1, src1w);
 1532: 		code = emit_x86_instruction(compiler, 2, dst_r, 0, src2, src2w);
 1533: 		FAIL_IF(!code);
 1534: 		*code++ = 0x0f;
 1535: 		*code = 0xaf;
 1536: 	}
 1537: 
 1538: 	if (dst_r == TMP_REGISTER)
 1539: 		EMIT_MOV(compiler, dst, dstw, TMP_REGISTER, 0);
 1540: 
 1541: 	return SLJIT_SUCCESS;
 1542: }
 1543: 
 1544: static int emit_lea_binary(struct sljit_compiler *compiler,
 1545: 	int dst, sljit_w dstw,
 1546: 	int src1, sljit_w src1w,
 1547: 	int src2, sljit_w src2w)
 1548: {
 1549: 	sljit_ub* code;
 1550: 	int dst_r, done = 0;
 1551: 
 1552: 	/* These cases better be left to handled by normal way. */
 1553: 	if (dst == src1 && dstw == src1w)
 1554: 		return SLJIT_ERR_UNSUPPORTED;
 1555: 	if (dst == src2 && dstw == src2w)
 1556: 		return SLJIT_ERR_UNSUPPORTED;
 1557: 
 1558: 	dst_r = (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) ? dst : TMP_REGISTER;
 1559: 
 1560: 	if (src1 >= SLJIT_TEMPORARY_REG1 && src1 <= SLJIT_NO_REGISTERS) {
 1561: 		if (src2 >= SLJIT_TEMPORARY_REG1 && src2 <= SLJIT_NO_REGISTERS) {
 1562: 			/* It is not possible to be both SLJIT_LOCALS_REG. */
 1563: 			if (src1 != SLJIT_LOCALS_REG || src2 != SLJIT_LOCALS_REG) {
 1564: 				code = emit_x86_instruction(compiler, 1, dst_r, 0, SLJIT_MEM2(src1, src2), 0);
 1565: 				FAIL_IF(!code);
 1566: 				*code = 0x8d;
 1567: 				done = 1;
 1568: 			}
 1569: 		}
 1570: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1571: 		if ((src2 & SLJIT_IMM) && (compiler->mode32 || IS_HALFWORD(src2w))) {
 1572: 			code = emit_x86_instruction(compiler, 1, dst_r, 0, SLJIT_MEM1(src1), (int)src2w);
 1573: #else
 1574: 		if (src2 & SLJIT_IMM) {
 1575: 			code = emit_x86_instruction(compiler, 1, dst_r, 0, SLJIT_MEM1(src1), src2w);
 1576: #endif
 1577: 			FAIL_IF(!code);
 1578: 			*code = 0x8d;
 1579: 			done = 1;
 1580: 		}
 1581: 	}
 1582: 	else if (src2 >= SLJIT_TEMPORARY_REG1 && src2 <= SLJIT_NO_REGISTERS) {
 1583: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1584: 		if ((src1 & SLJIT_IMM) && (compiler->mode32 || IS_HALFWORD(src1w))) {
 1585: 			code = emit_x86_instruction(compiler, 1, dst_r, 0, SLJIT_MEM1(src2), (int)src1w);
 1586: #else
 1587: 		if (src1 & SLJIT_IMM) {
 1588: 			code = emit_x86_instruction(compiler, 1, dst_r, 0, SLJIT_MEM1(src2), src1w);
 1589: #endif
 1590: 			FAIL_IF(!code);
 1591: 			*code = 0x8d;
 1592: 			done = 1;
 1593: 		}
 1594: 	}
 1595: 
 1596: 	if (done) {
 1597: 		if (dst_r == TMP_REGISTER)
 1598: 			return emit_mov(compiler, dst, dstw, TMP_REGISTER, 0);
 1599: 		return SLJIT_SUCCESS;
 1600: 	}
 1601: 	return SLJIT_ERR_UNSUPPORTED;
 1602: }
 1603: 
 1604: static int emit_cmp_binary(struct sljit_compiler *compiler,
 1605: 	int src1, sljit_w src1w,
 1606: 	int src2, sljit_w src2w)
 1607: {
 1608: 	sljit_ub* code;
 1609: 
 1610: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1611: 	if (src1 == SLJIT_TEMPORARY_REG1 && (src2 & SLJIT_IMM) && (src2w > 127 || src2w < -128) && (compiler->mode32 || IS_HALFWORD(src2w))) {
 1612: #else
 1613: 	if (src1 == SLJIT_TEMPORARY_REG1 && (src2 & SLJIT_IMM) && (src2w > 127 || src2w < -128)) {
 1614: #endif
 1615: 		BINARY_EAX_IMM(0x3d, src2w);
 1616: 		return SLJIT_SUCCESS;
 1617: 	}
 1618: 
 1619: 	if (src1 >= SLJIT_TEMPORARY_REG1 && src1 <= SLJIT_NO_REGISTERS) {
 1620: 		if (src2 & SLJIT_IMM) {
 1621: 			BINARY_IMM(0x7 << 3, 0x39, src2w, src1, 0);
 1622: 		}
 1623: 		else {
 1624: 			code = emit_x86_instruction(compiler, 1, src1, 0, src2, src2w);
 1625: 			FAIL_IF(!code);
 1626: 			*code = 0x3b;
 1627: 		}
 1628: 		return SLJIT_SUCCESS;
 1629: 	}
 1630: 
 1631: 	if (src2 >= SLJIT_TEMPORARY_REG1 && src2 <= SLJIT_NO_REGISTERS && !(src1 & SLJIT_IMM)) {
 1632: 		code = emit_x86_instruction(compiler, 1, src2, 0, src1, src1w);
 1633: 		FAIL_IF(!code);
 1634: 		*code = 0x39;
 1635: 		return SLJIT_SUCCESS;
 1636: 	}
 1637: 
 1638: 	if (src2 & SLJIT_IMM) {
 1639: 		if (src1 & SLJIT_IMM) {
 1640: 			EMIT_MOV(compiler, TMP_REGISTER, 0, src1, src1w);
 1641: 			src1 = TMP_REGISTER;
 1642: 			src1w = 0;
 1643: 		}
 1644: 		BINARY_IMM(0x7 << 3, 0x39, src2w, src1, src1w);
 1645: 	}
 1646: 	else {
 1647: 		EMIT_MOV(compiler, TMP_REGISTER, 0, src1, src1w);
 1648: 		code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, src2, src2w);
 1649: 		FAIL_IF(!code);
 1650: 		*code = 0x3b;
 1651: 	}
 1652: 	return SLJIT_SUCCESS;
 1653: }
 1654: 
 1655: static int emit_test_binary(struct sljit_compiler *compiler,
 1656: 	int src1, sljit_w src1w,
 1657: 	int src2, sljit_w src2w)
 1658: {
 1659: 	sljit_ub* code;
 1660: 
 1661: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1662: 	if (src1 == SLJIT_TEMPORARY_REG1 && (src2 & SLJIT_IMM) && (src2w > 127 || src2w < -128) && (compiler->mode32 || IS_HALFWORD(src2w))) {
 1663: #else
 1664: 	if (src1 == SLJIT_TEMPORARY_REG1 && (src2 & SLJIT_IMM) && (src2w > 127 || src2w < -128)) {
 1665: #endif
 1666: 		BINARY_EAX_IMM(0xa9, src2w);
 1667: 		return SLJIT_SUCCESS;
 1668: 	}
 1669: 
 1670: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1671: 	if (src2 == SLJIT_TEMPORARY_REG1 && (src2 & SLJIT_IMM) && (src1w > 127 || src1w < -128) && (compiler->mode32 || IS_HALFWORD(src1w))) {
 1672: #else
 1673: 	if (src2 == SLJIT_TEMPORARY_REG1 && (src1 & SLJIT_IMM) && (src1w > 127 || src1w < -128)) {
 1674: #endif
 1675: 		BINARY_EAX_IMM(0xa9, src1w);
 1676: 		return SLJIT_SUCCESS;
 1677: 	}
 1678: 
 1679: 	if (src1 >= SLJIT_TEMPORARY_REG1 && src1 <= SLJIT_NO_REGISTERS) {
 1680: 		if (src2 & SLJIT_IMM) {
 1681: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1682: 			if (IS_HALFWORD(src2w) || compiler->mode32) {
 1683: 				code = emit_x86_instruction(compiler, 1, SLJIT_IMM, src2w, src1, 0);
 1684: 				FAIL_IF(!code);
 1685: 				*code = 0xf7;
 1686: 			}
 1687: 			else {
 1688: 				FAIL_IF(emit_load_imm64(compiler, TMP_REG2, src2w));
 1689: 				code = emit_x86_instruction(compiler, 1, TMP_REG2, 0, src1, 0);
 1690: 				FAIL_IF(!code);
 1691: 				*code = 0x85;
 1692: 			}
 1693: #else
 1694: 			code = emit_x86_instruction(compiler, 1, SLJIT_IMM, src2w, src1, 0);
 1695: 			FAIL_IF(!code);
 1696: 			*code = 0xf7;
 1697: #endif
 1698: 		}
 1699: 		else {
 1700: 			code = emit_x86_instruction(compiler, 1, src1, 0, src2, src2w);
 1701: 			FAIL_IF(!code);
 1702: 			*code = 0x85;
 1703: 		}
 1704: 		return SLJIT_SUCCESS;
 1705: 	}
 1706: 
 1707: 	if (src2 >= SLJIT_TEMPORARY_REG1 && src2 <= SLJIT_NO_REGISTERS) {
 1708: 		if (src1 & SLJIT_IMM) {
 1709: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1710: 			if (IS_HALFWORD(src1w) || compiler->mode32) {
 1711: 				code = emit_x86_instruction(compiler, 1, SLJIT_IMM, src1w, src2, 0);
 1712: 				FAIL_IF(!code);
 1713: 				*code = 0xf7;
 1714: 			}
 1715: 			else {
 1716: 				FAIL_IF(emit_load_imm64(compiler, TMP_REG2, src1w));
 1717: 				code = emit_x86_instruction(compiler, 1, TMP_REG2, 0, src2, 0);
 1718: 				FAIL_IF(!code);
 1719: 				*code = 0x85;
 1720: 			}
 1721: #else
 1722: 			code = emit_x86_instruction(compiler, 1, src1, src1w, src2, 0);
 1723: 			FAIL_IF(!code);
 1724: 			*code = 0xf7;
 1725: #endif
 1726: 		}
 1727: 		else {
 1728: 			code = emit_x86_instruction(compiler, 1, src2, 0, src1, src1w);
 1729: 			FAIL_IF(!code);
 1730: 			*code = 0x85;
 1731: 		}
 1732: 		return SLJIT_SUCCESS;
 1733: 	}
 1734: 
 1735: 	EMIT_MOV(compiler, TMP_REGISTER, 0, src1, src1w);
 1736: 	if (src2 & SLJIT_IMM) {
 1737: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1738: 		if (IS_HALFWORD(src2w) || compiler->mode32) {
 1739: 			code = emit_x86_instruction(compiler, 1, SLJIT_IMM, src2w, TMP_REGISTER, 0);
 1740: 			FAIL_IF(!code);
 1741: 			*code = 0xf7;
 1742: 		}
 1743: 		else {
 1744: 			FAIL_IF(emit_load_imm64(compiler, TMP_REG2, src2w));
 1745: 			code = emit_x86_instruction(compiler, 1, TMP_REG2, 0, TMP_REGISTER, 0);
 1746: 			FAIL_IF(!code);
 1747: 			*code = 0x85;
 1748: 		}
 1749: #else
 1750: 		code = emit_x86_instruction(compiler, 1, SLJIT_IMM, src2w, TMP_REGISTER, 0);
 1751: 		FAIL_IF(!code);
 1752: 		*code = 0xf7;
 1753: #endif
 1754: 	}
 1755: 	else {
 1756: 		code = emit_x86_instruction(compiler, 1, TMP_REGISTER, 0, src2, src2w);
 1757: 		FAIL_IF(!code);
 1758: 		*code = 0x85;
 1759: 	}
 1760: 	return SLJIT_SUCCESS;
 1761: }
 1762: 
 1763: static int emit_shift(struct sljit_compiler *compiler,
 1764: 	sljit_ub mode,
 1765: 	int dst, sljit_w dstw,
 1766: 	int src1, sljit_w src1w,
 1767: 	int src2, sljit_w src2w)
 1768: {
 1769: 	sljit_ub* code;
 1770: 
 1771: 	if ((src2 & SLJIT_IMM) || (src2 == SLJIT_PREF_SHIFT_REG)) {
 1772: 		if (dst == src1 && dstw == src1w) {
 1773: 			code = emit_x86_instruction(compiler, 1 | EX86_SHIFT_INS, src2, src2w, dst, dstw);
 1774: 			FAIL_IF(!code);
 1775: 			*code |= mode;
 1776: 			return SLJIT_SUCCESS;
 1777: 		}
 1778: 		if (dst == SLJIT_UNUSED) {
 1779: 			EMIT_MOV(compiler, TMP_REGISTER, 0, src1, src1w);
 1780: 			code = emit_x86_instruction(compiler, 1 | EX86_SHIFT_INS, src2, src2w, TMP_REGISTER, 0);
 1781: 			FAIL_IF(!code);
 1782: 			*code |= mode;
 1783: 			return SLJIT_SUCCESS;
 1784: 		}
 1785: 		if (dst == SLJIT_PREF_SHIFT_REG && src2 == SLJIT_PREF_SHIFT_REG) {
 1786: 			EMIT_MOV(compiler, TMP_REGISTER, 0, src1, src1w);
 1787: 			code = emit_x86_instruction(compiler, 1 | EX86_SHIFT_INS, SLJIT_PREF_SHIFT_REG, 0, TMP_REGISTER, 0);
 1788: 			FAIL_IF(!code);
 1789: 			*code |= mode;
 1790: 			EMIT_MOV(compiler, SLJIT_PREF_SHIFT_REG, 0, TMP_REGISTER, 0);
 1791: 			return SLJIT_SUCCESS;
 1792: 		}
 1793: 		if (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) {
 1794: 			EMIT_MOV(compiler, dst, 0, src1, src1w);
 1795: 			code = emit_x86_instruction(compiler, 1 | EX86_SHIFT_INS, src2, src2w, dst, 0);
 1796: 			FAIL_IF(!code);
 1797: 			*code |= mode;
 1798: 			return SLJIT_SUCCESS;
 1799: 		}
 1800: 
 1801: 		EMIT_MOV(compiler, TMP_REGISTER, 0, src1, src1w);
 1802: 		code = emit_x86_instruction(compiler, 1 | EX86_SHIFT_INS, src2, src2w, TMP_REGISTER, 0);
 1803: 		FAIL_IF(!code);
 1804: 		*code |= mode;
 1805: 		EMIT_MOV(compiler, dst, dstw, TMP_REGISTER, 0);
 1806: 		return SLJIT_SUCCESS;
 1807: 	}
 1808: 
 1809: 	if (dst == SLJIT_PREF_SHIFT_REG) {
 1810: 		EMIT_MOV(compiler, TMP_REGISTER, 0, src1, src1w);
 1811: 		EMIT_MOV(compiler, SLJIT_PREF_SHIFT_REG, 0, src2, src2w);
 1812: 		code = emit_x86_instruction(compiler, 1 | EX86_SHIFT_INS, SLJIT_PREF_SHIFT_REG, 0, TMP_REGISTER, 0);
 1813: 		FAIL_IF(!code);
 1814: 		*code |= mode;
 1815: 		EMIT_MOV(compiler, SLJIT_PREF_SHIFT_REG, 0, TMP_REGISTER, 0);
 1816: 	}
 1817: 	else if (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS && dst != src2 && !ADDRESSING_DEPENDS_ON(src2, dst)) {
 1818: 		if (src1 != dst)
 1819: 			EMIT_MOV(compiler, dst, 0, src1, src1w);
 1820: 		EMIT_MOV(compiler, TMP_REGISTER, 0, SLJIT_PREF_SHIFT_REG, 0);
 1821: 		EMIT_MOV(compiler, SLJIT_PREF_SHIFT_REG, 0, src2, src2w);
 1822: 		code = emit_x86_instruction(compiler, 1 | EX86_SHIFT_INS, SLJIT_PREF_SHIFT_REG, 0, dst, 0);
 1823: 		FAIL_IF(!code);
 1824: 		*code |= mode;
 1825: 		EMIT_MOV(compiler, SLJIT_PREF_SHIFT_REG, 0, TMP_REGISTER, 0);
 1826: 	}
 1827: 	else {
 1828: 		/* This case is really difficult, since ecx itself may used for
 1829: 		   addressing, and we must ensure to work even in that case. */
 1830: 		EMIT_MOV(compiler, TMP_REGISTER, 0, src1, src1w);
 1831: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1832: 		EMIT_MOV(compiler, TMP_REG2, 0, SLJIT_PREF_SHIFT_REG, 0);
 1833: #else
 1834: 		/* [esp - 4] is reserved for eflags. */
 1835: 		EMIT_MOV(compiler, SLJIT_MEM1(SLJIT_LOCALS_REG), -(int)(2 * sizeof(sljit_w)), SLJIT_PREF_SHIFT_REG, 0);
 1836: #endif
 1837: 		EMIT_MOV(compiler, SLJIT_PREF_SHIFT_REG, 0, src2, src2w);
 1838: 		code = emit_x86_instruction(compiler, 1 | EX86_SHIFT_INS, SLJIT_PREF_SHIFT_REG, 0, TMP_REGISTER, 0);
 1839: 		FAIL_IF(!code);
 1840: 		*code |= mode;
 1841: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1842: 		EMIT_MOV(compiler, SLJIT_PREF_SHIFT_REG, 0, TMP_REG2, 0);
 1843: #else
 1844: 		/* [esp - 4] is reserved for eflags. */
 1845: 		EMIT_MOV(compiler, SLJIT_PREF_SHIFT_REG, 0, SLJIT_MEM1(SLJIT_LOCALS_REG), -(int)(2 * sizeof(sljit_w)));
 1846: #endif
 1847: 		EMIT_MOV(compiler, dst, dstw, TMP_REGISTER, 0);
 1848: 	}
 1849: 
 1850: 	return SLJIT_SUCCESS;
 1851: }
 1852: 
 1853: static int emit_shift_with_flags(struct sljit_compiler *compiler,
 1854: 	sljit_ub mode, int set_flags,
 1855: 	int dst, sljit_w dstw,
 1856: 	int src1, sljit_w src1w,
 1857: 	int src2, sljit_w src2w)
 1858: {
 1859: 	/* The CPU does not set flags if the shift count is 0. */
 1860: 	if (src2 & SLJIT_IMM) {
 1861: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1862: 		if ((src2w & 0x3f) != 0 || (compiler->mode32 && (src2w & 0x1f) != 0))
 1863: 			return emit_shift(compiler, mode, dst, dstw, src1, src1w, src2, src2w);
 1864: #else
 1865: 		if ((src2w & 0x1f) != 0)
 1866: 			return emit_shift(compiler, mode, dst, dstw, src1, src1w, src2, src2w);
 1867: #endif
 1868: 		if (!set_flags)
 1869: 			return emit_mov(compiler, dst, dstw, src1, src1w);
 1870: 		/* OR dst, src, 0 */
 1871: 		return emit_cum_binary(compiler, 0x0b, 0x09, 0x1 << 3, 0x0d,
 1872: 			dst, dstw, src1, src1w, SLJIT_IMM, 0);
 1873: 	}
 1874: 
 1875: 	if (!set_flags)
 1876: 		return emit_shift(compiler, mode, dst, dstw, src1, src1w, src2, src2w);
 1877: 
 1878: 	if (!(dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS))
 1879: 		FAIL_IF(emit_cmp_binary(compiler, src1, src1w, SLJIT_IMM, 0));
 1880: 
 1881: 	FAIL_IF(emit_shift(compiler,mode, dst, dstw, src1, src1w, src2, src2w));
 1882: 
 1883: 	if (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS)
 1884: 		return emit_cmp_binary(compiler, dst, dstw, SLJIT_IMM, 0);
 1885: 	return SLJIT_SUCCESS;
 1886: }
 1887: 
 1888: SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_op2(struct sljit_compiler *compiler, int op,
 1889: 	int dst, sljit_w dstw,
 1890: 	int src1, sljit_w src1w,
 1891: 	int src2, sljit_w src2w)
 1892: {
 1893: 	CHECK_ERROR();
 1894: 	check_sljit_emit_op2(compiler, op, dst, dstw, src1, src1w, src2, src2w);
 1895: 
 1896: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 1897: 	compiler->mode32 = op & SLJIT_INT_OP;
 1898: #endif
 1899: 	CHECK_EXTRA_REGS(dst, dstw, (void)0);
 1900: 	CHECK_EXTRA_REGS(src1, src1w, (void)0);
 1901: 	CHECK_EXTRA_REGS(src2, src2w, (void)0);
 1902: 
 1903: 	if (GET_OPCODE(op) >= SLJIT_MUL) {
 1904: 		if (SLJIT_UNLIKELY(GET_FLAGS(op)))
 1905: 			compiler->flags_saved = 0;
 1906: 		else if (SLJIT_UNLIKELY(op & SLJIT_KEEP_FLAGS) && !compiler->flags_saved)
 1907: 			FAIL_IF(emit_save_flags(compiler));
 1908: 	}
 1909: 
 1910: 	switch (GET_OPCODE(op)) {
 1911: 	case SLJIT_ADD:
 1912: 		if (!GET_FLAGS(op)) {
 1913: 			if (emit_lea_binary(compiler, dst, dstw, src1, src1w, src2, src2w) != SLJIT_ERR_UNSUPPORTED)
 1914: 				return compiler->error;
 1915: 		} 
 1916: 		else
 1917: 			compiler->flags_saved = 0;
 1918: 		if (SLJIT_UNLIKELY(op & SLJIT_KEEP_FLAGS) && !compiler->flags_saved)
 1919: 			FAIL_IF(emit_save_flags(compiler));
 1920: 		return emit_cum_binary(compiler, 0x03, 0x01, 0x0 << 3, 0x05,
 1921: 			dst, dstw, src1, src1w, src2, src2w);
 1922: 	case SLJIT_ADDC:
 1923: 		if (SLJIT_UNLIKELY(compiler->flags_saved)) /* C flag must be restored. */
 1924: 			FAIL_IF(emit_restore_flags(compiler, 1));
 1925: 		else if (SLJIT_UNLIKELY(op & SLJIT_KEEP_FLAGS))
 1926: 			FAIL_IF(emit_save_flags(compiler));
 1927: 		if (SLJIT_UNLIKELY(GET_FLAGS(op)))
 1928: 			compiler->flags_saved = 0;
 1929: 		return emit_cum_binary(compiler, 0x13, 0x11, 0x2 << 3, 0x15,
 1930: 			dst, dstw, src1, src1w, src2, src2w);
 1931: 	case SLJIT_SUB:
 1932: 		if (!GET_FLAGS(op)) {
 1933: 			if ((src2 & SLJIT_IMM) && emit_lea_binary(compiler, dst, dstw, src1, src1w, SLJIT_IMM, -src2w) != SLJIT_ERR_UNSUPPORTED)
 1934: 				return compiler->error;
 1935: 		}
 1936: 		else
 1937: 			compiler->flags_saved = 0;
 1938: 		if (SLJIT_UNLIKELY(op & SLJIT_KEEP_FLAGS) && !compiler->flags_saved)
 1939: 			FAIL_IF(emit_save_flags(compiler));
 1940: 		if (dst == SLJIT_UNUSED)
 1941: 			return emit_cmp_binary(compiler, src1, src1w, src2, src2w);
 1942: 		return emit_non_cum_binary(compiler, 0x2b, 0x29, 0x5 << 3, 0x2d,
 1943: 			dst, dstw, src1, src1w, src2, src2w);
 1944: 	case SLJIT_SUBC:
 1945: 		if (SLJIT_UNLIKELY(compiler->flags_saved)) /* C flag must be restored. */
 1946: 			FAIL_IF(emit_restore_flags(compiler, 1));
 1947: 		else if (SLJIT_UNLIKELY(op & SLJIT_KEEP_FLAGS))
 1948: 			FAIL_IF(emit_save_flags(compiler));
 1949: 		if (SLJIT_UNLIKELY(GET_FLAGS(op)))
 1950: 			compiler->flags_saved = 0;
 1951: 		return emit_non_cum_binary(compiler, 0x1b, 0x19, 0x3 << 3, 0x1d,
 1952: 			dst, dstw, src1, src1w, src2, src2w);
 1953: 	case SLJIT_MUL:
 1954: 		return emit_mul(compiler, dst, dstw, src1, src1w, src2, src2w);
 1955: 	case SLJIT_AND:
 1956: 		if (dst == SLJIT_UNUSED)
 1957: 			return emit_test_binary(compiler, src1, src1w, src2, src2w);
 1958: 		return emit_cum_binary(compiler, 0x23, 0x21, 0x4 << 3, 0x25,
 1959: 			dst, dstw, src1, src1w, src2, src2w);
 1960: 	case SLJIT_OR:
 1961: 		return emit_cum_binary(compiler, 0x0b, 0x09, 0x1 << 3, 0x0d,
 1962: 			dst, dstw, src1, src1w, src2, src2w);
 1963: 	case SLJIT_XOR:
 1964: 		return emit_cum_binary(compiler, 0x33, 0x31, 0x6 << 3, 0x35,
 1965: 			dst, dstw, src1, src1w, src2, src2w);
 1966: 	case SLJIT_SHL:
 1967: 		return emit_shift_with_flags(compiler, 0x4 << 3, GET_FLAGS(op),
 1968: 			dst, dstw, src1, src1w, src2, src2w);
 1969: 	case SLJIT_LSHR:
 1970: 		return emit_shift_with_flags(compiler, 0x5 << 3, GET_FLAGS(op),
 1971: 			dst, dstw, src1, src1w, src2, src2w);
 1972: 	case SLJIT_ASHR:
 1973: 		return emit_shift_with_flags(compiler, 0x7 << 3, GET_FLAGS(op),
 1974: 			dst, dstw, src1, src1w, src2, src2w);
 1975: 	}
 1976: 
 1977: 	return SLJIT_SUCCESS;
 1978: }
 1979: 
 1980: SLJIT_API_FUNC_ATTRIBUTE int sljit_get_register_index(int reg)
 1981: {
 1982: 	check_sljit_get_register_index(reg);
 1983: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 1984: 	if (reg == SLJIT_TEMPORARY_EREG1 || reg == SLJIT_TEMPORARY_EREG2
 1985: 			|| reg == SLJIT_SAVED_EREG1 || reg == SLJIT_SAVED_EREG2)
 1986: 		return -1;
 1987: #endif
 1988: 	return reg_map[reg];
 1989: }
 1990: 
 1991: SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_op_custom(struct sljit_compiler *compiler,
 1992: 	void *instruction, int size)
 1993: {
 1994: 	sljit_ub *buf;
 1995: 
 1996: 	CHECK_ERROR();
 1997: 	check_sljit_emit_op_custom(compiler, instruction, size);
 1998: 	SLJIT_ASSERT(size > 0 && size < 16);
 1999: 
 2000: 	buf = (sljit_ub*)ensure_buf(compiler, 1 + size);
 2001: 	FAIL_IF(!buf);
 2002: 	INC_SIZE(size);
 2003: 	SLJIT_MEMMOVE(buf, instruction, size);
 2004: 	return SLJIT_SUCCESS;
 2005: }
 2006: 
 2007: /* --------------------------------------------------------------------- */
 2008: /*  Floating point operators                                             */
 2009: /* --------------------------------------------------------------------- */
 2010: 
 2011: #if (defined SLJIT_SSE2_AUTO && SLJIT_SSE2_AUTO)
 2012: static int sse2_available = 0;
 2013: #endif
 2014: 
 2015: #if (defined SLJIT_SSE2 && SLJIT_SSE2)
 2016: 
 2017: /* Alignment + 2 * 16 bytes. */
 2018: static sljit_i sse2_data[3 + 4 + 4];
 2019: static sljit_i *sse2_buffer;
 2020: 
 2021: static void init_compiler()
 2022: {
 2023: #if (defined SLJIT_SSE2_AUTO && SLJIT_SSE2_AUTO)
 2024: 	int features = 0;
 2025: #endif
 2026: 
 2027: 	sse2_buffer = (sljit_i*)(((sljit_uw)sse2_data + 15) & ~0xf);
 2028: 	sse2_buffer[0] = 0;
 2029: 	sse2_buffer[1] = 0x80000000;
 2030: 	sse2_buffer[4] = 0xffffffff;
 2031: 	sse2_buffer[5] = 0x7fffffff;
 2032: 
 2033: #if (defined SLJIT_SSE2_AUTO && SLJIT_SSE2_AUTO)
 2034: #ifdef __GNUC__
 2035: 	/* AT&T syntax. */
 2036: 	asm (
 2037: 		"pushl %%ebx\n"
 2038: 		"movl $0x1, %%eax\n"
 2039: 		"cpuid\n"
 2040: 		"popl %%ebx\n"
 2041: 		"movl %%edx, %0\n"
 2042: 		: "=g" (features)
 2043: 		:
 2044: 		: "%eax", "%ecx", "%edx"
 2045: 	);
 2046: #elif defined(_MSC_VER) || defined(__BORLANDC__)
 2047: 	/* Intel syntax. */
 2048: 	__asm {
 2049: 		mov eax, 1
 2050: 		push ebx
 2051: 		cpuid
 2052: 		pop ebx
 2053: 		mov features, edx
 2054: 	}
 2055: #else
 2056: 	#error "SLJIT_SSE2_AUTO is not implemented for this C compiler"
 2057: #endif
 2058: 	sse2_available = (features >> 26) & 0x1;
 2059: #endif
 2060: }
 2061: 
 2062: #endif
 2063: 
 2064: SLJIT_API_FUNC_ATTRIBUTE int sljit_is_fpu_available(void)
 2065: {
 2066: 	/* Always available. */
 2067: 	return 1;
 2068: }
 2069: 
 2070: #if (defined SLJIT_SSE2 && SLJIT_SSE2)
 2071: 
 2072: static int emit_sse2(struct sljit_compiler *compiler, sljit_ub opcode,
 2073: 	int xmm1, int xmm2, sljit_w xmm2w)
 2074: {
 2075: 	sljit_ub *buf;
 2076: 
 2077: 	buf = emit_x86_instruction(compiler, 2 | EX86_PREF_F2 | EX86_SSE2, xmm1, 0, xmm2, xmm2w);
 2078: 	FAIL_IF(!buf);
 2079: 	*buf++ = 0x0f;
 2080: 	*buf = opcode;
 2081: 	return SLJIT_SUCCESS;
 2082: }
 2083: 
 2084: static int emit_sse2_logic(struct sljit_compiler *compiler, sljit_ub opcode,
 2085: 	int xmm1, int xmm2, sljit_w xmm2w)
 2086: {
 2087: 	sljit_ub *buf;
 2088: 
 2089: 	buf = emit_x86_instruction(compiler, 2 | EX86_PREF_66 | EX86_SSE2, xmm1, 0, xmm2, xmm2w);
 2090: 	FAIL_IF(!buf);
 2091: 	*buf++ = 0x0f;
 2092: 	*buf = opcode;
 2093: 	return SLJIT_SUCCESS;
 2094: }
 2095: 
 2096: static SLJIT_INLINE int emit_sse2_load(struct sljit_compiler *compiler,
 2097: 	int dst, int src, sljit_w srcw)
 2098: {
 2099: 	return emit_sse2(compiler, 0x10, dst, src, srcw);
 2100: }
 2101: 
 2102: static SLJIT_INLINE int emit_sse2_store(struct sljit_compiler *compiler,
 2103: 	int dst, sljit_w dstw, int src)
 2104: {
 2105: 	return emit_sse2(compiler, 0x11, src, dst, dstw);
 2106: }
 2107: 
 2108: #if !(defined SLJIT_SSE2_AUTO && SLJIT_SSE2_AUTO)
 2109: SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_fop1(struct sljit_compiler *compiler, int op,
 2110: #else
 2111: static int sljit_emit_sse2_fop1(struct sljit_compiler *compiler, int op,
 2112: #endif
 2113: 	int dst, sljit_w dstw,
 2114: 	int src, sljit_w srcw)
 2115: {
 2116: 	int dst_r;
 2117: 
 2118: 	CHECK_ERROR();
 2119: 	check_sljit_emit_fop1(compiler, op, dst, dstw, src, srcw);
 2120: 
 2121: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 2122: 	compiler->mode32 = 1;
 2123: #endif
 2124: 
 2125: 	if (GET_OPCODE(op) == SLJIT_FCMP) {
 2126: 		compiler->flags_saved = 0;
 2127: 		if (dst >= SLJIT_FLOAT_REG1 && dst <= SLJIT_FLOAT_REG4)
 2128: 			dst_r = dst;
 2129: 		else {
 2130: 			dst_r = TMP_FREG;
 2131: 			FAIL_IF(emit_sse2_load(compiler, dst_r, dst, dstw));
 2132: 		}
 2133: 		return emit_sse2_logic(compiler, 0x2e, dst_r, src, srcw);
 2134: 	}
 2135: 
 2136: 	if (op == SLJIT_FMOV) {
 2137: 		if (dst >= SLJIT_FLOAT_REG1 && dst <= SLJIT_FLOAT_REG4)
 2138: 			return emit_sse2_load(compiler, dst, src, srcw);
 2139: 		if (src >= SLJIT_FLOAT_REG1 && src <= SLJIT_FLOAT_REG4)
 2140: 			return emit_sse2_store(compiler, dst, dstw, src);
 2141: 		FAIL_IF(emit_sse2_load(compiler, TMP_FREG, src, srcw));
 2142: 		return emit_sse2_store(compiler, dst, dstw, TMP_FREG);
 2143: 	}
 2144: 
 2145: 	if (dst >= SLJIT_FLOAT_REG1 && dst <= SLJIT_FLOAT_REG4) {
 2146: 		dst_r = dst;
 2147: 		if (dst != src)
 2148: 			FAIL_IF(emit_sse2_load(compiler, dst_r, src, srcw));
 2149: 	}
 2150: 	else {
 2151: 		dst_r = TMP_FREG;
 2152: 		FAIL_IF(emit_sse2_load(compiler, dst_r, src, srcw));
 2153: 	}
 2154: 
 2155: 	switch (op) {
 2156: 	case SLJIT_FNEG:
 2157: 		FAIL_IF(emit_sse2_logic(compiler, 0x57, dst_r, SLJIT_MEM0(), (sljit_w)sse2_buffer));
 2158: 		break;
 2159: 
 2160: 	case SLJIT_FABS:
 2161: 		FAIL_IF(emit_sse2_logic(compiler, 0x54, dst_r, SLJIT_MEM0(), (sljit_w)(sse2_buffer + 4)));
 2162: 		break;
 2163: 	}
 2164: 
 2165: 	if (dst_r == TMP_FREG)
 2166: 		return emit_sse2_store(compiler, dst, dstw, TMP_FREG);
 2167: 	return SLJIT_SUCCESS;
 2168: }
 2169: 
 2170: #if !(defined SLJIT_SSE2_AUTO && SLJIT_SSE2_AUTO)
 2171: SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_fop2(struct sljit_compiler *compiler, int op,
 2172: #else
 2173: static int sljit_emit_sse2_fop2(struct sljit_compiler *compiler, int op,
 2174: #endif
 2175: 	int dst, sljit_w dstw,
 2176: 	int src1, sljit_w src1w,
 2177: 	int src2, sljit_w src2w)
 2178: {
 2179: 	int dst_r;
 2180: 
 2181: 	CHECK_ERROR();
 2182: 	check_sljit_emit_fop2(compiler, op, dst, dstw, src1, src1w, src2, src2w);
 2183: 
 2184: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 2185: 	compiler->mode32 = 1;
 2186: #endif
 2187: 
 2188: 	if (dst >= SLJIT_FLOAT_REG1 && dst <= SLJIT_FLOAT_REG4) {
 2189: 		dst_r = dst;
 2190: 		if (dst == src1)
 2191: 			; /* Do nothing here. */
 2192: 		else if (dst == src2 && (op == SLJIT_FADD || op == SLJIT_FMUL)) {
 2193: 			/* Swap arguments. */
 2194: 			src2 = src1;
 2195: 			src2w = src1w;
 2196: 		}
 2197: 		else if (dst != src2)
 2198: 			FAIL_IF(emit_sse2_load(compiler, dst_r, src1, src1w));
 2199: 		else {
 2200: 			dst_r = TMP_FREG;
 2201: 			FAIL_IF(emit_sse2_load(compiler, TMP_FREG, src1, src1w));
 2202: 		}
 2203: 	}
 2204: 	else {
 2205: 		dst_r = TMP_FREG;
 2206: 		FAIL_IF(emit_sse2_load(compiler, TMP_FREG, src1, src1w));
 2207: 	}
 2208: 
 2209: 	switch (op) {
 2210: 	case SLJIT_FADD:
 2211: 		FAIL_IF(emit_sse2(compiler, 0x58, dst_r, src2, src2w));
 2212: 		break;
 2213: 
 2214: 	case SLJIT_FSUB:
 2215: 		FAIL_IF(emit_sse2(compiler, 0x5c, dst_r, src2, src2w));
 2216: 		break;
 2217: 
 2218: 	case SLJIT_FMUL:
 2219: 		FAIL_IF(emit_sse2(compiler, 0x59, dst_r, src2, src2w));
 2220: 		break;
 2221: 
 2222: 	case SLJIT_FDIV:
 2223: 		FAIL_IF(emit_sse2(compiler, 0x5e, dst_r, src2, src2w));
 2224: 		break;
 2225: 	}
 2226: 
 2227: 	if (dst_r == TMP_FREG)
 2228: 		return emit_sse2_store(compiler, dst, dstw, TMP_FREG);
 2229: 	return SLJIT_SUCCESS;
 2230: }
 2231: 
 2232: #endif
 2233: 
 2234: #if (defined SLJIT_SSE2_AUTO && SLJIT_SSE2_AUTO) || !(defined SLJIT_SSE2 && SLJIT_SSE2)
 2235: 
 2236: static int emit_fld(struct sljit_compiler *compiler,
 2237: 	int src, sljit_w srcw)
 2238: {
 2239: 	sljit_ub *buf;
 2240: 
 2241: 	if (src >= SLJIT_FLOAT_REG1 && src <= SLJIT_FLOAT_REG4) {
 2242: 		buf = (sljit_ub*)ensure_buf(compiler, 1 + 2);
 2243: 		FAIL_IF(!buf);
 2244: 		INC_SIZE(2);
 2245: 		*buf++ = 0xd9;
 2246: 		*buf = 0xc0 + src - 1;
 2247: 		return SLJIT_SUCCESS;
 2248: 	}
 2249: 
 2250: 	buf = emit_x86_instruction(compiler, 1, 0, 0, src, srcw);
 2251: 	FAIL_IF(!buf);
 2252: 	*buf = 0xdd;
 2253: 	return SLJIT_SUCCESS;
 2254: }
 2255: 
 2256: static int emit_fop(struct sljit_compiler *compiler,
 2257: 	sljit_ub st_arg, sljit_ub st_arg2,
 2258: 	sljit_ub m64fp_arg, sljit_ub m64fp_arg2,
 2259: 	int src, sljit_w srcw)
 2260: {
 2261: 	sljit_ub *buf;
 2262: 
 2263: 	if (src >= SLJIT_FLOAT_REG1 && src <= SLJIT_FLOAT_REG4) {
 2264: 		buf = (sljit_ub*)ensure_buf(compiler, 1 + 2);
 2265: 		FAIL_IF(!buf);
 2266: 		INC_SIZE(2);
 2267: 		*buf++ = st_arg;
 2268: 		*buf = st_arg2 + src;
 2269: 		return SLJIT_SUCCESS;
 2270: 	}
 2271: 
 2272: 	buf = emit_x86_instruction(compiler, 1, 0, 0, src, srcw);
 2273: 	FAIL_IF(!buf);
 2274: 	*buf++ = m64fp_arg;
 2275: 	*buf |= m64fp_arg2;
 2276: 	return SLJIT_SUCCESS;
 2277: }
 2278: 
 2279: static int emit_fop_regs(struct sljit_compiler *compiler,
 2280: 	sljit_ub st_arg, sljit_ub st_arg2,
 2281: 	int src)
 2282: {
 2283: 	sljit_ub *buf;
 2284: 
 2285: 	buf = (sljit_ub*)ensure_buf(compiler, 1 + 2);
 2286: 	FAIL_IF(!buf);
 2287: 	INC_SIZE(2);
 2288: 	*buf++ = st_arg;
 2289: 	*buf = st_arg2 + src;
 2290: 	return SLJIT_SUCCESS;
 2291: }
 2292: 
 2293: #if !(defined SLJIT_SSE2_AUTO && SLJIT_SSE2_AUTO)
 2294: SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_fop1(struct sljit_compiler *compiler, int op,
 2295: #else
 2296: static int sljit_emit_fpu_fop1(struct sljit_compiler *compiler, int op,
 2297: #endif
 2298: 	int dst, sljit_w dstw,
 2299: 	int src, sljit_w srcw)
 2300: {
 2301: #if !(defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 2302: 	sljit_ub *buf;
 2303: #endif
 2304: 
 2305: 	CHECK_ERROR();
 2306: 	check_sljit_emit_fop1(compiler, op, dst, dstw, src, srcw);
 2307: 
 2308: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 2309: 	compiler->mode32 = 1;
 2310: #endif
 2311: 
 2312: 	if (GET_OPCODE(op) == SLJIT_FCMP) {
 2313: 		compiler->flags_saved = 0;
 2314: #if !(defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 2315: 		FAIL_IF(emit_fld(compiler, dst, dstw));
 2316: 		FAIL_IF(emit_fop(compiler, 0xd8, 0xd8, 0xdc, 0x3 << 3, src, srcw));
 2317: 
 2318: 		/* Copy flags. */
 2319: 		EMIT_MOV(compiler, TMP_REGISTER, 0, SLJIT_TEMPORARY_REG1, 0);
 2320: 		buf = (sljit_ub*)ensure_buf(compiler, 1 + 3);
 2321: 		FAIL_IF(!buf);
 2322: 		INC_SIZE(3);
 2323: 		*buf++ = 0xdf;
 2324: 		*buf++ = 0xe0;
 2325: 		/* Note: lahf is not supported on all x86-64 architectures. */
 2326: 		*buf++ = 0x9e;
 2327: 		EMIT_MOV(compiler, SLJIT_TEMPORARY_REG1, 0, TMP_REGISTER, 0);
 2328: #else
 2329: 		if (src >= SLJIT_FLOAT_REG1 && src <= SLJIT_FLOAT_REG4) {
 2330: 			FAIL_IF(emit_fld(compiler, dst, dstw));
 2331: 			FAIL_IF(emit_fop_regs(compiler, 0xdf, 0xe8, src));
 2332: 		} else {
 2333: 			FAIL_IF(emit_fld(compiler, src, srcw));
 2334: 			FAIL_IF(emit_fld(compiler, dst + ((dst >= SLJIT_FLOAT_REG1 && dst <= SLJIT_FLOAT_REG4) ? 1 : 0), dstw));
 2335: 			FAIL_IF(emit_fop_regs(compiler, 0xdf, 0xe8, src));
 2336: 			FAIL_IF(emit_fop_regs(compiler, 0xdd, 0xd8, 0));
 2337: 		}
 2338: #endif
 2339: 		return SLJIT_SUCCESS;
 2340: 	}
 2341: 
 2342: 	FAIL_IF(emit_fld(compiler, src, srcw));
 2343: 
 2344: 	switch (op) {
 2345: 	case SLJIT_FNEG:
 2346: 		FAIL_IF(emit_fop_regs(compiler, 0xd9, 0xe0, 0));
 2347: 		break;
 2348: 	case SLJIT_FABS:
 2349: 		FAIL_IF(emit_fop_regs(compiler, 0xd9, 0xe1, 0));
 2350: 		break;
 2351: 	}
 2352: 
 2353: 	FAIL_IF(emit_fop(compiler, 0xdd, 0xd8, 0xdd, 0x3 << 3, dst, dstw));
 2354: 
 2355: 	return SLJIT_SUCCESS;
 2356: }
 2357: 
 2358: #if !(defined SLJIT_SSE2_AUTO && SLJIT_SSE2_AUTO)
 2359: SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_fop2(struct sljit_compiler *compiler, int op,
 2360: #else
 2361: static int sljit_emit_fpu_fop2(struct sljit_compiler *compiler, int op,
 2362: #endif
 2363: 	int dst, sljit_w dstw,
 2364: 	int src1, sljit_w src1w,
 2365: 	int src2, sljit_w src2w)
 2366: {
 2367: 	CHECK_ERROR();
 2368: 	check_sljit_emit_fop2(compiler, op, dst, dstw, src1, src1w, src2, src2w);
 2369: 
 2370: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 2371: 	compiler->mode32 = 1;
 2372: #endif
 2373: 
 2374: 	if (src1 >= SLJIT_FLOAT_REG1 && src1 <= SLJIT_FLOAT_REG4 && dst == src1) {
 2375: 		FAIL_IF(emit_fld(compiler, src2, src2w));
 2376: 
 2377: 		switch (op) {
 2378: 		case SLJIT_FADD:
 2379: 			FAIL_IF(emit_fop_regs(compiler, 0xde, 0xc0, src1));
 2380: 			break;
 2381: 		case SLJIT_FSUB:
 2382: 			FAIL_IF(emit_fop_regs(compiler, 0xde, 0xe8, src1));
 2383: 			break;
 2384: 		case SLJIT_FMUL:
 2385: 			FAIL_IF(emit_fop_regs(compiler, 0xde, 0xc8, src1));
 2386: 			break;
 2387: 		case SLJIT_FDIV:
 2388: 			FAIL_IF(emit_fop_regs(compiler, 0xde, 0xf8, src1));
 2389: 			break;
 2390: 		}
 2391: 		return SLJIT_SUCCESS;
 2392: 	}
 2393: 
 2394: 	FAIL_IF(emit_fld(compiler, src1, src1w));
 2395: 
 2396: 	if (src2 >= SLJIT_FLOAT_REG1 && src2 <= SLJIT_FLOAT_REG4 && dst == src2) {
 2397: 		switch (op) {
 2398: 		case SLJIT_FADD:
 2399: 			FAIL_IF(emit_fop_regs(compiler, 0xde, 0xc0, src2));
 2400: 			break;
 2401: 		case SLJIT_FSUB:
 2402: 			FAIL_IF(emit_fop_regs(compiler, 0xde, 0xe0, src2));
 2403: 			break;
 2404: 		case SLJIT_FMUL:
 2405: 			FAIL_IF(emit_fop_regs(compiler, 0xde, 0xc8, src2));
 2406: 			break;
 2407: 		case SLJIT_FDIV:
 2408: 			FAIL_IF(emit_fop_regs(compiler, 0xde, 0xf0, src2));
 2409: 			break;
 2410: 		}
 2411: 		return SLJIT_SUCCESS;
 2412: 	}
 2413: 
 2414: 	switch (op) {
 2415: 	case SLJIT_FADD:
 2416: 		FAIL_IF(emit_fop(compiler, 0xd8, 0xc0, 0xdc, 0x0 << 3, src2, src2w));
 2417: 		break;
 2418: 	case SLJIT_FSUB:
 2419: 		FAIL_IF(emit_fop(compiler, 0xd8, 0xe0, 0xdc, 0x4 << 3, src2, src2w));
 2420: 		break;
 2421: 	case SLJIT_FMUL:
 2422: 		FAIL_IF(emit_fop(compiler, 0xd8, 0xc8, 0xdc, 0x1 << 3, src2, src2w));
 2423: 		break;
 2424: 	case SLJIT_FDIV:
 2425: 		FAIL_IF(emit_fop(compiler, 0xd8, 0xf0, 0xdc, 0x6 << 3, src2, src2w));
 2426: 		break;
 2427: 	}
 2428: 
 2429: 	FAIL_IF(emit_fop(compiler, 0xdd, 0xd8, 0xdd, 0x3 << 3, dst, dstw));
 2430: 
 2431: 	return SLJIT_SUCCESS;
 2432: }
 2433: #endif
 2434: 
 2435: #if (defined SLJIT_SSE2_AUTO && SLJIT_SSE2_AUTO)
 2436: 
 2437: SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_fop1(struct sljit_compiler *compiler, int op,
 2438: 	int dst, sljit_w dstw,
 2439: 	int src, sljit_w srcw)
 2440: {
 2441: 	if (sse2_available)
 2442: 		return sljit_emit_sse2_fop1(compiler, op, dst, dstw, src, srcw);
 2443: 	else
 2444: 		return sljit_emit_fpu_fop1(compiler, op, dst, dstw, src, srcw);
 2445: }
 2446: 
 2447: SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_fop2(struct sljit_compiler *compiler, int op,
 2448: 	int dst, sljit_w dstw,
 2449: 	int src1, sljit_w src1w,
 2450: 	int src2, sljit_w src2w)
 2451: {
 2452: 	if (sse2_available)
 2453: 		return sljit_emit_sse2_fop2(compiler, op, dst, dstw, src1, src1w, src2, src2w);
 2454: 	else
 2455: 		return sljit_emit_fpu_fop2(compiler, op, dst, dstw, src1, src1w, src2, src2w);
 2456: }
 2457: 
 2458: #endif
 2459: 
 2460: /* --------------------------------------------------------------------- */
 2461: /*  Conditional instructions                                             */
 2462: /* --------------------------------------------------------------------- */
 2463: 
 2464: SLJIT_API_FUNC_ATTRIBUTE struct sljit_label* sljit_emit_label(struct sljit_compiler *compiler)
 2465: {
 2466: 	sljit_ub *buf;
 2467: 	struct sljit_label *label;
 2468: 
 2469: 	CHECK_ERROR_PTR();
 2470: 	check_sljit_emit_label(compiler);
 2471: 
 2472: 	/* We should restore the flags before the label,
 2473: 	   since other taken jumps has their own flags as well. */
 2474: 	if (SLJIT_UNLIKELY(compiler->flags_saved))
 2475: 		PTR_FAIL_IF(emit_restore_flags(compiler, 0));
 2476: 
 2477: 	if (compiler->last_label && compiler->last_label->size == compiler->size)
 2478: 		return compiler->last_label;
 2479: 
 2480: 	label = (struct sljit_label*)ensure_abuf(compiler, sizeof(struct sljit_label));
 2481: 	PTR_FAIL_IF(!label);
 2482: 	set_label(label, compiler);
 2483: 
 2484: 	buf = (sljit_ub*)ensure_buf(compiler, 2);
 2485: 	PTR_FAIL_IF(!buf);
 2486: 
 2487: 	*buf++ = 0;
 2488: 	*buf++ = 0;
 2489: 
 2490: 	return label;
 2491: }
 2492: 
 2493: SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_jump(struct sljit_compiler *compiler, int type)
 2494: {
 2495: 	sljit_ub *buf;
 2496: 	struct sljit_jump *jump;
 2497: 
 2498: 	CHECK_ERROR_PTR();
 2499: 	check_sljit_emit_jump(compiler, type);
 2500: 
 2501: 	if (SLJIT_UNLIKELY(compiler->flags_saved)) {
 2502: 		if ((type & 0xff) <= SLJIT_JUMP)
 2503: 			PTR_FAIL_IF(emit_restore_flags(compiler, 0));
 2504: 		compiler->flags_saved = 0;
 2505: 	}
 2506: 
 2507: 	jump = (struct sljit_jump*)ensure_abuf(compiler, sizeof(struct sljit_jump));
 2508: 	PTR_FAIL_IF_NULL(jump);
 2509: 	set_jump(jump, compiler, type & SLJIT_REWRITABLE_JUMP);
 2510: 	type &= 0xff;
 2511: 
 2512: 	if (type >= SLJIT_CALL1)
 2513: 		PTR_FAIL_IF(call_with_args(compiler, type));
 2514: 
 2515: 	/* Worst case size. */
 2516: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 2517: 	compiler->size += (type >= SLJIT_JUMP) ? 5 : 6;
 2518: #else
 2519: 	compiler->size += (type >= SLJIT_JUMP) ? (10 + 3) : (2 + 10 + 3);
 2520: #endif
 2521: 
 2522: 	buf = (sljit_ub*)ensure_buf(compiler, 2);
 2523: 	PTR_FAIL_IF_NULL(buf);
 2524: 
 2525: 	*buf++ = 0;
 2526: 	*buf++ = type + 4;
 2527: 	return jump;
 2528: }
 2529: 
 2530: SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_ijump(struct sljit_compiler *compiler, int type, int src, sljit_w srcw)
 2531: {
 2532: 	sljit_ub *code;
 2533: 	struct sljit_jump *jump;
 2534: 
 2535: 	CHECK_ERROR();
 2536: 	check_sljit_emit_ijump(compiler, type, src, srcw);
 2537: 
 2538: 	CHECK_EXTRA_REGS(src, srcw, (void)0);
 2539: 	if (SLJIT_UNLIKELY(compiler->flags_saved)) {
 2540: 		if (type <= SLJIT_JUMP)
 2541: 			FAIL_IF(emit_restore_flags(compiler, 0));
 2542: 		compiler->flags_saved = 0;
 2543: 	}
 2544: 
 2545: 	if (type >= SLJIT_CALL1) {
 2546: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 2547: #if (defined SLJIT_X86_32_FASTCALL && SLJIT_X86_32_FASTCALL)
 2548: 		if (src == SLJIT_TEMPORARY_REG3) {
 2549: 			EMIT_MOV(compiler, TMP_REGISTER, 0, src, 0);
 2550: 			src = TMP_REGISTER;
 2551: 		}
 2552: 		if ((src & SLJIT_MEM) && (src & 0xf) == SLJIT_LOCALS_REG && type >= SLJIT_CALL3) {
 2553: 			if (src & 0xf0) {
 2554: 				EMIT_MOV(compiler, TMP_REGISTER, 0, src, srcw);
 2555: 				src = TMP_REGISTER;
 2556: 			}
 2557: 			else
 2558: 				srcw += sizeof(sljit_w);
 2559: 		}
 2560: #else
 2561: 		if ((src & SLJIT_MEM) && (src & 0xf) == SLJIT_LOCALS_REG) {
 2562: 			if (src & 0xf0) {
 2563: 				EMIT_MOV(compiler, TMP_REGISTER, 0, src, srcw);
 2564: 				src = TMP_REGISTER;
 2565: 			}
 2566: 			else
 2567: 				srcw += sizeof(sljit_w) * (type - SLJIT_CALL0);
 2568: 		}
 2569: #endif
 2570: #endif
 2571: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64) && defined(_WIN64)
 2572: 		if (src == SLJIT_TEMPORARY_REG3) {
 2573: 			EMIT_MOV(compiler, TMP_REGISTER, 0, src, 0);
 2574: 			src = TMP_REGISTER;
 2575: 		}
 2576: #endif
 2577: 		FAIL_IF(call_with_args(compiler, type));
 2578: 	}
 2579: 
 2580: 	if (src == SLJIT_IMM) {
 2581: 		jump = (struct sljit_jump*)ensure_abuf(compiler, sizeof(struct sljit_jump));
 2582: 		FAIL_IF_NULL(jump);
 2583: 		set_jump(jump, compiler, JUMP_ADDR);
 2584: 		jump->u.target = srcw;
 2585: 
 2586: 		/* Worst case size. */
 2587: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 2588: 		compiler->size += 5;
 2589: #else
 2590: 		compiler->size += 10 + 3;
 2591: #endif
 2592: 
 2593: 		code = (sljit_ub*)ensure_buf(compiler, 2);
 2594: 		FAIL_IF_NULL(code);
 2595: 
 2596: 		*code++ = 0;
 2597: 		*code++ = type + 4;
 2598: 	}
 2599: 	else {
 2600: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 2601: 		/* REX_W is not necessary (src is not immediate). */
 2602: 		compiler->mode32 = 1;
 2603: #endif
 2604: 		code = emit_x86_instruction(compiler, 1, 0, 0, src, srcw);
 2605: 		FAIL_IF(!code);
 2606: 		*code++ = 0xff;
 2607: 		*code |= (type >= SLJIT_FAST_CALL) ? (2 << 3) : (4 << 3);
 2608: 	}
 2609: 	return SLJIT_SUCCESS;
 2610: }
 2611: 
 2612: SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_cond_value(struct sljit_compiler *compiler, int op, int dst, sljit_w dstw, int type)
 2613: {
 2614: 	sljit_ub *buf;
 2615: 	sljit_ub cond_set = 0;
 2616: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 2617: 	int reg;
 2618: #endif
 2619: 
 2620: 	CHECK_ERROR();
 2621: 	check_sljit_emit_cond_value(compiler, op, dst, dstw, type);
 2622: 
 2623: 	if (dst == SLJIT_UNUSED)
 2624: 		return SLJIT_SUCCESS;
 2625: 
 2626: 	CHECK_EXTRA_REGS(dst, dstw, (void)0);
 2627: 	if (SLJIT_UNLIKELY(compiler->flags_saved))
 2628: 		FAIL_IF(emit_restore_flags(compiler, 0));
 2629: 
 2630: 	switch (type) {
 2631: 	case SLJIT_C_EQUAL:
 2632: 	case SLJIT_C_FLOAT_EQUAL:
 2633: 		cond_set = 0x94;
 2634: 		break;
 2635: 
 2636: 	case SLJIT_C_NOT_EQUAL:
 2637: 	case SLJIT_C_FLOAT_NOT_EQUAL:
 2638: 		cond_set = 0x95;
 2639: 		break;
 2640: 
 2641: 	case SLJIT_C_LESS:
 2642: 	case SLJIT_C_FLOAT_LESS:
 2643: 		cond_set = 0x92;
 2644: 		break;
 2645: 
 2646: 	case SLJIT_C_GREATER_EQUAL:
 2647: 	case SLJIT_C_FLOAT_GREATER_EQUAL:
 2648: 		cond_set = 0x93;
 2649: 		break;
 2650: 
 2651: 	case SLJIT_C_GREATER:
 2652: 	case SLJIT_C_FLOAT_GREATER:
 2653: 		cond_set = 0x97;
 2654: 		break;
 2655: 
 2656: 	case SLJIT_C_LESS_EQUAL:
 2657: 	case SLJIT_C_FLOAT_LESS_EQUAL:
 2658: 		cond_set = 0x96;
 2659: 		break;
 2660: 
 2661: 	case SLJIT_C_SIG_LESS:
 2662: 		cond_set = 0x9c;
 2663: 		break;
 2664: 
 2665: 	case SLJIT_C_SIG_GREATER_EQUAL:
 2666: 		cond_set = 0x9d;
 2667: 		break;
 2668: 
 2669: 	case SLJIT_C_SIG_GREATER:
 2670: 		cond_set = 0x9f;
 2671: 		break;
 2672: 
 2673: 	case SLJIT_C_SIG_LESS_EQUAL:
 2674: 		cond_set = 0x9e;
 2675: 		break;
 2676: 
 2677: 	case SLJIT_C_OVERFLOW:
 2678: 	case SLJIT_C_MUL_OVERFLOW:
 2679: 		cond_set = 0x90;
 2680: 		break;
 2681: 
 2682: 	case SLJIT_C_NOT_OVERFLOW:
 2683: 	case SLJIT_C_MUL_NOT_OVERFLOW:
 2684: 		cond_set = 0x91;
 2685: 		break;
 2686: 
 2687: 	case SLJIT_C_FLOAT_NAN:
 2688: 		cond_set = 0x9a;
 2689: 		break;
 2690: 
 2691: 	case SLJIT_C_FLOAT_NOT_NAN:
 2692: 		cond_set = 0x9b;
 2693: 		break;
 2694: 	}
 2695: 
 2696: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 2697: 	reg = (op == SLJIT_MOV && dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) ? dst : TMP_REGISTER;
 2698: 
 2699: 	buf = (sljit_ub*)ensure_buf(compiler, 1 + 4 + 4);
 2700: 	FAIL_IF(!buf);
 2701: 	INC_SIZE(4 + 4);
 2702: 	/* Set low register to conditional flag. */
 2703: 	*buf++ = (reg_map[reg] <= 7) ? 0x40 : REX_B;
 2704: 	*buf++ = 0x0f;
 2705: 	*buf++ = cond_set;
 2706: 	*buf++ = 0xC0 | reg_lmap[reg];
 2707: 	*buf++ = REX_W | (reg_map[reg] <= 7 ? 0 : (REX_B | REX_R));
 2708: 	*buf++ = 0x0f;
 2709: 	*buf++ = 0xb6;
 2710: 	*buf = 0xC0 | (reg_lmap[reg] << 3) | reg_lmap[reg];
 2711: 
 2712: 	if (reg == TMP_REGISTER) {
 2713: 		if (op == SLJIT_MOV) {
 2714: 			compiler->mode32 = 0;
 2715: 			EMIT_MOV(compiler, dst, dstw, TMP_REGISTER, 0);
 2716: 		}
 2717: 		else {
 2718: #if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG)
 2719: 			compiler->skip_checks = 1;
 2720: #endif
 2721: 			return sljit_emit_op2(compiler, op, dst, dstw, dst, dstw, TMP_REGISTER, 0);
 2722: 		}
 2723: 	}
 2724: #else
 2725: 	if (op == SLJIT_MOV) {
 2726: 		if (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_TEMPORARY_REG3) {
 2727: 			buf = (sljit_ub*)ensure_buf(compiler, 1 + 3 + 3);
 2728: 			FAIL_IF(!buf);
 2729: 			INC_SIZE(3 + 3);
 2730: 			/* Set low byte to conditional flag. */
 2731: 			*buf++ = 0x0f;
 2732: 			*buf++ = cond_set;
 2733: 			*buf++ = 0xC0 | reg_map[dst];
 2734: 
 2735: 			*buf++ = 0x0f;
 2736: 			*buf++ = 0xb6;
 2737: 			*buf = 0xC0 | (reg_map[dst] << 3) | reg_map[dst];
 2738: 		}
 2739: 		else {
 2740: 			EMIT_MOV(compiler, TMP_REGISTER, 0, SLJIT_TEMPORARY_REG1, 0);
 2741: 
 2742: 			buf = (sljit_ub*)ensure_buf(compiler, 1 + 3 + 3);
 2743: 			FAIL_IF(!buf);
 2744: 			INC_SIZE(3 + 3);
 2745: 			/* Set al to conditional flag. */
 2746: 			*buf++ = 0x0f;
 2747: 			*buf++ = cond_set;
 2748: 			*buf++ = 0xC0;
 2749: 
 2750: 			*buf++ = 0x0f;
 2751: 			*buf++ = 0xb6;
 2752: 			if (dst >= SLJIT_SAVED_REG1 && dst <= SLJIT_NO_REGISTERS)
 2753: 				*buf = 0xC0 | (reg_map[dst] << 3);
 2754: 			else {
 2755: 				*buf = 0xC0;
 2756: 				EMIT_MOV(compiler, dst, dstw, SLJIT_TEMPORARY_REG1, 0);
 2757: 			}
 2758: 
 2759: 			EMIT_MOV(compiler, SLJIT_TEMPORARY_REG1, 0, TMP_REGISTER, 0);
 2760: 		}
 2761: 	}
 2762: 	else {
 2763: 		if (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_TEMPORARY_REG3) {
 2764: 			EMIT_MOV(compiler, TMP_REGISTER, 0, dst, 0);
 2765: 			buf = (sljit_ub*)ensure_buf(compiler, 1 + 3);
 2766: 			FAIL_IF(!buf);
 2767: 			INC_SIZE(3);
 2768: 
 2769: 			*buf++ = 0x0f;
 2770: 			*buf++ = cond_set;
 2771: 			*buf++ = 0xC0 | reg_map[dst];
 2772: 		}
 2773: 		else {
 2774: 			EMIT_MOV(compiler, TMP_REGISTER, 0, SLJIT_TEMPORARY_REG1, 0);
 2775: 
 2776: 			buf = (sljit_ub*)ensure_buf(compiler, 1 + 3 + 3 + 1);
 2777: 			FAIL_IF(!buf);
 2778: 			INC_SIZE(3 + 3 + 1);
 2779: 			/* Set al to conditional flag. */
 2780: 			*buf++ = 0x0f;
 2781: 			*buf++ = cond_set;
 2782: 			*buf++ = 0xC0;
 2783: 
 2784: 			*buf++ = 0x0f;
 2785: 			*buf++ = 0xb6;
 2786: 			*buf++ = 0xC0;
 2787: 
 2788: 			*buf++ = 0x90 + reg_map[TMP_REGISTER];
 2789: 		}
 2790: #if (defined SLJIT_VERBOSE && SLJIT_VERBOSE) || (defined SLJIT_DEBUG && SLJIT_DEBUG)
 2791: 		compiler->skip_checks = 1;
 2792: #endif
 2793: 		return sljit_emit_op2(compiler, op, dst, dstw, dst, dstw, TMP_REGISTER, 0);
 2794: 	}
 2795: #endif
 2796: 
 2797: 	return SLJIT_SUCCESS;
 2798: }
 2799: 
 2800: SLJIT_API_FUNC_ATTRIBUTE struct sljit_const* sljit_emit_const(struct sljit_compiler *compiler, int dst, sljit_w dstw, sljit_w init_value)
 2801: {
 2802: 	sljit_ub *buf;
 2803: 	struct sljit_const *const_;
 2804: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 2805: 	int reg;
 2806: #endif
 2807: 
 2808: 	CHECK_ERROR_PTR();
 2809: 	check_sljit_emit_const(compiler, dst, dstw, init_value);
 2810: 
 2811: 	CHECK_EXTRA_REGS(dst, dstw, (void)0);
 2812: 
 2813: 	const_ = (struct sljit_const*)ensure_abuf(compiler, sizeof(struct sljit_const));
 2814: 	PTR_FAIL_IF(!const_);
 2815: 	set_const(const_, compiler);
 2816: 
 2817: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 2818: 	compiler->mode32 = 0;
 2819: 	reg = (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) ? dst : TMP_REGISTER;
 2820: 
 2821: 	if (emit_load_imm64(compiler, reg, init_value))
 2822: 		return NULL;
 2823: #else
 2824: 	if (dst == SLJIT_UNUSED)
 2825: 		dst = TMP_REGISTER;
 2826: 
 2827: 	if (emit_mov(compiler, dst, dstw, SLJIT_IMM, init_value))
 2828: 		return NULL;
 2829: #endif
 2830: 
 2831: 	buf = (sljit_ub*)ensure_buf(compiler, 2);
 2832: 	PTR_FAIL_IF(!buf);
 2833: 
 2834: 	*buf++ = 0;
 2835: 	*buf++ = 1;
 2836: 
 2837: #if (defined SLJIT_CONFIG_X86_64 && SLJIT_CONFIG_X86_64)
 2838: 	if (reg == TMP_REGISTER && dst != SLJIT_UNUSED)
 2839: 		if (emit_mov(compiler, dst, dstw, TMP_REGISTER, 0))
 2840: 			return NULL;
 2841: #endif
 2842: 
 2843: 	return const_;
 2844: }
 2845: 
 2846: SLJIT_API_FUNC_ATTRIBUTE void sljit_set_jump_addr(sljit_uw addr, sljit_uw new_addr)
 2847: {
 2848: #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 2849: 	*(sljit_w*)addr = new_addr - (addr + 4);
 2850: #else
 2851: 	*(sljit_uw*)addr = new_addr;
 2852: #endif
 2853: }
 2854: 
 2855: SLJIT_API_FUNC_ATTRIBUTE void sljit_set_const(sljit_uw addr, sljit_w new_constant)
 2856: {
 2857: 	*(sljit_w*)addr = new_constant;
 2858: }

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>