165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich/* 265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * Stack-less Just-In-Time compiler 365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * 465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * Copyright 2013-2013 Tilera Corporation(jiwang@tilera.com). All rights reserved. 565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * Copyright 2009-2012 Zoltan Herczeg (hzmester@freemail.hu). All rights reserved. 665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * 765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * Redistribution and use in source and binary forms, with or without modification, are 865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * permitted provided that the following conditions are met: 965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * 1065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * 1. Redistributions of source code must retain the above copyright notice, this list of 1165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * conditions and the following disclaimer. 1265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * 1365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * 2. Redistributions in binary form must reproduce the above copyright notice, this list 1465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * of conditions and the following disclaimer in the documentation and/or other materials 1565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * provided with the distribution. 1665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * 1765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER(S) AND CONTRIBUTORS ``AS IS'' AND ANY 1865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 1965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT 2065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * SHALL THE COPYRIGHT HOLDER(S) OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 2165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 2265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR 2365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 2465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN 2565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 2665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich */ 2765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 2865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich/* TileGX architecture. */ 2965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich/* Contributed by Tilera Corporation. */ 3065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#include "sljitNativeTILEGX-encoder.c" 3165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 3265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SIMM_8BIT_MAX (0x7f) 3365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SIMM_8BIT_MIN (-0x80) 3465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SIMM_16BIT_MAX (0x7fff) 3565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SIMM_16BIT_MIN (-0x8000) 3665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SIMM_17BIT_MAX (0xffff) 3765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SIMM_17BIT_MIN (-0x10000) 3865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SIMM_32BIT_MIN (-0x80000000) 3965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SIMM_32BIT_MAX (0x7fffffff) 4065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SIMM_48BIT_MIN (0x800000000000L) 4165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SIMM_48BIT_MAX (0x7fffffff0000L) 4265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define IMM16(imm) ((imm) & 0xffff) 4365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 4465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define UIMM_16BIT_MAX (0xffff) 4565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 4665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define TMP_REG1 (SLJIT_NO_REGISTERS + 1) 4765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define TMP_REG2 (SLJIT_NO_REGISTERS + 2) 4865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define TMP_REG3 (SLJIT_NO_REGISTERS + 3) 4965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ADDR_TMP (SLJIT_NO_REGISTERS + 4) 5065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define PIC_ADDR_REG TMP_REG2 5165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 5265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic SLJIT_CONST sljit_ub reg_map[SLJIT_NO_REGISTERS + 5] = { 5365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 63, 0, 1, 2, 3, 4, 30, 31, 32, 33, 34, 54, 5, 16, 6, 7 5465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich}; 5565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 5665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SLJIT_LOCALS_REG_mapped 54 5765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define TMP_REG1_mapped 5 5865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define TMP_REG2_mapped 16 5965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define TMP_REG3_mapped 6 6065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ADDR_TMP_mapped 7 6165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SLJIT_SAVED_REG1_mapped 30 6265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SLJIT_SAVED_REG2_mapped 31 6365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SLJIT_SAVED_REG3_mapped 32 6465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SLJIT_SAVED_EREG1_mapped 33 6565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SLJIT_SAVED_EREG2_mapped 34 6665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 6765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich/* Flags are keept in volatile registers. */ 6865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define EQUAL_FLAG 8 6965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich/* And carry flag as well. */ 7065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ULESS_FLAG 9 7165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define UGREATER_FLAG 10 7265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define LESS_FLAG 11 7365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define GREATER_FLAG 12 7465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define OVERFLOW_FLAG 13 7565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 7665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ZERO 63 7765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define RA 55 7865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define TMP_EREG1 14 7965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define TMP_EREG2 15 8065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 8165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define LOAD_DATA 0x01 8265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define WORD_DATA 0x00 8365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BYTE_DATA 0x02 8465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define HALF_DATA 0x04 8565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define INT_DATA 0x06 8665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SIGNED_DATA 0x08 8765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define DOUBLE_DATA 0x10 8865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 8965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich/* Separates integer and floating point registers */ 9065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define GPR_REG 0xf 9165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 9265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define MEM_MASK 0x1f 9365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 9465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define WRITE_BACK 0x00020 9565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ARG_TEST 0x00040 9665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ALT_KEEP_CACHE 0x00080 9765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CUMULATIVE_OP 0x00100 9865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define LOGICAL_OP 0x00200 9965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define IMM_OP 0x00400 10065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SRC2_IMM 0x00800 10165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 10265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define UNUSED_DEST 0x01000 10365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define REG_DEST 0x02000 10465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define REG1_SOURCE 0x04000 10565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define REG2_SOURCE 0x08000 10665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SLOW_SRC1 0x10000 10765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SLOW_SRC2 0x20000 10865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SLOW_DEST 0x40000 10965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 11065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich/* Only these flags are set. UNUSED_DEST is not set when no flags should be set. 11165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich */ 11265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CHECK_FLAGS(list) (!(flags & UNUSED_DEST) || (op & GET_FLAGS(~(list)))) 11365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 11465de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE SLJIT_CONST char *sljit_get_platform_name(void) 11565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 11665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return "TileGX" SLJIT_CPUINFO; 11765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 11865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 11965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich/* Length of an instruction word */ 12065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichtypedef sljit_uw sljit_ins; 12165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 12265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstruct jit_instr { 12365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const struct tilegx_opcode* opcode; 12465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich tilegx_pipeline pipe; 12565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich unsigned long input_registers; 12665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich unsigned long output_registers; 12765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich int operand_value[4]; 12865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich int line; 12965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich}; 13065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 13165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich/* Opcode Helper Macros */ 13265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define TILEGX_X_MODE 0 13365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 13465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define X_MODE create_Mode(TILEGX_X_MODE) 13565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 13665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define FNOP_X0 \ 13765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Opcode_X0(RRR_0_OPCODE_X0) | \ 13865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X0(UNARY_RRR_0_OPCODE_X0) | \ 13965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_UnaryOpcodeExtension_X0(FNOP_UNARY_OPCODE_X0) 14065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 14165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define FNOP_X1 \ 14265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Opcode_X1(RRR_0_OPCODE_X1) | \ 14365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(UNARY_RRR_0_OPCODE_X1) | \ 14465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_UnaryOpcodeExtension_X1(FNOP_UNARY_OPCODE_X1) 14565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 14665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define NOP \ 14765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | FNOP_X0 | FNOP_X1 14865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 14965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ANOP_X0 \ 15065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Opcode_X0(RRR_0_OPCODE_X0) | \ 15165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X0(UNARY_RRR_0_OPCODE_X0) | \ 15265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_UnaryOpcodeExtension_X0(NOP_UNARY_OPCODE_X0) 15365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 15465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BPT create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 15565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(UNARY_RRR_0_OPCODE_X1) | \ 15665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_UnaryOpcodeExtension_X1(ILL_UNARY_OPCODE_X1) | \ 15765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Dest_X1(0x1C) | create_SrcA_X1(0x25) | ANOP_X0 15865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 15965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ADD_X1 \ 16065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 16165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(ADD_RRR_0_OPCODE_X1) | FNOP_X0 16265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 16365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ADDI_X1 \ 16465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(IMM8_OPCODE_X1) | \ 16565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Imm8OpcodeExtension_X1(ADDI_IMM8_OPCODE_X1) | FNOP_X0 16665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 16765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SUB_X1 \ 16865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 16965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(SUB_RRR_0_OPCODE_X1) | FNOP_X0 17065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 17165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define NOR_X1 \ 17265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 17365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(NOR_RRR_0_OPCODE_X1) | FNOP_X0 17465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 17565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define OR_X1 \ 17665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 17765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(OR_RRR_0_OPCODE_X1) | FNOP_X0 17865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 17965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define AND_X1 \ 18065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 18165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(AND_RRR_0_OPCODE_X1) | FNOP_X0 18265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 18365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define XOR_X1 \ 18465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 18565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(XOR_RRR_0_OPCODE_X1) | FNOP_X0 18665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 18765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CMOVNEZ_X0 \ 18865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X0(RRR_0_OPCODE_X0) | \ 18965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X0(CMOVNEZ_RRR_0_OPCODE_X0) | FNOP_X1 19065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 19165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CMOVEQZ_X0 \ 19265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X0(RRR_0_OPCODE_X0) | \ 19365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X0(CMOVEQZ_RRR_0_OPCODE_X0) | FNOP_X1 19465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 19565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ADDLI_X1 \ 19665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(ADDLI_OPCODE_X1) | FNOP_X0 19765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 19865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define V4INT_L_X1 \ 19965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 20065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(V4INT_L_RRR_0_OPCODE_X1) | FNOP_X0 20165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 20265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BFEXTU_X0 \ 20365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X0(BF_OPCODE_X0) | \ 20465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_BFOpcodeExtension_X0(BFEXTU_BF_OPCODE_X0) | FNOP_X1 20565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 20665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BFEXTS_X0 \ 20765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X0(BF_OPCODE_X0) | \ 20865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_BFOpcodeExtension_X0(BFEXTS_BF_OPCODE_X0) | FNOP_X1 20965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 21065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SHL16INSLI_X1 \ 21165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(SHL16INSLI_OPCODE_X1) | FNOP_X0 21265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 21365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ST_X1 \ 21465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 21565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(ST_RRR_0_OPCODE_X1) | create_Dest_X1(0x0) | FNOP_X0 21665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 21765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define LD_X1 \ 21865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 21965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(UNARY_RRR_0_OPCODE_X1) | \ 22065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_UnaryOpcodeExtension_X1(LD_UNARY_OPCODE_X1) | FNOP_X0 22165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 22265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define JR_X1 \ 22365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 22465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(UNARY_RRR_0_OPCODE_X1) | \ 22565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_UnaryOpcodeExtension_X1(JR_UNARY_OPCODE_X1) | FNOP_X0 22665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 22765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define JALR_X1 \ 22865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 22965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(UNARY_RRR_0_OPCODE_X1) | \ 23065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_UnaryOpcodeExtension_X1(JALR_UNARY_OPCODE_X1) | FNOP_X0 23165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 23265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CLZ_X0 \ 23365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X0(RRR_0_OPCODE_X0) | \ 23465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X0(UNARY_RRR_0_OPCODE_X0) | \ 23565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_UnaryOpcodeExtension_X0(CNTLZ_UNARY_OPCODE_X0) | FNOP_X1 23665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 23765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CMPLTUI_X1 \ 23865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(IMM8_OPCODE_X1) | \ 23965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Imm8OpcodeExtension_X1(CMPLTUI_IMM8_OPCODE_X1) | FNOP_X0 24065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 24165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CMPLTU_X1 \ 24265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 24365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(CMPLTU_RRR_0_OPCODE_X1) | FNOP_X0 24465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 24565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CMPLTS_X1 \ 24665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 24765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(CMPLTS_RRR_0_OPCODE_X1) | FNOP_X0 24865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 24965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define XORI_X1 \ 25065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(IMM8_OPCODE_X1) | \ 25165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Imm8OpcodeExtension_X1(XORI_IMM8_OPCODE_X1) | FNOP_X0 25265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 25365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ORI_X1 \ 25465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(IMM8_OPCODE_X1) | \ 25565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Imm8OpcodeExtension_X1(ORI_IMM8_OPCODE_X1) | FNOP_X0 25665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 25765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ANDI_X1 \ 25865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(IMM8_OPCODE_X1) | \ 25965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Imm8OpcodeExtension_X1(ANDI_IMM8_OPCODE_X1) | FNOP_X0 26065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 26165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SHLI_X1 \ 26265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(SHIFT_OPCODE_X1) | \ 26365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_ShiftOpcodeExtension_X1(SHLI_SHIFT_OPCODE_X1) | FNOP_X0 26465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 26565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SHL_X1 \ 26665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 26765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(SHL_RRR_0_OPCODE_X1) | FNOP_X0 26865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 26965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SHRSI_X1 \ 27065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(SHIFT_OPCODE_X1) | \ 27165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_ShiftOpcodeExtension_X1(SHRSI_SHIFT_OPCODE_X1) | FNOP_X0 27265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 27365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SHRS_X1 \ 27465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 27565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(SHRS_RRR_0_OPCODE_X1) | FNOP_X0 27665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 27765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SHRUI_X1 \ 27865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(SHIFT_OPCODE_X1) | \ 27965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_ShiftOpcodeExtension_X1(SHRUI_SHIFT_OPCODE_X1) | FNOP_X0 28065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 28165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SHRU_X1 \ 28265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(RRR_0_OPCODE_X1) | \ 28365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_RRROpcodeExtension_X1(SHRU_RRR_0_OPCODE_X1) | FNOP_X0 28465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 28565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BEQZ_X1 \ 28665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(BRANCH_OPCODE_X1) | \ 28765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_BrType_X1(BEQZ_BRANCH_OPCODE_X1) | FNOP_X0 28865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 28965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BNEZ_X1 \ 29065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(BRANCH_OPCODE_X1) | \ 29165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_BrType_X1(BNEZ_BRANCH_OPCODE_X1) | FNOP_X0 29265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 29365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define J_X1 \ 29465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(JUMP_OPCODE_X1) | \ 29565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_JumpOpcodeExtension_X1(J_JUMP_OPCODE_X1) | FNOP_X0 29665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 29765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define JAL_X1 \ 29865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_Mode(TILEGX_X_MODE) | create_Opcode_X1(JUMP_OPCODE_X1) | \ 29965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich create_JumpOpcodeExtension_X1(JAL_JUMP_OPCODE_X1) | FNOP_X0 30065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 30165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define DEST_X0(x) create_Dest_X0(x) 30265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SRCA_X0(x) create_SrcA_X0(x) 30365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SRCB_X0(x) create_SrcB_X0(x) 30465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define DEST_X1(x) create_Dest_X1(x) 30565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SRCA_X1(x) create_SrcA_X1(x) 30665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SRCB_X1(x) create_SrcB_X1(x) 30765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define IMM16_X1(x) create_Imm16_X1(x) 30865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define IMM8_X1(x) create_Imm8_X1(x) 30965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BFSTART_X0(x) create_BFStart_X0(x) 31065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BFEND_X0(x) create_BFEnd_X0(x) 31165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SHIFTIMM_X1(x) create_ShAmt_X1(x) 31265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define JOFF_X1(x) create_JumpOff_X1(x) 31365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BOFF_X1(x) create_BrOff_X1(x) 31465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 31565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic SLJIT_CONST tilegx_mnemonic data_transfer_insts[16] = { 31665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* u w s */ TILEGX_OPC_ST /* st */, 31765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* u w l */ TILEGX_OPC_LD /* ld */, 31865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* u b s */ TILEGX_OPC_ST1 /* st1 */, 31965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* u b l */ TILEGX_OPC_LD1U /* ld1u */, 32065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* u h s */ TILEGX_OPC_ST2 /* st2 */, 32165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* u h l */ TILEGX_OPC_LD2U /* ld2u */, 32265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* u i s */ TILEGX_OPC_ST4 /* st4 */, 32365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* u i l */ TILEGX_OPC_LD4U /* ld4u */, 32465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* s w s */ TILEGX_OPC_ST /* st */, 32565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* s w l */ TILEGX_OPC_LD /* ld */, 32665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* s b s */ TILEGX_OPC_ST1 /* st1 */, 32765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* s b l */ TILEGX_OPC_LD1S /* ld1s */, 32865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* s h s */ TILEGX_OPC_ST2 /* st2 */, 32965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* s h l */ TILEGX_OPC_LD2S /* ld2s */, 33065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* s i s */ TILEGX_OPC_ST4 /* st4 */, 33165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* s i l */ TILEGX_OPC_LD4S /* ld4s */, 33265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich}; 33365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 33465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 33565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si push_inst_debug(struct sljit_compiler *compiler, sljit_ins ins, int line) 33665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 33765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins *ptr = (sljit_ins *)ensure_buf(compiler, sizeof(sljit_ins)); 33865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(!ptr); 33965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich *ptr = ins; 34065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->size++; 34165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("|%04d|S0|:\t\t", line); 34265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich print_insn_tilegx(ptr); 34365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 34465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 34565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 34665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si push_inst_nodebug(struct sljit_compiler *compiler, sljit_ins ins) 34765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 34865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins *ptr = (sljit_ins *)ensure_buf(compiler, sizeof(sljit_ins)); 34965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(!ptr); 35065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich *ptr = ins; 35165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->size++; 35265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 35365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 35465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 35565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define push_inst(a, b) push_inst_debug(a, b, __LINE__) 35665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#else 35765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si push_inst(struct sljit_compiler *compiler, sljit_ins ins) 35865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 35965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins *ptr = (sljit_ins *)ensure_buf(compiler, sizeof(sljit_ins)); 36065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(!ptr); 36165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich *ptr = ins; 36265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->size++; 36365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 36465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 36565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 36665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 36765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BUNDLE_FORMAT_MASK(p0, p1, p2) \ 36865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ((p0) | ((p1) << 8) | ((p2) << 16)) 36965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 37065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BUNDLE_FORMAT(p0, p1, p2) \ 37165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich { \ 37265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich { \ 37365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich (tilegx_pipeline)(p0), \ 37465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich (tilegx_pipeline)(p1), \ 37565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich (tilegx_pipeline)(p2) \ 37665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich }, \ 37765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BUNDLE_FORMAT_MASK(1 << (p0), 1 << (p1), (1 << (p2))) \ 37865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 37965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 38065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define NO_PIPELINE TILEGX_NUM_PIPELINE_ENCODINGS 38165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 38265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define tilegx_is_x_pipeline(p) ((int)(p) <= (int)TILEGX_PIPELINE_X1) 38365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 38465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define PI(encoding) \ 38565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_inst(compiler, encoding) 38665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 38765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define PB3(opcode, dst, srca, srcb) \ 38865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, opcode, dst, srca, srcb, __LINE__) 38965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 39065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define PB2(opcode, dst, src) \ 39165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_2_buffer(compiler, opcode, dst, src, __LINE__) 39265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 39365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define JR(reg) \ 39465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_jr_buffer(compiler, TILEGX_OPC_JR, reg, __LINE__) 39565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 39665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ADD(dst, srca, srcb) \ 39765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_ADD, dst, srca, srcb, __LINE__) 39865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 39965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SUB(dst, srca, srcb) \ 40065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_SUB, dst, srca, srcb, __LINE__) 40165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 40265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define NOR(dst, srca, srcb) \ 40365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_NOR, dst, srca, srcb, __LINE__) 40465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 40565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define OR(dst, srca, srcb) \ 40665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_OR, dst, srca, srcb, __LINE__) 40765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 40865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define XOR(dst, srca, srcb) \ 40965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_XOR, dst, srca, srcb, __LINE__) 41065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 41165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define AND(dst, srca, srcb) \ 41265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_AND, dst, srca, srcb, __LINE__) 41365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 41465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CLZ(dst, src) \ 41565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_2_buffer(compiler, TILEGX_OPC_CLZ, dst, src, __LINE__) 41665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 41765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SHLI(dst, srca, srcb) \ 41865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_SHLI, dst, srca, srcb, __LINE__) 41965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 42065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SHRUI(dst, srca, imm) \ 42165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_SHRUI, dst, srca, imm, __LINE__) 42265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 42365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define XORI(dst, srca, imm) \ 42465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_XORI, dst, srca, imm, __LINE__) 42565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 42665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ORI(dst, srca, imm) \ 42765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_ORI, dst, srca, imm, __LINE__) 42865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 42965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CMPLTU(dst, srca, srcb) \ 43065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_CMPLTU, dst, srca, srcb, __LINE__) 43165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 43265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CMPLTS(dst, srca, srcb) \ 43365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_CMPLTS, dst, srca, srcb, __LINE__) 43465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 43565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CMPLTUI(dst, srca, imm) \ 43665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_CMPLTUI, dst, srca, imm, __LINE__) 43765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 43865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CMOVNEZ(dst, srca, srcb) \ 43965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_CMOVNEZ, dst, srca, srcb, __LINE__) 44065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 44165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define CMOVEQZ(dst, srca, srcb) \ 44265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_CMOVEQZ, dst, srca, srcb, __LINE__) 44365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 44465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ADDLI(dst, srca, srcb) \ 44565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_ADDLI, dst, srca, srcb, __LINE__) 44665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 44765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SHL16INSLI(dst, srca, srcb) \ 44865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_SHL16INSLI, dst, srca, srcb, __LINE__) 44965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 45065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define LD_ADD(dst, addr, adjust) \ 45165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_LD_ADD, dst, addr, adjust, __LINE__) 45265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 45365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ST_ADD(src, addr, adjust) \ 45465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_3_buffer(compiler, TILEGX_OPC_ST_ADD, src, addr, adjust, __LINE__) 45565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 45665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define LD(dst, addr) \ 45765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_2_buffer(compiler, TILEGX_OPC_LD, dst, addr, __LINE__) 45865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 45965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BFEXTU(dst, src, start, end) \ 46065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_4_buffer(compiler, TILEGX_OPC_BFEXTU, dst, src, start, end, __LINE__) 46165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 46265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BFEXTS(dst, src, start, end) \ 46365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_4_buffer(compiler, TILEGX_OPC_BFEXTS, dst, src, start, end, __LINE__) 46465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 46565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ADD_SOLO(dest, srca, srcb) \ 46665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_inst(compiler, ADD_X1 | DEST_X1(dest) | SRCA_X1(srca) | SRCB_X1(srcb)) 46765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 46865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ADDI_SOLO(dest, srca, imm) \ 46965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_inst(compiler, ADDI_X1 | DEST_X1(dest) | SRCA_X1(srca) | IMM8_X1(imm)) 47065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 47165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define ADDLI_SOLO(dest, srca, imm) \ 47265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_inst(compiler, ADDLI_X1 | DEST_X1(dest) | SRCA_X1(srca) | IMM16_X1(imm)) 47365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 47465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define SHL16INSLI_SOLO(dest, srca, imm) \ 47565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_inst(compiler, SHL16INSLI_X1 | DEST_X1(dest) | SRCA_X1(srca) | IMM16_X1(imm)) 47665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 47765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define JALR_SOLO(reg) \ 47865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_inst(compiler, JALR_X1 | SRCA_X1(reg)) 47965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 48065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define JR_SOLO(reg) \ 48165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich push_inst(compiler, JR_X1 | SRCA_X1(reg)) 48265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 48365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstruct Format { 48465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Mapping of bundle issue slot to assigned pipe. */ 48565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich tilegx_pipeline pipe[TILEGX_MAX_INSTRUCTIONS_PER_BUNDLE]; 48665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 48765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Mask of pipes used by this bundle. */ 48865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich unsigned int pipe_mask; 48965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich}; 49065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 49165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichconst struct Format formats[] = 49265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 49365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* In Y format we must always have something in Y2, since it has 49465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich * no fnop, so this conveys that Y2 must always be used. */ 49565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BUNDLE_FORMAT(TILEGX_PIPELINE_Y0, TILEGX_PIPELINE_Y2, NO_PIPELINE), 49665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BUNDLE_FORMAT(TILEGX_PIPELINE_Y1, TILEGX_PIPELINE_Y2, NO_PIPELINE), 49765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BUNDLE_FORMAT(TILEGX_PIPELINE_Y2, TILEGX_PIPELINE_Y0, NO_PIPELINE), 49865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BUNDLE_FORMAT(TILEGX_PIPELINE_Y2, TILEGX_PIPELINE_Y1, NO_PIPELINE), 49965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 50065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Y format has three instructions. */ 50165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BUNDLE_FORMAT(TILEGX_PIPELINE_Y0, TILEGX_PIPELINE_Y1, TILEGX_PIPELINE_Y2), 50265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BUNDLE_FORMAT(TILEGX_PIPELINE_Y0, TILEGX_PIPELINE_Y2, TILEGX_PIPELINE_Y1), 50365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BUNDLE_FORMAT(TILEGX_PIPELINE_Y1, TILEGX_PIPELINE_Y0, TILEGX_PIPELINE_Y2), 50465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BUNDLE_FORMAT(TILEGX_PIPELINE_Y1, TILEGX_PIPELINE_Y2, TILEGX_PIPELINE_Y0), 50565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BUNDLE_FORMAT(TILEGX_PIPELINE_Y2, TILEGX_PIPELINE_Y0, TILEGX_PIPELINE_Y1), 50665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BUNDLE_FORMAT(TILEGX_PIPELINE_Y2, TILEGX_PIPELINE_Y1, TILEGX_PIPELINE_Y0), 50765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 50865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* X format has only two instructions. */ 50965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BUNDLE_FORMAT(TILEGX_PIPELINE_X0, TILEGX_PIPELINE_X1, NO_PIPELINE), 51065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BUNDLE_FORMAT(TILEGX_PIPELINE_X1, TILEGX_PIPELINE_X0, NO_PIPELINE) 51165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich}; 51265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 51365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 51465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstruct jit_instr inst_buf[TILEGX_MAX_INSTRUCTIONS_PER_BUNDLE]; 51565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichunsigned long inst_buf_index; 51665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 51765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichtilegx_pipeline get_any_valid_pipe(const struct tilegx_opcode* opcode) 51865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 51965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* FIXME: tile: we could pregenerate this. */ 52065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich int pipe; 52165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich for (pipe = 0; ((opcode->pipes & (1 << pipe)) == 0 && pipe < TILEGX_NUM_PIPELINE_ENCODINGS); pipe++) 52265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ; 52365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return (tilegx_pipeline)(pipe); 52465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 52565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 52665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichvoid insert_nop(tilegx_mnemonic opc, int line) 52765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 52865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const struct tilegx_opcode* opcode = NULL; 52965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 53065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich memmove(&inst_buf[1], &inst_buf[0], inst_buf_index * sizeof inst_buf[0]); 53165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 53265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich opcode = &tilegx_opcodes[opc]; 53365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[0].opcode = opcode; 53465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[0].pipe = get_any_valid_pipe(opcode); 53565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[0].input_registers = 0; 53665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[0].output_registers = 0; 53765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[0].line = line; 53865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ++inst_buf_index; 53965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 54065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 54165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichconst struct Format* compute_format() 54265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 54365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich unsigned int compatible_pipes = BUNDLE_FORMAT_MASK( 54465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[0].opcode->pipes, 54565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[1].opcode->pipes, 54665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich (inst_buf_index == 3 ? inst_buf[2].opcode->pipes : (1 << NO_PIPELINE))); 54765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 54865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const struct Format* match = NULL; 54965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const struct Format *b = NULL; 55065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich unsigned int i = 0; 55165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich for (i; i < sizeof formats / sizeof formats[0]; i++) { 55265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich b = &formats[i]; 55365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((b->pipe_mask & compatible_pipes) == b->pipe_mask) { 55465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich match = b; 55565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 55665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 55765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 55865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 55965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return match; 56065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 56165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 56265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichsljit_si assign_pipes() 56365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 56465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich unsigned long output_registers = 0; 56565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich unsigned int i = 0; 56665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 56765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (inst_buf_index == 1) { 56865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich tilegx_mnemonic opc = inst_buf[0].opcode->can_bundle 56965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ? TILEGX_OPC_FNOP : TILEGX_OPC_NOP; 57065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich insert_nop(opc, __LINE__); 57165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 57265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 57365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const struct Format* match = compute_format(); 57465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 57565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (match == NULL) 57665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return -1; 57765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 57865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich for (i = 0; i < inst_buf_index; i++) { 57965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 58065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((i > 0) && ((inst_buf[i].input_registers & output_registers) != 0)) 58165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return -1; 58265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 58365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((i > 0) && ((inst_buf[i].output_registers & output_registers) != 0)) 58465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return -1; 58565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 58665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Don't include Rzero in the match set, to avoid triggering 58765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich needlessly on 'prefetch' instrs. */ 58865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 58965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich output_registers |= inst_buf[i].output_registers & 0xFFFFFFFFFFFFFFL; 59065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 59165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[i].pipe = match->pipe[i]; 59265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 59365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 59465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* If only 2 instrs, and in Y-mode, insert a nop. */ 59565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (inst_buf_index == 2 && !tilegx_is_x_pipeline(match->pipe[0])) { 59665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich insert_nop(TILEGX_OPC_FNOP, __LINE__); 59765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 59865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Select the yet unassigned pipe. */ 59965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich tilegx_pipeline pipe = (tilegx_pipeline)(((TILEGX_PIPELINE_Y0 60065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich + TILEGX_PIPELINE_Y1 + TILEGX_PIPELINE_Y2) 60165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich - (inst_buf[1].pipe + inst_buf[2].pipe))); 60265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 60365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[0].pipe = pipe; 60465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 60565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 60665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return 0; 60765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 60865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 60965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichtilegx_bundle_bits get_bundle_bit(struct jit_instr *inst) 61065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 61165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich int i, val; 61265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const struct tilegx_opcode* opcode = inst->opcode; 61365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich tilegx_bundle_bits bits = opcode->fixed_bit_values[inst->pipe]; 61465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 61565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const struct tilegx_operand* operand = NULL; 61665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich for (i = 0; i < opcode->num_operands; i++) { 61765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich operand = &tilegx_operands[opcode->operands[inst->pipe][i]]; 61865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich val = inst->operand_value[i]; 61965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 62065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich bits |= operand->insert(val); 62165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 62265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 62365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return bits; 62465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 62565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 62665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si update_buffer(struct sljit_compiler *compiler) 62765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 62865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich int count; 62965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich int i; 63065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich int orig_index = inst_buf_index; 63165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich struct jit_instr inst0 = inst_buf[0]; 63265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich struct jit_instr inst1 = inst_buf[1]; 63365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich struct jit_instr inst2 = inst_buf[2]; 63465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich tilegx_bundle_bits bits = 0; 63565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 63665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* If the bundle is valid as is, perform the encoding and return 1. */ 63765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (assign_pipes() == 0) { 63865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich for (i = 0; i < inst_buf_index; i++) { 63965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich bits |= get_bundle_bit(inst_buf + i); 64065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 64165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("|%04d", inst_buf[i].line); 64265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 64365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 64465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 64565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (inst_buf_index == 3) 64665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("|M0|:\t"); 64765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 64865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("|M0|:\t\t"); 64965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich print_insn_tilegx(&bits); 65065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 65165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 65265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf_index = 0; 65365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 65465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 65565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return push_inst_nodebug(compiler, bits); 65665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#else 65765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return push_inst(compiler, bits); 65865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 65965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 66065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 66165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* If the bundle is invalid, split it in two. First encode the first two 66265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich (or possibly 1) instructions, and then the last, separately. Note that 66365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich assign_pipes may have re-ordered the instrs (by inserting no-ops in 66465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich lower slots) so we need to reset them. */ 66565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 66665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf_index = orig_index - 1; 66765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[0] = inst0; 66865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[1] = inst1; 66965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[2] = inst2; 67065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (assign_pipes() == 0) { 67165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich for (i = 0; i < inst_buf_index; i++) { 67265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich bits |= get_bundle_bit(inst_buf + i); 67365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 67465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("|%04d", inst_buf[i].line); 67565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 67665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 67765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 67865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 67965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (inst_buf_index == 3) 68065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("|M1|:\t"); 68165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 68265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("|M1|:\t\t"); 68365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich print_insn_tilegx(&bits); 68465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 68565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 68665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((orig_index - 1) == 2) { 68765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[0] = inst2; 68865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf_index = 1; 68965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else if ((orig_index - 1) == 1) { 69065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[0] = inst1; 69165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf_index = 1; 69265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else 69365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT_STOP(); 69465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 69565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 69665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return push_inst_nodebug(compiler, bits); 69765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#else 69865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return push_inst(compiler, bits); 69965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 70065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 70165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* We had 3 instrs of which the first 2 can't live in the same bundle. 70265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich Split those two. Note that we don't try to then combine the second 70365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich and third instr into a single bundle. First instruction: */ 70465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf_index = 1; 70565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[0] = inst0; 70665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[1] = inst1; 70765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[2] = inst2; 70865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (assign_pipes() == 0) { 70965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich for (i = 0; i < inst_buf_index; i++) { 71065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich bits |= get_bundle_bit(inst_buf + i); 71165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 71265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("|%04d", inst_buf[i].line); 71365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 71465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 71565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 71665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 71765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (inst_buf_index == 3) 71865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("|M2|:\t"); 71965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 72065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("|M2|:\t\t"); 72165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich print_insn_tilegx(&bits); 72265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 72365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 72465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[0] = inst1; 72565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[1] = inst2; 72665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf_index = orig_index - 1; 72765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 72865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return push_inst_nodebug(compiler, bits); 72965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#else 73065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return push_inst(compiler, bits); 73165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 73265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else 73365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT_STOP(); 73465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 73565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 73665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT_STOP(); 73765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 73865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 73965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si flush_buffer(struct sljit_compiler *compiler) 74065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 74165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich while (inst_buf_index != 0) 74265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich update_buffer(compiler); 74365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 74465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 74565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si push_4_buffer(struct sljit_compiler *compiler, tilegx_mnemonic opc, int op0, int op1, int op2, int op3, int line) 74665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 74765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (inst_buf_index == TILEGX_MAX_INSTRUCTIONS_PER_BUNDLE) 74865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(update_buffer(compiler)); 74965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 75065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const struct tilegx_opcode* opcode = &tilegx_opcodes[opc]; 75165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].opcode = opcode; 75265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].pipe = get_any_valid_pipe(opcode); 75365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].operand_value[0] = op0; 75465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].operand_value[1] = op1; 75565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].operand_value[2] = op2; 75665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].operand_value[3] = op3; 75765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].input_registers = 1L << op1; 75865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].output_registers = 1L << op0; 75965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].line = line; 76065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf_index++; 76165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 76265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 76365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 76465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 76565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si push_3_buffer(struct sljit_compiler *compiler, tilegx_mnemonic opc, int op0, int op1, int op2, int line) 76665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 76765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (inst_buf_index == TILEGX_MAX_INSTRUCTIONS_PER_BUNDLE) 76865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(update_buffer(compiler)); 76965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 77065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const struct tilegx_opcode* opcode = &tilegx_opcodes[opc]; 77165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].opcode = opcode; 77265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].pipe = get_any_valid_pipe(opcode); 77365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].operand_value[0] = op0; 77465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].operand_value[1] = op1; 77565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].operand_value[2] = op2; 77665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].line = line; 77765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 77865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich switch (opc) { 77965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_ST_ADD: 78065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].input_registers = (1L << op0) | (1L << op1); 78165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].output_registers = 1L << op0; 78265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 78365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_LD_ADD: 78465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].input_registers = 1L << op1; 78565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].output_registers = (1L << op0) | (1L << op1); 78665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 78765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_ADD: 78865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_AND: 78965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_SUB: 79065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_OR: 79165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_XOR: 79265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_NOR: 79365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_SHL: 79465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_SHRU: 79565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_SHRS: 79665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_CMPLTU: 79765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_CMPLTS: 79865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_CMOVEQZ: 79965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_CMOVNEZ: 80065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].input_registers = (1L << op1) | (1L << op2); 80165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].output_registers = 1L << op0; 80265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 80365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_ADDLI: 80465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_XORI: 80565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_ORI: 80665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_SHLI: 80765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_SHRUI: 80865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_SHRSI: 80965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_SHL16INSLI: 81065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_CMPLTUI: 81165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_CMPLTSI: 81265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].input_registers = 1L << op1; 81365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].output_registers = 1L << op0; 81465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 81565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich default: 81665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("unrecoginzed opc: %s\n", opcode->name); 81765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT_STOP(); 81865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 81965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 82065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf_index++; 82165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 82265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 82365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 82465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 82565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si push_2_buffer(struct sljit_compiler *compiler, tilegx_mnemonic opc, int op0, int op1, int line) 82665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 82765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (inst_buf_index == TILEGX_MAX_INSTRUCTIONS_PER_BUNDLE) 82865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(update_buffer(compiler)); 82965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 83065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const struct tilegx_opcode* opcode = &tilegx_opcodes[opc]; 83165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].opcode = opcode; 83265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].pipe = get_any_valid_pipe(opcode); 83365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].operand_value[0] = op0; 83465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].operand_value[1] = op1; 83565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].line = line; 83665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 83765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich switch (opc) { 83865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_BEQZ: 83965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_BNEZ: 84065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].input_registers = 1L << op0; 84165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 84265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_ST: 84365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_ST1: 84465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_ST2: 84565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_ST4: 84665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].input_registers = (1L << op0) | (1L << op1); 84765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].output_registers = 0; 84865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 84965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_CLZ: 85065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_LD: 85165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_LD1U: 85265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_LD1S: 85365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_LD2U: 85465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_LD2S: 85565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_LD4U: 85665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case TILEGX_OPC_LD4S: 85765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].input_registers = 1L << op1; 85865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].output_registers = 1L << op0; 85965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 86065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich default: 86165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("unrecoginzed opc: %s\n", opcode->name); 86265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT_STOP(); 86365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 86465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 86565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf_index++; 86665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 86765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 86865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 86965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 87065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si push_0_buffer(struct sljit_compiler *compiler, tilegx_mnemonic opc, int line) 87165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 87265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (inst_buf_index == TILEGX_MAX_INSTRUCTIONS_PER_BUNDLE) 87365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(update_buffer(compiler)); 87465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 87565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const struct tilegx_opcode* opcode = &tilegx_opcodes[opc]; 87665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].opcode = opcode; 87765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].pipe = get_any_valid_pipe(opcode); 87865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].input_registers = 0; 87965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].output_registers = 0; 88065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].line = line; 88165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf_index++; 88265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 88365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 88465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 88565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 88665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si push_jr_buffer(struct sljit_compiler *compiler, tilegx_mnemonic opc, int op0, int line) 88765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 88865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (inst_buf_index == TILEGX_MAX_INSTRUCTIONS_PER_BUNDLE) 88965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(update_buffer(compiler)); 89065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 89165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const struct tilegx_opcode* opcode = &tilegx_opcodes[opc]; 89265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].opcode = opcode; 89365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].pipe = get_any_valid_pipe(opcode); 89465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].operand_value[0] = op0; 89565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].input_registers = 1L << op0; 89665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].output_registers = 0; 89765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf[inst_buf_index].line = line; 89865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst_buf_index++; 89965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 90065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return flush_buffer(compiler); 90165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 90265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 90365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic SLJIT_INLINE sljit_ins * detect_jump_type(struct sljit_jump *jump, sljit_ins *code_ptr, sljit_ins *code) 90465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 90565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_sw diff; 90665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_uw target_addr; 90765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins *inst; 90865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins saved_inst; 90965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 91065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (jump->flags & SLJIT_REWRITABLE_JUMP) 91165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return code_ptr; 91265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 91365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (jump->flags & JUMP_ADDR) 91465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich target_addr = jump->u.target; 91565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else { 91665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(jump->flags & JUMP_LABEL); 91765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich target_addr = (sljit_uw)(code + jump->u.label->size); 91865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 91965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 92065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst = (sljit_ins *)jump->addr; 92165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (jump->flags & IS_COND) 92265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst--; 92365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 92465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich diff = ((sljit_sw) target_addr - (sljit_sw) inst) >> 3; 92565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (diff <= SIMM_17BIT_MAX && diff >= SIMM_17BIT_MIN) { 92665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->flags |= PATCH_B; 92765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 92865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (!(jump->flags & IS_COND)) { 92965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (jump->flags & IS_JAL) { 93065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->flags &= ~(PATCH_B); 93165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->flags |= PATCH_J; 93265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[0] = JAL_X1; 93365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 93465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 93565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("[runtime relocate]%04d:\t", __LINE__); 93665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich print_insn_tilegx(inst); 93765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 93865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 93965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[0] = BEQZ_X1 | SRCA_X1(ZERO); 94065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 94165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 94265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("[runtime relocate]%04d:\t", __LINE__); 94365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich print_insn_tilegx(inst); 94465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 94565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 94665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 94765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return inst; 94865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 94965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 95065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[0] = inst[0] ^ (0x7L << 55); 95165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 95265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 95365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("[runtime relocate]%04d:\t", __LINE__); 95465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich print_insn_tilegx(inst); 95565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 95665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->addr -= sizeof(sljit_ins); 95765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return inst; 95865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 95965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 96065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (jump->flags & IS_COND) { 96165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((target_addr & ~0x3FFFFFFFL) == ((jump->addr + sizeof(sljit_ins)) & ~0x3FFFFFFFL)) { 96265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->flags |= PATCH_J; 96365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[0] = (inst[0] & ~(BOFF_X1(-1))) | BOFF_X1(2); 96465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[1] = J_X1; 96565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return inst + 1; 96665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 96765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 96865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return code_ptr; 96965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 97065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 97165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((target_addr & ~0x3FFFFFFFL) == ((jump->addr + sizeof(sljit_ins)) & ~0x3FFFFFFFL)) { 97265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->flags |= PATCH_J; 97365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 97465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (jump->flags & IS_JAL) { 97565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[0] = JAL_X1; 97665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 97765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 97865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("[runtime relocate]%04d:\t", __LINE__); 97965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich print_insn_tilegx(inst); 98065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 98165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 98265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 98365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[0] = J_X1; 98465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 98565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 98665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("[runtime relocate]%04d:\t", __LINE__); 98765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich print_insn_tilegx(inst); 98865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 98965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 99065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 99165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return inst; 99265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 99365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 99465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return code_ptr; 99565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 99665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 99765de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE void * sljit_generate_code(struct sljit_compiler *compiler) 99865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 99965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich struct sljit_memory_fragment *buf; 100065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins *code; 100165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins *code_ptr; 100265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins *buf_ptr; 100365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins *buf_end; 100465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_uw word_count; 100565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_uw addr; 100665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 100765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich struct sljit_label *label; 100865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich struct sljit_jump *jump; 100965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich struct sljit_const *const_; 101065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 101165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR_PTR(); 101265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_generate_code(compiler); 101365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich reverse_buf(compiler); 101465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 101565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich code = (sljit_ins *)SLJIT_MALLOC_EXEC(compiler->size * sizeof(sljit_ins)); 101665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich PTR_FAIL_WITH_EXEC_IF(code); 101765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich buf = compiler->buf; 101865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 101965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich code_ptr = code; 102065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich word_count = 0; 102165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich label = compiler->labels; 102265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump = compiler->jumps; 102365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const_ = compiler->consts; 102465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich do { 102565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich buf_ptr = (sljit_ins *)buf->memory; 102665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich buf_end = buf_ptr + (buf->used_size >> 3); 102765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich do { 102865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich *code_ptr = *buf_ptr++; 102965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(!label || label->size >= word_count); 103065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(!jump || jump->addr >= word_count); 103165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(!const_ || const_->addr >= word_count); 103265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* These structures are ordered by their address. */ 103365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (label && label->size == word_count) { 103465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Just recording the address. */ 103565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich label->addr = (sljit_uw) code_ptr; 103665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich label->size = code_ptr - code; 103765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich label = label->next; 103865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 103965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 104065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (jump && jump->addr == word_count) { 104165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (jump->flags & IS_JAL) 104265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->addr = (sljit_uw)(code_ptr - 4); 104365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 104465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->addr = (sljit_uw)(code_ptr - 3); 104565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 104665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich code_ptr = detect_jump_type(jump, code_ptr, code); 104765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump = jump->next; 104865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 104965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 105065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (const_ && const_->addr == word_count) { 105165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Just recording the address. */ 105265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const_->addr = (sljit_uw) code_ptr; 105365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const_ = const_->next; 105465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 105565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 105665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich code_ptr++; 105765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich word_count++; 105865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } while (buf_ptr < buf_end); 105965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 106065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich buf = buf->next; 106165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } while (buf); 106265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 106365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (label && label->size == word_count) { 106465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich label->addr = (sljit_uw) code_ptr; 106565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich label->size = code_ptr - code; 106665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich label = label->next; 106765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 106865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 106965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(!label); 107065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(!jump); 107165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(!const_); 107265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(code_ptr - code <= (sljit_sw)compiler->size); 107365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 107465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump = compiler->jumps; 107565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich while (jump) { 107665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich do { 107765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich addr = (jump->flags & JUMP_LABEL) ? jump->u.label->addr : jump->u.target; 107865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich buf_ptr = (sljit_ins *)jump->addr; 107965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 108065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (jump->flags & PATCH_B) { 108165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich addr = (sljit_sw)(addr - (jump->addr)) >> 3; 108265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT((sljit_sw) addr <= SIMM_17BIT_MAX && (sljit_sw) addr >= SIMM_17BIT_MIN); 108365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich buf_ptr[0] = (buf_ptr[0] & ~(BOFF_X1(-1))) | BOFF_X1(addr); 108465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 108565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 108665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("[runtime relocate]%04d:\t", __LINE__); 108765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich print_insn_tilegx(buf_ptr); 108865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 108965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 109065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 109165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 109265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (jump->flags & PATCH_J) { 109365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT((addr & ~0x3FFFFFFFL) == ((jump->addr + sizeof(sljit_ins)) & ~0x3FFFFFFFL)); 109465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich addr = (sljit_sw)(addr - (jump->addr)) >> 3; 109565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich buf_ptr[0] = (buf_ptr[0] & ~(JOFF_X1(-1))) | JOFF_X1(addr); 109665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 109765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#ifdef TILEGX_JIT_DEBUG 109865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich printf("[runtime relocate]%04d:\t", __LINE__); 109965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich print_insn_tilegx(buf_ptr); 110065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 110165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 110265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 110365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 110465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(!(jump->flags & IS_JAL)); 110565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 110665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Set the fields of immediate loads. */ 110765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich buf_ptr[0] = (buf_ptr[0] & ~(0xFFFFL << 43)) | (((addr >> 32) & 0xFFFFL) << 43); 110865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich buf_ptr[1] = (buf_ptr[1] & ~(0xFFFFL << 43)) | (((addr >> 16) & 0xFFFFL) << 43); 110965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich buf_ptr[2] = (buf_ptr[2] & ~(0xFFFFL << 43)) | ((addr & 0xFFFFL) << 43); 111065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } while (0); 111165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 111265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump = jump->next; 111365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 111465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 111565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->error = SLJIT_ERR_COMPILED; 111665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->executable_size = (code_ptr - code) * sizeof(sljit_ins); 111765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_CACHE_FLUSH(code, code_ptr); 111865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return code; 111965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 112065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 112165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si load_immediate(struct sljit_compiler *compiler, sljit_si dst_ar, sljit_sw imm) 112265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 112365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 112465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (imm <= SIMM_16BIT_MAX && imm >= SIMM_16BIT_MIN) 112565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return ADDLI(dst_ar, ZERO, imm); 112665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 112765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (imm <= SIMM_32BIT_MAX && imm >= SIMM_32BIT_MIN) { 112865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(dst_ar, ZERO, imm >> 16)); 112965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SHL16INSLI(dst_ar, dst_ar, imm); 113065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 113165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 113265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (imm <= SIMM_48BIT_MAX && imm >= SIMM_48BIT_MIN) { 113365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(dst_ar, ZERO, imm >> 32)); 113465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHL16INSLI(dst_ar, dst_ar, imm >> 16)); 113565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SHL16INSLI(dst_ar, dst_ar, imm); 113665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 113765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 113865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(dst_ar, ZERO, imm >> 48)); 113965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHL16INSLI(dst_ar, dst_ar, imm >> 32)); 114065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHL16INSLI(dst_ar, dst_ar, imm >> 16)); 114165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SHL16INSLI(dst_ar, dst_ar, imm); 114265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 114365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 114465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si emit_const(struct sljit_compiler *compiler, sljit_si dst_ar, sljit_sw imm, int flush) 114565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 114665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Should *not* be optimized as load_immediate, as pcre relocation 114765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich mechanism will match this fixed 4-instruction pattern. */ 114865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flush) { 114965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI_SOLO(dst_ar, ZERO, imm >> 32)); 115065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHL16INSLI_SOLO(dst_ar, dst_ar, imm >> 16)); 115165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SHL16INSLI_SOLO(dst_ar, dst_ar, imm); 115265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 115365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 115465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(dst_ar, ZERO, imm >> 32)); 115565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHL16INSLI(dst_ar, dst_ar, imm >> 16)); 115665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SHL16INSLI(dst_ar, dst_ar, imm); 115765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 115865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 115965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si emit_const_64(struct sljit_compiler *compiler, sljit_si dst_ar, sljit_sw imm, int flush) 116065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 116165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Should *not* be optimized as load_immediate, as pcre relocation 116265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich mechanism will match this fixed 4-instruction pattern. */ 116365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flush) { 116465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI_SOLO(reg_map[dst_ar], ZERO, imm >> 48)); 116565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHL16INSLI_SOLO(reg_map[dst_ar], reg_map[dst_ar], imm >> 32)); 116665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHL16INSLI_SOLO(reg_map[dst_ar], reg_map[dst_ar], imm >> 16)); 116765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SHL16INSLI_SOLO(reg_map[dst_ar], reg_map[dst_ar], imm); 116865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 116965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 117065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(reg_map[dst_ar], ZERO, imm >> 48)); 117165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHL16INSLI(reg_map[dst_ar], reg_map[dst_ar], imm >> 32)); 117265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHL16INSLI(reg_map[dst_ar], reg_map[dst_ar], imm >> 16)); 117365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SHL16INSLI(reg_map[dst_ar], reg_map[dst_ar], imm); 117465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 117565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 117665de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_enter(struct sljit_compiler *compiler, 117765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si options, sljit_si args, sljit_si scratches, sljit_si saveds, 117865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si fscratches, sljit_si fsaveds, sljit_si local_size) 117965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 118065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins base; 118165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins bundle = 0; 118265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 118365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR(); 118465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_emit_enter(compiler, options, args, scratches, saveds, fscratches, fsaveds, local_size); 118565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 118665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->options = options; 118765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->scratches = scratches; 118865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->saveds = saveds; 118965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->fscratches = fscratches; 119065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->fsaveds = fsaveds; 119165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 119265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->logical_local_size = local_size; 119365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 119465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 119565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich local_size += (saveds + 1) * sizeof(sljit_sw); 119665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich local_size = (local_size + 7) & ~7; 119765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->local_size = local_size; 119865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 119965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (local_size <= SIMM_16BIT_MAX) { 120065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Frequent case. */ 120165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(SLJIT_LOCALS_REG_mapped, SLJIT_LOCALS_REG_mapped, -local_size)); 120265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich base = SLJIT_LOCALS_REG_mapped; 120365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 120465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(load_immediate(compiler, TMP_REG1_mapped, local_size)); 120565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(TMP_REG2_mapped, SLJIT_LOCALS_REG_mapped, ZERO)); 120665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SUB(SLJIT_LOCALS_REG_mapped, SLJIT_LOCALS_REG_mapped, TMP_REG1_mapped)); 120765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich base = TMP_REG2_mapped; 120865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich local_size = 0; 120965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 121065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 121165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(ADDR_TMP_mapped, base, local_size - 8)); 121265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ST_ADD(ADDR_TMP_mapped, RA, -8)); 121365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 121465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (saveds >= 1) 121565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ST_ADD(ADDR_TMP_mapped, SLJIT_SAVED_REG1_mapped, -8)); 121665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 121765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (saveds >= 2) 121865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ST_ADD(ADDR_TMP_mapped, SLJIT_SAVED_REG2_mapped, -8)); 121965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 122065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (saveds >= 3) 122165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ST_ADD(ADDR_TMP_mapped, SLJIT_SAVED_REG3_mapped, -8)); 122265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 122365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (saveds >= 4) 122465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ST_ADD(ADDR_TMP_mapped, SLJIT_SAVED_EREG1_mapped, -8)); 122565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 122665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (saveds >= 5) 122765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ST_ADD(ADDR_TMP_mapped, SLJIT_SAVED_EREG2_mapped, -8)); 122865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 122965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (args >= 1) 123065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(SLJIT_SAVED_REG1_mapped, 0, ZERO)); 123165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 123265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (args >= 2) 123365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(SLJIT_SAVED_REG2_mapped, 1, ZERO)); 123465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 123565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (args >= 3) 123665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(SLJIT_SAVED_REG3_mapped, 2, ZERO)); 123765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 123865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 123965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 124065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 124165de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE void sljit_set_context(struct sljit_compiler *compiler, 124265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si options, sljit_si args, sljit_si scratches, sljit_si saveds, 124365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si fscratches, sljit_si fsaveds, sljit_si local_size) 124465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 124565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR_VOID(); 124665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_set_context(compiler, options, args, scratches, saveds, fscratches, fsaveds, local_size); 124765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 124865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->options = options; 124965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->scratches = scratches; 125065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->saveds = saveds; 125165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->fscratches = fscratches; 125265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->fsaveds = fsaveds; 125365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#if (defined SLJIT_DEBUG && SLJIT_DEBUG) 125465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->logical_local_size = local_size; 125565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#endif 125665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 125765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich local_size += (saveds + 1) * sizeof(sljit_sw); 125865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->local_size = (local_size + 7) & ~7; 125965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 126065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 126165de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_return(struct sljit_compiler *compiler, sljit_si op, sljit_si src, sljit_sw srcw) 126265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 126365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si local_size; 126465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins base; 126565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich int addr_initialized = 0; 126665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 126765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR(); 126865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_emit_return(compiler, op, src, srcw); 126965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 127065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(emit_mov_before_return(compiler, op, src, srcw)); 127165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 127265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich local_size = compiler->local_size; 127365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (local_size <= SIMM_16BIT_MAX) 127465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich base = SLJIT_LOCALS_REG_mapped; 127565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else { 127665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(load_immediate(compiler, TMP_REG1_mapped, local_size)); 127765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(TMP_REG1_mapped, SLJIT_LOCALS_REG_mapped, TMP_REG1_mapped)); 127865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich base = TMP_REG1_mapped; 127965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich local_size = 0; 128065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 128165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 128265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(ADDR_TMP_mapped, base, local_size - 8)); 128365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(LD(RA, ADDR_TMP_mapped)); 128465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 128565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (compiler->saveds >= 5) { 128665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(ADDR_TMP_mapped, base, local_size - 48)); 128765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich addr_initialized = 1; 128865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 128965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(LD_ADD(SLJIT_SAVED_EREG2_mapped, ADDR_TMP_mapped, 8)); 129065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 129165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 129265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (compiler->saveds >= 4) { 129365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (addr_initialized == 0) { 129465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(ADDR_TMP_mapped, base, local_size - 40)); 129565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich addr_initialized = 1; 129665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 129765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 129865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(LD_ADD(SLJIT_SAVED_EREG1_mapped, ADDR_TMP_mapped, 8)); 129965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 130065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 130165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (compiler->saveds >= 3) { 130265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (addr_initialized == 0) { 130365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(ADDR_TMP_mapped, base, local_size - 32)); 130465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich addr_initialized = 1; 130565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 130665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 130765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(LD_ADD(SLJIT_SAVED_REG3_mapped, ADDR_TMP_mapped, 8)); 130865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 130965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 131065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (compiler->saveds >= 2) { 131165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (addr_initialized == 0) { 131265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(ADDR_TMP_mapped, base, local_size - 24)); 131365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich addr_initialized = 1; 131465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 131565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 131665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(LD_ADD(SLJIT_SAVED_REG2_mapped, ADDR_TMP_mapped, 8)); 131765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 131865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 131965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (compiler->saveds >= 1) { 132065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (addr_initialized == 0) { 132165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(ADDR_TMP_mapped, base, local_size - 16)); 132265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* addr_initialized = 1; no need to initialize as it's the last one. */ 132365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 132465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 132565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(LD_ADD(SLJIT_SAVED_REG1_mapped, ADDR_TMP_mapped, 8)); 132665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 132765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 132865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (compiler->local_size <= SIMM_16BIT_MAX) 132965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(SLJIT_LOCALS_REG_mapped, SLJIT_LOCALS_REG_mapped, compiler->local_size)); 133065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 133165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(SLJIT_LOCALS_REG_mapped, TMP_REG1_mapped, ZERO)); 133265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 133365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return JR(RA); 133465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 133565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 133665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich/* reg_ar is an absoulute register! */ 133765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 133865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich/* Can perform an operation using at most 1 instruction. */ 133965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si getput_arg_fast(struct sljit_compiler *compiler, sljit_si flags, sljit_si reg_ar, sljit_si arg, sljit_sw argw) 134065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 134165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(arg & SLJIT_MEM); 134265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 134365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((!(flags & WRITE_BACK) || !(arg & REG_MASK)) 134465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich && !(arg & OFFS_REG_MASK) && argw <= SIMM_16BIT_MAX && argw >= SIMM_16BIT_MIN) { 134565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Works for both absoulte and relative addresses. */ 134665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (SLJIT_UNLIKELY(flags & ARG_TEST)) 134765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return 1; 134865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 134965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(ADDR_TMP_mapped, reg_map[arg & REG_MASK], argw)); 135065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 135165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & LOAD_DATA) 135265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(PB2(data_transfer_insts[flags & MEM_MASK], reg_ar, ADDR_TMP_mapped)); 135365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 135465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(PB2(data_transfer_insts[flags & MEM_MASK], ADDR_TMP_mapped, reg_ar)); 135565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 135665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return -1; 135765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 135865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 135965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return 0; 136065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 136165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 136265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich/* See getput_arg below. 136365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich Note: can_cache is called only for binary operators. Those 136465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich operators always uses word arguments without write back. */ 136565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si can_cache(sljit_si arg, sljit_sw argw, sljit_si next_arg, sljit_sw next_argw) 136665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 136765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT((arg & SLJIT_MEM) && (next_arg & SLJIT_MEM)); 136865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 136965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Simple operation except for updates. */ 137065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (arg & OFFS_REG_MASK) { 137165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich argw &= 0x3; 137265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich next_argw &= 0x3; 137365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (argw && argw == next_argw 137465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich && (arg == next_arg || (arg & OFFS_REG_MASK) == (next_arg & OFFS_REG_MASK))) 137565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return 1; 137665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return 0; 137765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 137865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 137965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (arg == next_arg) { 138065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (((next_argw - argw) <= SIMM_16BIT_MAX 138165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich && (next_argw - argw) >= SIMM_16BIT_MIN)) 138265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return 1; 138365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 138465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return 0; 138565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 138665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 138765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return 0; 138865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 138965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 139065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich/* Emit the necessary instructions. See can_cache above. */ 139165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si getput_arg(struct sljit_compiler *compiler, sljit_si flags, sljit_si reg_ar, sljit_si arg, sljit_sw argw, sljit_si next_arg, sljit_sw next_argw) 139265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 139365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si tmp_ar, base; 139465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 139565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(arg & SLJIT_MEM); 139665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (!(next_arg & SLJIT_MEM)) { 139765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich next_arg = 0; 139865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich next_argw = 0; 139965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 140065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 140165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((flags & MEM_MASK) <= GPR_REG && (flags & LOAD_DATA)) 140265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich tmp_ar = reg_ar; 140365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 140465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich tmp_ar = TMP_REG1_mapped; 140565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 140665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich base = arg & REG_MASK; 140765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 140865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (SLJIT_UNLIKELY(arg & OFFS_REG_MASK)) { 140965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich argw &= 0x3; 141065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 141165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((flags & WRITE_BACK) && reg_ar == reg_map[base]) { 141265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(!(flags & LOAD_DATA) && reg_map[TMP_REG1] != reg_ar); 141365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(TMP_REG1_mapped, reg_ar, ZERO)); 141465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich reg_ar = TMP_REG1_mapped; 141565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 141665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 141765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Using the cache. */ 141865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (argw == compiler->cache_argw) { 141965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (!(flags & WRITE_BACK)) { 142065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (arg == compiler->cache_arg) { 142165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & LOAD_DATA) 142265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_ar, TMP_REG3_mapped); 142365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 142465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], TMP_REG3_mapped, reg_ar); 142565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 142665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 142765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((SLJIT_MEM | (arg & OFFS_REG_MASK)) == compiler->cache_arg) { 142865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (arg == next_arg && argw == (next_argw & 0x3)) { 142965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_arg = arg; 143065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_argw = argw; 143165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(TMP_REG3_mapped, reg_map[base], TMP_REG3_mapped)); 143265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & LOAD_DATA) 143365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_ar, TMP_REG3_mapped); 143465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 143565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], TMP_REG3_mapped, reg_ar); 143665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 143765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 143865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(tmp_ar, reg_map[base], TMP_REG3_mapped)); 143965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & LOAD_DATA) 144065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_ar, tmp_ar); 144165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 144265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], tmp_ar, reg_ar); 144365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 144465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 144565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((SLJIT_MEM | (arg & OFFS_REG_MASK)) == compiler->cache_arg) { 144665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(reg_map[base], reg_map[base], TMP_REG3_mapped)); 144765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & LOAD_DATA) 144865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_ar, reg_map[base]); 144965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 145065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_map[base], reg_ar); 145165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 145265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 145365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 145465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 145565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (SLJIT_UNLIKELY(argw)) { 145665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_arg = SLJIT_MEM | (arg & OFFS_REG_MASK); 145765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_argw = argw; 145865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHLI(TMP_REG3_mapped, reg_map[OFFS_REG(arg)], argw)); 145965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 146065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 146165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (!(flags & WRITE_BACK)) { 146265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (arg == next_arg && argw == (next_argw & 0x3)) { 146365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_arg = arg; 146465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_argw = argw; 146565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(TMP_REG3_mapped, reg_map[base], reg_map[!argw ? OFFS_REG(arg) : TMP_REG3])); 146665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich tmp_ar = TMP_REG3_mapped; 146765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else 146865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(tmp_ar, reg_map[base], reg_map[!argw ? OFFS_REG(arg) : TMP_REG3])); 146965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 147065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & LOAD_DATA) 147165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_ar, tmp_ar); 147265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 147365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], tmp_ar, reg_ar); 147465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 147565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 147665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(reg_map[base], reg_map[base], reg_map[!argw ? OFFS_REG(arg) : TMP_REG3])); 147765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 147865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & LOAD_DATA) 147965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_ar, reg_map[base]); 148065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 148165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_map[base], reg_ar); 148265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 148365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 148465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (SLJIT_UNLIKELY(flags & WRITE_BACK) && base) { 148565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Update only applies if a base register exists. */ 148665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (reg_ar == reg_map[base]) { 148765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(!(flags & LOAD_DATA) && TMP_REG1_mapped != reg_ar); 148865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (argw <= SIMM_16BIT_MAX && argw >= SIMM_16BIT_MIN) { 148965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(ADDR_TMP_mapped, reg_map[base], argw)); 149065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & LOAD_DATA) 149165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(PB2(data_transfer_insts[flags & MEM_MASK], reg_ar, ADDR_TMP_mapped)); 149265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 149365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(PB2(data_transfer_insts[flags & MEM_MASK], ADDR_TMP_mapped, reg_ar)); 149465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 149565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (argw) 149665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return ADDLI(reg_map[base], reg_map[base], argw); 149765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 149865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 149965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 150065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 150165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(TMP_REG1_mapped, reg_ar, ZERO)); 150265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich reg_ar = TMP_REG1_mapped; 150365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 150465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 150565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (argw <= SIMM_16BIT_MAX && argw >= SIMM_16BIT_MIN) { 150665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (argw) 150765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(reg_map[base], reg_map[base], argw)); 150865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 150965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (compiler->cache_arg == SLJIT_MEM 151065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich && argw - compiler->cache_argw <= SIMM_16BIT_MAX 151165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich && argw - compiler->cache_argw >= SIMM_16BIT_MIN) { 151265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (argw != compiler->cache_argw) { 151365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(TMP_REG3_mapped, TMP_REG3_mapped, argw - compiler->cache_argw)); 151465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_argw = argw; 151565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 151665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 151765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(reg_map[base], reg_map[base], TMP_REG3_mapped)); 151865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 151965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_arg = SLJIT_MEM; 152065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_argw = argw; 152165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(load_immediate(compiler, TMP_REG3_mapped, argw)); 152265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(reg_map[base], reg_map[base], TMP_REG3_mapped)); 152365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 152465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 152565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 152665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & LOAD_DATA) 152765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_ar, reg_map[base]); 152865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 152965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_map[base], reg_ar); 153065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 153165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 153265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (compiler->cache_arg == arg 153365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich && argw - compiler->cache_argw <= SIMM_16BIT_MAX 153465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich && argw - compiler->cache_argw >= SIMM_16BIT_MIN) { 153565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (argw != compiler->cache_argw) { 153665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(TMP_REG3_mapped, TMP_REG3_mapped, argw - compiler->cache_argw)); 153765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_argw = argw; 153865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 153965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 154065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & LOAD_DATA) 154165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_ar, TMP_REG3_mapped); 154265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 154365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], TMP_REG3_mapped, reg_ar); 154465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 154565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 154665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (compiler->cache_arg == SLJIT_MEM 154765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich && argw - compiler->cache_argw <= SIMM_16BIT_MAX 154865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich && argw - compiler->cache_argw >= SIMM_16BIT_MIN) { 154965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (argw != compiler->cache_argw) 155065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(TMP_REG3_mapped, TMP_REG3_mapped, argw - compiler->cache_argw)); 155165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 155265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_arg = SLJIT_MEM; 155365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(load_immediate(compiler, TMP_REG3_mapped, argw)); 155465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 155565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 155665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_argw = argw; 155765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 155865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (!base) { 155965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & LOAD_DATA) 156065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_ar, TMP_REG3_mapped); 156165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 156265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], TMP_REG3_mapped, reg_ar); 156365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 156465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 156565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (arg == next_arg 156665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich && next_argw - argw <= SIMM_16BIT_MAX 156765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich && next_argw - argw >= SIMM_16BIT_MIN) { 156865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_arg = arg; 156965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(TMP_REG3_mapped, TMP_REG3_mapped, reg_map[base])); 157065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & LOAD_DATA) 157165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_ar, TMP_REG3_mapped); 157265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 157365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], TMP_REG3_mapped, reg_ar); 157465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 157565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 157665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(tmp_ar, TMP_REG3_mapped, reg_map[base])); 157765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 157865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & LOAD_DATA) 157965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], reg_ar, tmp_ar); 158065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 158165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PB2(data_transfer_insts[flags & MEM_MASK], tmp_ar, reg_ar); 158265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 158365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 158465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic SLJIT_INLINE sljit_si emit_op_mem(struct sljit_compiler *compiler, sljit_si flags, sljit_si reg_ar, sljit_si arg, sljit_sw argw) 158565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 158665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (getput_arg_fast(compiler, flags, reg_ar, arg, argw)) 158765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return compiler->error; 158865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 158965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_arg = 0; 159065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_argw = 0; 159165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return getput_arg(compiler, flags, reg_ar, arg, argw, 0, 0); 159265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 159365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 159465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic SLJIT_INLINE sljit_si emit_op_mem2(struct sljit_compiler *compiler, sljit_si flags, sljit_si reg, sljit_si arg1, sljit_sw arg1w, sljit_si arg2, sljit_sw arg2w) 159565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 159665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (getput_arg_fast(compiler, flags, reg, arg1, arg1w)) 159765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return compiler->error; 159865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return getput_arg(compiler, flags, reg, arg1, arg1w, arg2, arg2w); 159965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 160065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 160165de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_fast_enter(struct sljit_compiler *compiler, sljit_si dst, sljit_sw dstw) 160265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 160365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR(); 160465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_emit_fast_enter(compiler, dst, dstw); 160565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ADJUST_LOCAL_OFFSET(dst, dstw); 160665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 160765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* For UNUSED dst. Uncommon, but possible. */ 160865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (dst == SLJIT_UNUSED) 160965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 161065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 161165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (FAST_IS_REG(dst)) 161265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return ADD(reg_map[dst], RA, ZERO); 161365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 161465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Memory. */ 161565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op_mem(compiler, WORD_DATA, RA, dst, dstw); 161665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 161765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 161865de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_fast_return(struct sljit_compiler *compiler, sljit_si src, sljit_sw srcw) 161965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 162065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR(); 162165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_emit_fast_return(compiler, src, srcw); 162265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ADJUST_LOCAL_OFFSET(src, srcw); 162365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 162465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (FAST_IS_REG(src)) 162565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(RA, reg_map[src], ZERO)); 162665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 162765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else if (src & SLJIT_MEM) 162865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(emit_op_mem(compiler, WORD_DATA | LOAD_DATA, RA, src, srcw)); 162965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 163065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else if (src & SLJIT_IMM) 163165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(load_immediate(compiler, RA, srcw)); 163265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 163365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return JR(RA); 163465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 163565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 163665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic SLJIT_INLINE sljit_si emit_single_op(struct sljit_compiler *compiler, sljit_si op, sljit_si flags, sljit_si dst, sljit_si src1, sljit_sw src2) 163765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 163865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si overflow_ra = 0; 163965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 164065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich switch (GET_OPCODE(op)) { 164165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV: 164265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_P: 164365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(src1 == TMP_REG1 && !(flags & SRC2_IMM)); 164465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (dst != src2) 164565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return ADD(reg_map[dst], reg_map[src2], ZERO); 164665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 164765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 164865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_UI: 164965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_SI: 165065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(src1 == TMP_REG1 && !(flags & SRC2_IMM)); 165165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((flags & (REG_DEST | REG2_SOURCE)) == (REG_DEST | REG2_SOURCE)) { 165265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op == SLJIT_MOV_SI) 165365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return BFEXTS(reg_map[dst], reg_map[src2], 0, 31); 165465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 165565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return BFEXTU(reg_map[dst], reg_map[src2], 0, 31); 165665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else if (dst != src2) 165765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT_STOP(); 165865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 165965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 166065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 166165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_UB: 166265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_SB: 166365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(src1 == TMP_REG1 && !(flags & SRC2_IMM)); 166465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((flags & (REG_DEST | REG2_SOURCE)) == (REG_DEST | REG2_SOURCE)) { 166565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op == SLJIT_MOV_SB) 166665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return BFEXTS(reg_map[dst], reg_map[src2], 0, 7); 166765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 166865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return BFEXTU(reg_map[dst], reg_map[src2], 0, 7); 166965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else if (dst != src2) 167065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT_STOP(); 167165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 167265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 167365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 167465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_UH: 167565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_SH: 167665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(src1 == TMP_REG1 && !(flags & SRC2_IMM)); 167765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((flags & (REG_DEST | REG2_SOURCE)) == (REG_DEST | REG2_SOURCE)) { 167865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op == SLJIT_MOV_SH) 167965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return BFEXTS(reg_map[dst], reg_map[src2], 0, 15); 168065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 168165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return BFEXTU(reg_map[dst], reg_map[src2], 0, 15); 168265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else if (dst != src2) 168365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT_STOP(); 168465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 168565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 168665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 168765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_NOT: 168865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(src1 == TMP_REG1 && !(flags & SRC2_IMM)); 168965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_E) 169065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(NOR(EQUAL_FLAG, reg_map[src2], reg_map[src2])); 169165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (CHECK_FLAGS(SLJIT_SET_E)) 169265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(NOR(reg_map[dst], reg_map[src2], reg_map[src2])); 169365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 169465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 169565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 169665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_CLZ: 169765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(src1 == TMP_REG1 && !(flags & SRC2_IMM)); 169865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_E) 169965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CLZ(EQUAL_FLAG, reg_map[src2])); 170065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (CHECK_FLAGS(SLJIT_SET_E)) 170165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CLZ(reg_map[dst], reg_map[src2])); 170265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 170365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 170465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 170565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_ADD: 170665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & SRC2_IMM) { 170765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_O) { 170865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHRUI(TMP_EREG1, reg_map[src1], 63)); 170965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src2 < 0) 171065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(XORI(TMP_EREG1, TMP_EREG1, 1)); 171165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 171265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 171365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_E) 171465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(EQUAL_FLAG, reg_map[src1], src2)); 171565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 171665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_C) { 171765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src2 >= 0) 171865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ORI(ULESS_FLAG ,reg_map[src1], src2)); 171965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else { 172065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(ULESS_FLAG ,ZERO, src2)); 172165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(OR(ULESS_FLAG,reg_map[src1],ULESS_FLAG)); 172265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 172365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 172465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 172565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* dst may be the same as src1 or src2. */ 172665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (CHECK_FLAGS(SLJIT_SET_E)) 172765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(reg_map[dst], reg_map[src1], src2)); 172865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 172965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_O) { 173065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHRUI(OVERFLOW_FLAG, reg_map[dst], 63)); 173165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 173265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src2 < 0) 173365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(XORI(OVERFLOW_FLAG, OVERFLOW_FLAG, 1)); 173465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 173565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 173665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_O) { 173765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(XOR(TMP_EREG1, reg_map[src1], reg_map[src2])); 173865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHRUI(TMP_EREG1, TMP_EREG1, 63)); 173965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 174065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src1 != dst) 174165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich overflow_ra = reg_map[src1]; 174265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else if (src2 != dst) 174365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich overflow_ra = reg_map[src2]; 174465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else { 174565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Rare ocasion. */ 174665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(TMP_EREG2, reg_map[src1], ZERO)); 174765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich overflow_ra = TMP_EREG2; 174865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 174965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 175065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 175165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_E) 175265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(EQUAL_FLAG ,reg_map[src1], reg_map[src2])); 175365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 175465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_C) 175565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(OR(ULESS_FLAG,reg_map[src1], reg_map[src2])); 175665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 175765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* dst may be the same as src1 or src2. */ 175865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (CHECK_FLAGS(SLJIT_SET_E)) 175965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(reg_map[dst],reg_map[src1], reg_map[src2])); 176065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 176165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_O) { 176265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(XOR(OVERFLOW_FLAG,reg_map[dst], overflow_ra)); 176365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHRUI(OVERFLOW_FLAG, OVERFLOW_FLAG, 63)); 176465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 176565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 176665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 176765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* a + b >= a | b (otherwise, the carry should be set to 1). */ 176865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_C) 176965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CMPLTU(ULESS_FLAG ,reg_map[dst] ,ULESS_FLAG)); 177065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 177165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_O) 177265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return CMOVNEZ(OVERFLOW_FLAG, TMP_EREG1, ZERO); 177365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 177465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 177565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 177665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_ADDC: 177765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & SRC2_IMM) { 177865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_C) { 177965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src2 >= 0) 178065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ORI(TMP_EREG1, reg_map[src1], src2)); 178165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else { 178265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(TMP_EREG1, ZERO, src2)); 178365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(OR(TMP_EREG1, reg_map[src1], TMP_EREG1)); 178465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 178565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 178665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 178765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(reg_map[dst], reg_map[src1], src2)); 178865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 178965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 179065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_C) 179165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(OR(TMP_EREG1, reg_map[src1], reg_map[src2])); 179265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 179365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* dst may be the same as src1 or src2. */ 179465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(reg_map[dst], reg_map[src1], reg_map[src2])); 179565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 179665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 179765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_C) 179865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CMPLTU(TMP_EREG1, reg_map[dst], TMP_EREG1)); 179965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 180065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(reg_map[dst], reg_map[dst], ULESS_FLAG)); 180165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 180265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (!(op & SLJIT_SET_C)) 180365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 180465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 180565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Set TMP_EREG2 (dst == 0) && (ULESS_FLAG == 1). */ 180665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CMPLTUI(TMP_EREG2, reg_map[dst], 1)); 180765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(AND(TMP_EREG2, TMP_EREG2, ULESS_FLAG)); 180865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Set carry flag. */ 180965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return OR(ULESS_FLAG, TMP_EREG2, TMP_EREG1); 181065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 181165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_SUB: 181265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((flags & SRC2_IMM) && ((op & (SLJIT_SET_U | SLJIT_SET_S)) || src2 == SIMM_16BIT_MIN)) { 181365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(TMP_REG2_mapped, ZERO, src2)); 181465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2 = TMP_REG2; 181565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flags &= ~SRC2_IMM; 181665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 181765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 181865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & SRC2_IMM) { 181965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_O) { 182065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHRUI(TMP_EREG1,reg_map[src1], 63)); 182165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 182265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src2 < 0) 182365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(XORI(TMP_EREG1, TMP_EREG1, 1)); 182465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 182565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src1 != dst) 182665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich overflow_ra = reg_map[src1]; 182765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else { 182865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Rare ocasion. */ 182965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(TMP_EREG2, reg_map[src1], ZERO)); 183065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 183165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich overflow_ra = TMP_EREG2; 183265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 183365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 183465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 183565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_E) 183665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(EQUAL_FLAG, reg_map[src1], -src2)); 183765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 183865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_C) { 183965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(load_immediate(compiler, ADDR_TMP_mapped, src2)); 184065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CMPLTU(ULESS_FLAG, reg_map[src1], ADDR_TMP_mapped)); 184165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 184265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 184365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* dst may be the same as src1 or src2. */ 184465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (CHECK_FLAGS(SLJIT_SET_E)) 184565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(reg_map[dst], reg_map[src1], -src2)); 184665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 184765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 184865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 184965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_O) { 185065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(XOR(TMP_EREG1, reg_map[src1], reg_map[src2])); 185165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHRUI(TMP_EREG1, TMP_EREG1, 63)); 185265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 185365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src1 != dst) 185465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich overflow_ra = reg_map[src1]; 185565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else { 185665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Rare ocasion. */ 185765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(TMP_EREG2, reg_map[src1], ZERO)); 185865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich overflow_ra = TMP_EREG2; 185965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 186065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 186165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 186265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_E) 186365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SUB(EQUAL_FLAG, reg_map[src1], reg_map[src2])); 186465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 186565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & (SLJIT_SET_U | SLJIT_SET_C)) 186665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CMPLTU(ULESS_FLAG, reg_map[src1], reg_map[src2])); 186765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 186865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_U) 186965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CMPLTU(UGREATER_FLAG, reg_map[src2], reg_map[src1])); 187065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 187165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_S) { 187265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CMPLTS(LESS_FLAG ,reg_map[src1] ,reg_map[src2])); 187365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CMPLTS(GREATER_FLAG ,reg_map[src2] ,reg_map[src1])); 187465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 187565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 187665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* dst may be the same as src1 or src2. */ 187765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (CHECK_FLAGS(SLJIT_SET_E | SLJIT_SET_U | SLJIT_SET_S | SLJIT_SET_C)) 187865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SUB(reg_map[dst], reg_map[src1], reg_map[src2])); 187965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 188065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 188165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_O) { 188265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(XOR(OVERFLOW_FLAG, reg_map[dst], overflow_ra)); 188365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SHRUI(OVERFLOW_FLAG, OVERFLOW_FLAG, 63)); 188465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return CMOVEQZ(OVERFLOW_FLAG, TMP_EREG1, ZERO); 188565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 188665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 188765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 188865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 188965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_SUBC: 189065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((flags & SRC2_IMM) && src2 == SIMM_16BIT_MIN) { 189165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(TMP_REG2_mapped, ZERO, src2)); 189265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2 = TMP_REG2; 189365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flags &= ~SRC2_IMM; 189465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 189565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 189665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & SRC2_IMM) { 189765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_C) { 189865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(load_immediate(compiler, ADDR_TMP_mapped, -src2)); 189965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CMPLTU(TMP_EREG1, reg_map[src1], ADDR_TMP_mapped)); 190065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 190165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 190265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* dst may be the same as src1 or src2. */ 190365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDLI(reg_map[dst], reg_map[src1], -src2)); 190465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 190565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 190665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_C) 190765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CMPLTU(TMP_EREG1, reg_map[src1], reg_map[src2])); 190865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* dst may be the same as src1 or src2. */ 190965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SUB(reg_map[dst], reg_map[src1], reg_map[src2])); 191065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 191165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 191265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_C) 191365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CMOVEQZ(TMP_EREG1, reg_map[dst], ULESS_FLAG)); 191465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 191565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(SUB(reg_map[dst], reg_map[dst], ULESS_FLAG)); 191665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 191765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_C) 191865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(ULESS_FLAG, TMP_EREG1, ZERO)); 191965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 192065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 192165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 192265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define EMIT_LOGICAL(op_imm, op_norm) \ 192365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & SRC2_IMM) { \ 192465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(load_immediate(compiler, ADDR_TMP_mapped, src2)); \ 192565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_E) \ 192665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(push_3_buffer( \ 192765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler, op_norm, EQUAL_FLAG, reg_map[src1], \ 192865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ADDR_TMP_mapped, __LINE__)); \ 192965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (CHECK_FLAGS(SLJIT_SET_E)) \ 193065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(push_3_buffer( \ 193165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler, op_norm, reg_map[dst], reg_map[src1], \ 193265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ADDR_TMP_mapped, __LINE__)); \ 193365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { \ 193465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_E) \ 193565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(push_3_buffer( \ 193665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler, op_norm, EQUAL_FLAG, reg_map[src1], \ 193765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich reg_map[src2], __LINE__)); \ 193865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (CHECK_FLAGS(SLJIT_SET_E)) \ 193965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(push_3_buffer( \ 194065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler, op_norm, reg_map[dst], reg_map[src1], \ 194165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich reg_map[src2], __LINE__)); \ 194265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 194365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 194465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_AND: 194565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich EMIT_LOGICAL(TILEGX_OPC_ANDI, TILEGX_OPC_AND); 194665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 194765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 194865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_OR: 194965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich EMIT_LOGICAL(TILEGX_OPC_ORI, TILEGX_OPC_OR); 195065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 195165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 195265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_XOR: 195365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich EMIT_LOGICAL(TILEGX_OPC_XORI, TILEGX_OPC_XOR); 195465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 195565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 195665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define EMIT_SHIFT(op_imm, op_norm) \ 195765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & SRC2_IMM) { \ 195865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_E) \ 195965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(push_3_buffer( \ 196065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler, op_imm, EQUAL_FLAG, reg_map[src1], \ 196165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2 & 0x3F, __LINE__)); \ 196265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (CHECK_FLAGS(SLJIT_SET_E)) \ 196365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(push_3_buffer( \ 196465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler, op_imm, reg_map[dst], reg_map[src1], \ 196565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2 & 0x3F, __LINE__)); \ 196665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { \ 196765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_SET_E) \ 196865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(push_3_buffer( \ 196965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler, op_imm, reg_map[dst], reg_map[src1], \ 197065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2 & 0x3F, __LINE__)); \ 197165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (CHECK_FLAGS(SLJIT_SET_E)) \ 197265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(push_3_buffer( \ 197365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler, op_norm, reg_map[dst], reg_map[src1], \ 197465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich reg_map[src2], __LINE__)); \ 197565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 197665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 197765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_SHL: 197865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich EMIT_SHIFT(TILEGX_OPC_SHLI, TILEGX_OPC_SHL); 197965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 198065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 198165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_LSHR: 198265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich EMIT_SHIFT(TILEGX_OPC_SHRUI, TILEGX_OPC_SHRU); 198365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 198465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 198565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_ASHR: 198665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich EMIT_SHIFT(TILEGX_OPC_SHRSI, TILEGX_OPC_SHRS); 198765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 198865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 198965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 199065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT_STOP(); 199165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 199265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 199365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 199465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevichstatic sljit_si emit_op(struct sljit_compiler *compiler, sljit_si op, sljit_si flags, sljit_si dst, sljit_sw dstw, sljit_si src1, sljit_sw src1w, sljit_si src2, sljit_sw src2w) 199565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 199665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* arg1 goes to TMP_REG1 or src reg. 199765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich arg2 goes to TMP_REG2, imm or src reg. 199865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich TMP_REG3 can be used for caching. 199965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich result goes to TMP_REG2, so put result can use TMP_REG1 and TMP_REG3. */ 200065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si dst_r = TMP_REG2; 200165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si src1_r; 200265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_sw src2_r = 0; 200365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si sugg_src2_r = TMP_REG2; 200465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 200565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (!(flags & ALT_KEEP_CACHE)) { 200665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_arg = 0; 200765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_argw = 0; 200865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 200965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 201065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (SLJIT_UNLIKELY(dst == SLJIT_UNUSED)) { 201165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op >= SLJIT_MOV && op <= SLJIT_MOVU_SI && !(src2 & SLJIT_MEM)) 201265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 201365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (GET_FLAGS(op)) 201465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flags |= UNUSED_DEST; 201565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else if (FAST_IS_REG(dst)) { 201665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich dst_r = dst; 201765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flags |= REG_DEST; 201865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op >= SLJIT_MOV && op <= SLJIT_MOVU_SI) 201965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sugg_src2_r = dst_r; 202065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else if ((dst & SLJIT_MEM) && !getput_arg_fast(compiler, flags | ARG_TEST, TMP_REG1_mapped, dst, dstw)) 202165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flags |= SLOW_DEST; 202265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 202365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (flags & IMM_OP) { 202465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((src2 & SLJIT_IMM) && src2w) { 202565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((!(flags & LOGICAL_OP) 202665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich && (src2w <= SIMM_16BIT_MAX && src2w >= SIMM_16BIT_MIN)) 202765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich || ((flags & LOGICAL_OP) && !(src2w & ~UIMM_16BIT_MAX))) { 202865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flags |= SRC2_IMM; 202965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2_r = src2w; 203065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 203165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 203265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 203365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (!(flags & SRC2_IMM) && (flags & CUMULATIVE_OP) && (src1 & SLJIT_IMM) && src1w) { 203465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((!(flags & LOGICAL_OP) 203565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich && (src1w <= SIMM_16BIT_MAX && src1w >= SIMM_16BIT_MIN)) 203665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich || ((flags & LOGICAL_OP) && !(src1w & ~UIMM_16BIT_MAX))) { 203765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flags |= SRC2_IMM; 203865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2_r = src1w; 203965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 204065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* And swap arguments. */ 204165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src1 = src2; 204265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src1w = src2w; 204365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2 = SLJIT_IMM; 204465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* src2w = src2_r unneeded. */ 204565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 204665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 204765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 204865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 204965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Source 1. */ 205065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (FAST_IS_REG(src1)) { 205165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src1_r = src1; 205265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flags |= REG1_SOURCE; 205365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else if (src1 & SLJIT_IMM) { 205465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src1w) { 205565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(load_immediate(compiler, TMP_REG1_mapped, src1w)); 205665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src1_r = TMP_REG1; 205765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else 205865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src1_r = 0; 205965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 206065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (getput_arg_fast(compiler, flags | LOAD_DATA, TMP_REG1_mapped, src1, src1w)) 206165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(compiler->error); 206265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 206365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flags |= SLOW_SRC1; 206465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src1_r = TMP_REG1; 206565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 206665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 206765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Source 2. */ 206865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (FAST_IS_REG(src2)) { 206965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2_r = src2; 207065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flags |= REG2_SOURCE; 207165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (!(flags & REG_DEST) && op >= SLJIT_MOV && op <= SLJIT_MOVU_SI) 207265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich dst_r = src2_r; 207365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else if (src2 & SLJIT_IMM) { 207465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (!(flags & SRC2_IMM)) { 207565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src2w) { 207665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(load_immediate(compiler, reg_map[sugg_src2_r], src2w)); 207765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2_r = sugg_src2_r; 207865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 207965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2_r = 0; 208065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((op >= SLJIT_MOV && op <= SLJIT_MOVU_SI) && (dst & SLJIT_MEM)) 208165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich dst_r = 0; 208265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 208365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 208465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 208565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (getput_arg_fast(compiler, flags | LOAD_DATA, reg_map[sugg_src2_r], src2, src2w)) 208665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(compiler->error); 208765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 208865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flags |= SLOW_SRC2; 208965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2_r = sugg_src2_r; 209065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 209165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 209265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if ((flags & (SLOW_SRC1 | SLOW_SRC2)) == (SLOW_SRC1 | SLOW_SRC2)) { 209365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(src2_r == TMP_REG2); 209465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (!can_cache(src1, src1w, src2, src2w) && can_cache(src1, src1w, dst, dstw)) { 209565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(getput_arg(compiler, flags | LOAD_DATA, TMP_REG2_mapped, src2, src2w, src1, src1w)); 209665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(getput_arg(compiler, flags | LOAD_DATA, TMP_REG1_mapped, src1, src1w, dst, dstw)); 209765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 209865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(getput_arg(compiler, flags | LOAD_DATA, TMP_REG1_mapped, src1, src1w, src2, src2w)); 209965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(getput_arg(compiler, flags | LOAD_DATA, TMP_REG2_mapped, src2, src2w, dst, dstw)); 210065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 210165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else if (flags & SLOW_SRC1) 210265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(getput_arg(compiler, flags | LOAD_DATA, TMP_REG1_mapped, src1, src1w, dst, dstw)); 210365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else if (flags & SLOW_SRC2) 210465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(getput_arg(compiler, flags | LOAD_DATA, reg_map[sugg_src2_r], src2, src2w, dst, dstw)); 210565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 210665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(emit_single_op(compiler, op, flags, dst_r, src1_r, src2_r)); 210765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 210865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (dst & SLJIT_MEM) { 210965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (!(flags & SLOW_DEST)) { 211065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich getput_arg_fast(compiler, flags, reg_map[dst_r], dst, dstw); 211165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return compiler->error; 211265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 211365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 211465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return getput_arg(compiler, flags, reg_map[dst_r], dst, dstw, 0, 0); 211565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 211665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 211765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 211865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 211965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 212065de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_op_flags(struct sljit_compiler *compiler, sljit_si op, sljit_si dst, sljit_sw dstw, sljit_si src, sljit_sw srcw, sljit_si type) 212165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 212265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si sugg_dst_ar, dst_ar; 212365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si flags = GET_ALL_FLAGS(op); 212465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 212565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR(); 212665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_emit_op_flags(compiler, op, dst, dstw, src, srcw, type); 212765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ADJUST_LOCAL_OFFSET(dst, dstw); 212865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 212965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (dst == SLJIT_UNUSED) 213065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 213165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 213265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich op = GET_OPCODE(op); 213365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sugg_dst_ar = reg_map[(op < SLJIT_ADD && FAST_IS_REG(dst)) ? dst : TMP_REG2]; 213465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 213565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_arg = 0; 213665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich compiler->cache_argw = 0; 213765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op >= SLJIT_ADD && (src & SLJIT_MEM)) { 213865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ADJUST_LOCAL_OFFSET(src, srcw); 213965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(emit_op_mem2(compiler, WORD_DATA | LOAD_DATA, TMP_REG1_mapped, src, srcw, dst, dstw)); 214065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src = TMP_REG1; 214165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich srcw = 0; 214265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 214365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 214465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich switch (type) { 214565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_EQUAL: 214665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_NOT_EQUAL: 214765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CMPLTUI(sugg_dst_ar, EQUAL_FLAG, 1)); 214865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich dst_ar = sugg_dst_ar; 214965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 215065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_LESS: 215165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_GREATER_EQUAL: 215265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_FLOAT_LESS: 215365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_FLOAT_GREATER_EQUAL: 215465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich dst_ar = ULESS_FLAG; 215565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 215665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_GREATER: 215765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_LESS_EQUAL: 215865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_FLOAT_GREATER: 215965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_FLOAT_LESS_EQUAL: 216065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich dst_ar = UGREATER_FLAG; 216165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 216265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_SIG_LESS: 216365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_SIG_GREATER_EQUAL: 216465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich dst_ar = LESS_FLAG; 216565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 216665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_SIG_GREATER: 216765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_SIG_LESS_EQUAL: 216865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich dst_ar = GREATER_FLAG; 216965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 217065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_OVERFLOW: 217165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_NOT_OVERFLOW: 217265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich dst_ar = OVERFLOW_FLAG; 217365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 217465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_MUL_OVERFLOW: 217565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_MUL_NOT_OVERFLOW: 217665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(CMPLTUI(sugg_dst_ar, OVERFLOW_FLAG, 1)); 217765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich dst_ar = sugg_dst_ar; 217865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich type ^= 0x1; /* Flip type bit for the XORI below. */ 217965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 218065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_FLOAT_EQUAL: 218165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_FLOAT_NOT_EQUAL: 218265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich dst_ar = EQUAL_FLAG; 218365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 218465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 218565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich default: 218665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT_STOP(); 218765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich dst_ar = sugg_dst_ar; 218865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 218965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 219065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 219165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (type & 0x1) { 219265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(XORI(sugg_dst_ar, dst_ar, 1)); 219365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich dst_ar = sugg_dst_ar; 219465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 219565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 219665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op >= SLJIT_ADD) { 219765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (TMP_REG2_mapped != dst_ar) 219865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD(TMP_REG2_mapped, dst_ar, ZERO)); 219965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, op | flags, CUMULATIVE_OP | LOGICAL_OP | IMM_OP | ALT_KEEP_CACHE, dst, dstw, src, srcw, TMP_REG2, 0); 220065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 220165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 220265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (dst & SLJIT_MEM) 220365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op_mem(compiler, WORD_DATA, dst_ar, dst, dstw); 220465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 220565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (sugg_dst_ar != dst_ar) 220665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return ADD(sugg_dst_ar, dst_ar, ZERO); 220765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 220865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 220965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 221065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 221165de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_op0(struct sljit_compiler *compiler, sljit_si op) { 221265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR(); 221365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_emit_op0(compiler, op); 221465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 221565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich op = GET_OPCODE(op); 221665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich switch (op) { 221765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_NOP: 221865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return push_0_buffer(compiler, TILEGX_OPC_FNOP, __LINE__); 221965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 222065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_BREAKPOINT: 222165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return PI(BPT); 222265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 222365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_UMUL: 222465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_SMUL: 222565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_UDIV: 222665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_SDIV: 222765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT_STOP(); 222865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 222965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 223065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 223165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 223265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 223365de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_op1(struct sljit_compiler *compiler, sljit_si op, sljit_si dst, sljit_sw dstw, sljit_si src, sljit_sw srcw) 223465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 223565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR(); 223665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_emit_op1(compiler, op, dst, dstw, src, srcw); 223765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ADJUST_LOCAL_OFFSET(dst, dstw); 223865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ADJUST_LOCAL_OFFSET(src, srcw); 223965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 224065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich switch (GET_OPCODE(op)) { 224165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV: 224265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_P: 224365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV, WORD_DATA, dst, dstw, TMP_REG1, 0, src, srcw); 224465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 224565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_UI: 224665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV_UI, INT_DATA, dst, dstw, TMP_REG1, 0, src, srcw); 224765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 224865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_SI: 224965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV_SI, INT_DATA | SIGNED_DATA, dst, dstw, TMP_REG1, 0, src, srcw); 225065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 225165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_UB: 225265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV_UB, BYTE_DATA, dst, dstw, TMP_REG1, 0, src, (src & SLJIT_IMM) ? (sljit_ub) srcw : srcw); 225365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 225465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_SB: 225565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV_SB, BYTE_DATA | SIGNED_DATA, dst, dstw, TMP_REG1, 0, src, (src & SLJIT_IMM) ? (sljit_sb) srcw : srcw); 225665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 225765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_UH: 225865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV_UH, HALF_DATA, dst, dstw, TMP_REG1, 0, src, (src & SLJIT_IMM) ? (sljit_uh) srcw : srcw); 225965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 226065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOV_SH: 226165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV_SH, HALF_DATA | SIGNED_DATA, dst, dstw, TMP_REG1, 0, src, (src & SLJIT_IMM) ? (sljit_sh) srcw : srcw); 226265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 226365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOVU: 226465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOVU_P: 226565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV, WORD_DATA | WRITE_BACK, dst, dstw, TMP_REG1, 0, src, srcw); 226665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 226765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOVU_UI: 226865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV_UI, INT_DATA | WRITE_BACK, dst, dstw, TMP_REG1, 0, src, srcw); 226965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 227065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOVU_SI: 227165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV_SI, INT_DATA | SIGNED_DATA | WRITE_BACK, dst, dstw, TMP_REG1, 0, src, srcw); 227265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 227365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOVU_UB: 227465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV_UB, BYTE_DATA | WRITE_BACK, dst, dstw, TMP_REG1, 0, src, (src & SLJIT_IMM) ? (sljit_ub) srcw : srcw); 227565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 227665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOVU_SB: 227765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV_SB, BYTE_DATA | SIGNED_DATA | WRITE_BACK, dst, dstw, TMP_REG1, 0, src, (src & SLJIT_IMM) ? (sljit_sb) srcw : srcw); 227865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 227965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOVU_UH: 228065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV_UH, HALF_DATA | WRITE_BACK, dst, dstw, TMP_REG1, 0, src, (src & SLJIT_IMM) ? (sljit_uh) srcw : srcw); 228165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 228265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MOVU_SH: 228365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_MOV_SH, HALF_DATA | SIGNED_DATA | WRITE_BACK, dst, dstw, TMP_REG1, 0, src, (src & SLJIT_IMM) ? (sljit_sh) srcw : srcw); 228465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 228565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_NOT: 228665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, op, 0, dst, dstw, TMP_REG1, 0, src, srcw); 228765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 228865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_NEG: 228965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, SLJIT_SUB | GET_ALL_FLAGS(op), IMM_OP, dst, dstw, SLJIT_IMM, 0, src, srcw); 229065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 229165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_CLZ: 229265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, op, 0, dst, dstw, TMP_REG1, 0, src, srcw); 229365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 229465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 229565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 229665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 229765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 229865de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_op2(struct sljit_compiler *compiler, sljit_si op, sljit_si dst, sljit_sw dstw, sljit_si src1, sljit_sw src1w, sljit_si src2, sljit_sw src2w) 229965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 230065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR(); 230165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_emit_op2(compiler, op, dst, dstw, src1, src1w, src2, src2w); 230265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ADJUST_LOCAL_OFFSET(dst, dstw); 230365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ADJUST_LOCAL_OFFSET(src1, src1w); 230465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ADJUST_LOCAL_OFFSET(src2, src2w); 230565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 230665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich switch (GET_OPCODE(op)) { 230765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_ADD: 230865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_ADDC: 230965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, op, CUMULATIVE_OP | IMM_OP, dst, dstw, src1, src1w, src2, src2w); 231065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 231165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_SUB: 231265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_SUBC: 231365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, op, IMM_OP, dst, dstw, src1, src1w, src2, src2w); 231465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 231565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_MUL: 231665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, op, CUMULATIVE_OP, dst, dstw, src1, src1w, src2, src2w); 231765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 231865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_AND: 231965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_OR: 232065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_XOR: 232165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, op, CUMULATIVE_OP | LOGICAL_OP | IMM_OP, dst, dstw, src1, src1w, src2, src2w); 232265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 232365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_SHL: 232465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_LSHR: 232565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_ASHR: 232665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src2 & SLJIT_IMM) 232765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2w &= 0x3f; 232865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (op & SLJIT_INT_OP) 232965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src2w &= 0x1f; 233065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 233165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return emit_op(compiler, op, IMM_OP, dst, dstw, src1, src1w, src2, src2w); 233265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 233365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 233465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 233565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 233665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 233765de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE struct sljit_label * sljit_emit_label(struct sljit_compiler *compiler) 233865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 233965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich struct sljit_label *label; 234065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 234165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flush_buffer(compiler); 234265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 234365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR_PTR(); 234465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_emit_label(compiler); 234565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 234665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (compiler->last_label && compiler->last_label->size == compiler->size) 234765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return compiler->last_label; 234865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 234965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich label = (struct sljit_label *)ensure_abuf(compiler, sizeof(struct sljit_label)); 235065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich PTR_FAIL_IF(!label); 235165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich set_label(label, compiler); 235265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return label; 235365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 235465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 235565de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_ijump(struct sljit_compiler *compiler, sljit_si type, sljit_si src, sljit_sw srcw) 235665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 235765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si src_r = TMP_REG2; 235865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich struct sljit_jump *jump = NULL; 235965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 236065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flush_buffer(compiler); 236165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 236265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR(); 236365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_emit_ijump(compiler, type, src, srcw); 236465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ADJUST_LOCAL_OFFSET(src, srcw); 236565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 236665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (FAST_IS_REG(src)) { 236765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (reg_map[src] != 0) 236865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich src_r = src; 236965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else 237065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD_SOLO(TMP_REG2_mapped, reg_map[src], ZERO)); 237165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 237265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 237365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (type >= SLJIT_CALL0) { 237465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(reg_map[PIC_ADDR_REG] == 16 && PIC_ADDR_REG == TMP_REG2); 237565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src & (SLJIT_IMM | SLJIT_MEM)) { 237665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src & SLJIT_IMM) 237765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(emit_const(compiler, reg_map[PIC_ADDR_REG], srcw, 1)); 237865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich else { 237965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(src_r == TMP_REG2 && (src & SLJIT_MEM)); 238065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(emit_op(compiler, SLJIT_MOV, WORD_DATA, TMP_REG2, 0, TMP_REG1, 0, src, srcw)); 238165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 238265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 238365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD_SOLO(0, reg_map[SLJIT_R0], ZERO)); 238465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 238565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDI_SOLO(54, 54, -16)); 238665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 238765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(JALR_SOLO(reg_map[PIC_ADDR_REG])); 238865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 238965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return ADDI_SOLO(54, 54, 16); 239065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 239165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 239265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Register input. */ 239365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (type >= SLJIT_CALL1) 239465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD_SOLO(0, reg_map[SLJIT_R0], ZERO)); 239565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 239665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD_SOLO(reg_map[PIC_ADDR_REG], reg_map[src_r], ZERO)); 239765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 239865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADDI_SOLO(54, 54, -16)); 239965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 240065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(JALR_SOLO(reg_map[src_r])); 240165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 240265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return ADDI_SOLO(54, 54, 16); 240365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 240465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 240565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (src & SLJIT_IMM) { 240665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump = (struct sljit_jump *)ensure_abuf(compiler, sizeof(struct sljit_jump)); 240765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(!jump); 240865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich set_jump(jump, compiler, JUMP_ADDR | ((type >= SLJIT_FAST_CALL) ? IS_JAL : 0)); 240965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->u.target = srcw; 241065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(emit_const(compiler, TMP_REG2_mapped, 0, 1)); 241165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 241265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (type >= SLJIT_FAST_CALL) { 241365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(ADD_SOLO(ZERO, ZERO, ZERO)); 241465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->addr = compiler->size; 241565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(JR_SOLO(reg_map[src_r])); 241665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 241765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->addr = compiler->size; 241865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(JR_SOLO(reg_map[src_r])); 241965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 242065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 242165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 242265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 242365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else if (src & SLJIT_MEM) 242465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(emit_op(compiler, SLJIT_MOV, WORD_DATA, TMP_REG2, 0, TMP_REG1, 0, src, srcw)); 242565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 242665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich FAIL_IF(JR_SOLO(reg_map[src_r])); 242765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 242865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (jump) 242965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->addr = compiler->size; 243065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 243165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return SLJIT_SUCCESS; 243265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 243365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 243465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BR_Z(src) \ 243565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst = BEQZ_X1 | SRCA_X1(src); \ 243665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flags = IS_COND; 243765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 243865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich#define BR_NZ(src) \ 243965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst = BNEZ_X1 | SRCA_X1(src); \ 244065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flags = IS_COND; 244165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 244265de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE struct sljit_jump * sljit_emit_jump(struct sljit_compiler *compiler, sljit_si type) 244365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 244465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich struct sljit_jump *jump; 244565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins inst; 244665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si flags = 0; 244765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 244865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flush_buffer(compiler); 244965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 245065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR_PTR(); 245165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_emit_jump(compiler, type); 245265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 245365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump = (struct sljit_jump *)ensure_abuf(compiler, sizeof(struct sljit_jump)); 245465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich PTR_FAIL_IF(!jump); 245565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich set_jump(jump, compiler, type & SLJIT_REWRITABLE_JUMP); 245665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich type &= 0xff; 245765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 245865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich switch (type) { 245965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_EQUAL: 246065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_FLOAT_NOT_EQUAL: 246165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BR_NZ(EQUAL_FLAG); 246265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 246365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_NOT_EQUAL: 246465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_FLOAT_EQUAL: 246565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BR_Z(EQUAL_FLAG); 246665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 246765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_LESS: 246865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_FLOAT_LESS: 246965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BR_Z(ULESS_FLAG); 247065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 247165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_GREATER_EQUAL: 247265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_FLOAT_GREATER_EQUAL: 247365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BR_NZ(ULESS_FLAG); 247465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 247565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_GREATER: 247665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_FLOAT_GREATER: 247765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BR_Z(UGREATER_FLAG); 247865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 247965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_LESS_EQUAL: 248065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_FLOAT_LESS_EQUAL: 248165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BR_NZ(UGREATER_FLAG); 248265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 248365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_SIG_LESS: 248465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BR_Z(LESS_FLAG); 248565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 248665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_SIG_GREATER_EQUAL: 248765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BR_NZ(LESS_FLAG); 248865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 248965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_SIG_GREATER: 249065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BR_Z(GREATER_FLAG); 249165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 249265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_SIG_LESS_EQUAL: 249365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BR_NZ(GREATER_FLAG); 249465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 249565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_OVERFLOW: 249665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_MUL_OVERFLOW: 249765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BR_Z(OVERFLOW_FLAG); 249865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 249965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_NOT_OVERFLOW: 250065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich case SLJIT_C_MUL_NOT_OVERFLOW: 250165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich BR_NZ(OVERFLOW_FLAG); 250265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 250365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich default: 250465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Not conditional branch. */ 250565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst = 0; 250665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich break; 250765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 250865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 250965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->flags |= flags; 251065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 251165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (inst) { 251265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst = inst | ((type <= SLJIT_JUMP) ? BOFF_X1(5) : BOFF_X1(6)); 251365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich PTR_FAIL_IF(PI(inst)); 251465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 251565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 251665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich PTR_FAIL_IF(emit_const(compiler, TMP_REG2_mapped, 0, 1)); 251765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (type <= SLJIT_JUMP) { 251865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->addr = compiler->size; 251965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich PTR_FAIL_IF(JR_SOLO(TMP_REG2_mapped)); 252065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } else { 252165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT(reg_map[PIC_ADDR_REG] == 16 && PIC_ADDR_REG == TMP_REG2); 252265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich /* Cannot be optimized out if type is >= CALL0. */ 252365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->flags |= IS_JAL | (type >= SLJIT_CALL0 ? SLJIT_REWRITABLE_JUMP : 0); 252465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich PTR_FAIL_IF(ADD_SOLO(0, reg_map[SLJIT_R0], ZERO)); 252565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich jump->addr = compiler->size; 252665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich PTR_FAIL_IF(JALR_SOLO(TMP_REG2_mapped)); 252765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich } 252865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 252965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return jump; 253065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 253165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 253265de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_is_fpu_available(void) 253365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 253465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return 0; 253565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 253665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 253765de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_fop1(struct sljit_compiler *compiler, sljit_si op, sljit_si dst, sljit_sw dstw, sljit_si src, sljit_sw srcw) 253865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 253965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT_STOP(); 254065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 254165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 254265de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE sljit_si sljit_emit_fop2(struct sljit_compiler *compiler, sljit_si op, sljit_si dst, sljit_sw dstw, sljit_si src1, sljit_sw src1w, sljit_si src2, sljit_sw src2w) 254365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 254465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_ASSERT_STOP(); 254565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 254665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 254765de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE struct sljit_const * sljit_emit_const(struct sljit_compiler *compiler, sljit_si dst, sljit_sw dstw, sljit_sw init_value) 254865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 254965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich struct sljit_const *const_; 255065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_si reg; 255165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 255265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich flush_buffer(compiler); 255365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 255465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich CHECK_ERROR_PTR(); 255565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich check_sljit_emit_const(compiler, dst, dstw, init_value); 255665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich ADJUST_LOCAL_OFFSET(dst, dstw); 255765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 255865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich const_ = (struct sljit_const *)ensure_abuf(compiler, sizeof(struct sljit_const)); 255965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich PTR_FAIL_IF(!const_); 256065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich set_const(const_, compiler); 256165de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 256265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich reg = FAST_IS_REG(dst) ? dst : TMP_REG2; 256365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 256465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich PTR_FAIL_IF(emit_const_64(compiler, reg, init_value, 1)); 256565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 256665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich if (dst & SLJIT_MEM) 256765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich PTR_FAIL_IF(emit_op(compiler, SLJIT_MOV, WORD_DATA, dst, dstw, TMP_REG1, 0, TMP_REG2, 0)); 256865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich return const_; 256965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 257065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 257165de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE void sljit_set_jump_addr(sljit_uw addr, sljit_uw new_addr) 257265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 257365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins *inst = (sljit_ins *)addr; 257465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 257565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[0] = (inst[0] & ~(0xFFFFL << 43)) | (((new_addr >> 32) & 0xffff) << 43); 257665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[1] = (inst[1] & ~(0xFFFFL << 43)) | (((new_addr >> 16) & 0xffff) << 43); 257765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[2] = (inst[2] & ~(0xFFFFL << 43)) | ((new_addr & 0xffff) << 43); 257865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_CACHE_FLUSH(inst, inst + 3); 257965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 258065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 258165de34233da93a3d65c00b8aad3ff9aad44c57deNick KralevichSLJIT_API_FUNC_ATTRIBUTE void sljit_set_const(sljit_uw addr, sljit_sw new_constant) 258265de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich{ 258365de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich sljit_ins *inst = (sljit_ins *)addr; 258465de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich 258565de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[0] = (inst[0] & ~(0xFFFFL << 43)) | (((new_constant >> 48) & 0xFFFFL) << 43); 258665de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[1] = (inst[1] & ~(0xFFFFL << 43)) | (((new_constant >> 32) & 0xFFFFL) << 43); 258765de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[2] = (inst[2] & ~(0xFFFFL << 43)) | (((new_constant >> 16) & 0xFFFFL) << 43); 258865de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich inst[3] = (inst[3] & ~(0xFFFFL << 43)) | ((new_constant & 0xFFFFL) << 43); 258965de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich SLJIT_CACHE_FLUSH(inst, inst + 4); 259065de34233da93a3d65c00b8aad3ff9aad44c57deNick Kralevich} 2591