2 * mini-llvm.c: llvm "Backend" for the mono JIT
4 * Copyright 2009-2011 Novell Inc (http://www.novell.com)
5 * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
9 #include <mono/metadata/debug-helpers.h>
10 #include <mono/metadata/mempool-internals.h>
11 #include <mono/utils/mono-tls.h>
12 #include <mono/utils/mono-dl.h>
14 #ifndef __STDC_LIMIT_MACROS
15 #define __STDC_LIMIT_MACROS
17 #ifndef __STDC_CONSTANT_MACROS
18 #define __STDC_CONSTANT_MACROS
21 #include "llvm-c/Core.h"
22 #include "llvm-c/ExecutionEngine.h"
23 #include "llvm-c/BitWriter.h"
24 #include "llvm-c/Analysis.h"
26 #include "mini-llvm-cpp.h"
29 * Information associated by mono with LLVM modules.
33 LLVMValueRef throw, rethrow, throw_corlib_exception;
34 GHashTable *llvm_types;
36 const char *got_symbol;
37 GHashTable *plt_entries;
44 * Information associated by the backend with mono basic blocks.
47 LLVMBasicBlockRef bblock, end_bblock;
48 LLVMValueRef finally_ind;
49 gboolean added, invoke_target;
51 * If this bblock is the start of a finally clause, this is a list of bblocks it
52 * needs to branch to in ENDFINALLY.
54 GSList *call_handler_return_bbs;
56 * If this bblock is the start of a finally clause, this is the bblock that
57 * CALL_HANDLER needs to branch to.
59 LLVMBasicBlockRef call_handler_target_bb;
60 /* The list of switch statements generated by ENDFINALLY instructions */
61 GSList *endfinally_switch_ins_list;
66 * Structure containing emit state
71 /* Maps method names to the corresponding LLVMValueRef */
72 GHashTable *emitted_method_decls;
76 MonoLLVMModule *lmodule;
79 int sindex, default_index, ex_index;
80 LLVMBuilderRef builder;
81 LLVMValueRef *values, *addresses;
82 MonoType **vreg_cli_types;
84 MonoMethodSignature *sig;
86 GHashTable *region_to_handler;
87 LLVMBuilderRef alloca_builder;
88 LLVMValueRef last_alloca;
89 LLVMValueRef rgctx_arg;
90 LLVMTypeRef *vreg_types;
92 gboolean *unreachable;
101 MonoBasicBlock *in_bb;
106 * Instruction metadata
107 * This is the same as ins_info, but LREG != IREG.
115 #define MINI_OP(a,b,dest,src1,src2) dest, src1, src2, ' ',
116 #define MINI_OP3(a,b,dest,src1,src2,src3) dest, src1, src2, src3,
123 /* keep in sync with the enum in mini.h */
126 #include "mini-ops.h"
131 #if SIZEOF_VOID_P == 4
132 #define GET_LONG_IMM(ins) (((guint64)(ins)->inst_ms_word << 32) | (guint64)(guint32)(ins)->inst_ls_word)
134 #define GET_LONG_IMM(ins) ((ins)->inst_imm)
137 #define LLVM_INS_INFO(opcode) (&llvm_ins_info [((opcode) - OP_START - 1) * 4])
140 #define TRACE_FAILURE(msg) do { printf ("%s\n", msg); } while (0)
142 #define TRACE_FAILURE(msg)
146 #define IS_TARGET_X86 1
148 #define IS_TARGET_X86 0
152 #define IS_TARGET_AMD64 1
154 #define IS_TARGET_AMD64 0
157 #define LLVM_FAILURE(ctx, reason) do { \
158 TRACE_FAILURE (reason); \
159 (ctx)->cfg->exception_message = g_strdup (reason); \
160 (ctx)->cfg->disable_llvm = TRUE; \
164 #define CHECK_FAILURE(ctx) do { \
165 if ((ctx)->cfg->disable_llvm) \
169 static LLVMIntPredicate cond_to_llvm_cond [] = {
182 static LLVMRealPredicate fpcond_to_llvm_cond [] = {
195 static LLVMExecutionEngineRef ee;
196 static MonoNativeTlsKey current_cfg_tls_id;
198 static MonoLLVMModule jit_module, aot_module;
199 static gboolean jit_module_inited;
200 static int memset_param_count, memcpy_param_count;
201 static const char *memset_func_name;
202 static const char *memcpy_func_name;
204 static void init_jit_module (void);
209 * The LLVM type with width == sizeof (gpointer)
214 return sizeof (gpointer) == 8 ? LLVMInt64Type () : LLVMInt32Type ();
220 return sizeof (gpointer) == 8 ? LLVMPointerType (LLVMInt64Type (), 0) : LLVMPointerType (LLVMInt32Type (), 0);
226 return sizeof (gpointer) == 8 ? LLVMPointerType (LLVMInt64Type (), 0) : LLVMPointerType (LLVMInt32Type (), 0);
232 * Return the size of the LLVM representation of the vtype T.
235 get_vtype_size (MonoType *t)
239 size = mono_class_value_size (mono_class_from_mono_type (t), NULL);
241 while (size < 2 * sizeof (gpointer) && mono_is_power_of_two (size) == -1)
248 * simd_class_to_llvm_type:
250 * Return the LLVM type corresponding to the Mono.SIMD class KLASS
253 simd_class_to_llvm_type (EmitContext *ctx, MonoClass *klass)
255 if (!strcmp (klass->name, "Vector2d")) {
256 return LLVMVectorType (LLVMDoubleType (), 2);
257 } else if (!strcmp (klass->name, "Vector2l")) {
258 return LLVMVectorType (LLVMInt64Type (), 2);
259 } else if (!strcmp (klass->name, "Vector2ul")) {
260 return LLVMVectorType (LLVMInt64Type (), 2);
261 } else if (!strcmp (klass->name, "Vector4i")) {
262 return LLVMVectorType (LLVMInt32Type (), 4);
263 } else if (!strcmp (klass->name, "Vector4ui")) {
264 return LLVMVectorType (LLVMInt32Type (), 4);
265 } else if (!strcmp (klass->name, "Vector4f")) {
266 return LLVMVectorType (LLVMFloatType (), 4);
267 } else if (!strcmp (klass->name, "Vector8s")) {
268 return LLVMVectorType (LLVMInt16Type (), 8);
269 } else if (!strcmp (klass->name, "Vector8us")) {
270 return LLVMVectorType (LLVMInt16Type (), 8);
271 } else if (!strcmp (klass->name, "Vector16sb")) {
272 return LLVMVectorType (LLVMInt8Type (), 16);
273 } else if (!strcmp (klass->name, "Vector16b")) {
274 return LLVMVectorType (LLVMInt8Type (), 16);
276 printf ("%s\n", klass->name);
282 /* Return the 128 bit SIMD type corresponding to the mono type TYPE */
283 static inline G_GNUC_UNUSED LLVMTypeRef
284 type_to_simd_type (int type)
288 return LLVMVectorType (LLVMInt8Type (), 16);
290 return LLVMVectorType (LLVMInt16Type (), 8);
292 return LLVMVectorType (LLVMInt32Type (), 4);
294 return LLVMVectorType (LLVMInt64Type (), 2);
296 return LLVMVectorType (LLVMDoubleType (), 2);
298 return LLVMVectorType (LLVMFloatType (), 4);
300 g_assert_not_reached ();
308 * Return the LLVM type corresponding to T.
311 type_to_llvm_type (EmitContext *ctx, MonoType *t)
314 return LLVMPointerType (LLVMInt8Type (), 0);
317 return LLVMVoidType ();
319 return LLVMInt8Type ();
321 return LLVMInt16Type ();
323 return LLVMInt32Type ();
325 return LLVMInt8Type ();
327 return LLVMInt16Type ();
329 return LLVMInt32Type ();
330 case MONO_TYPE_BOOLEAN:
331 return LLVMInt8Type ();
334 return LLVMInt64Type ();
336 return LLVMInt16Type ();
338 return LLVMFloatType ();
340 return LLVMDoubleType ();
343 return IntPtrType ();
344 case MONO_TYPE_OBJECT:
345 case MONO_TYPE_CLASS:
346 case MONO_TYPE_ARRAY:
347 case MONO_TYPE_SZARRAY:
348 case MONO_TYPE_STRING:
350 return ObjRefType ();
353 /* Because of generic sharing */
354 return ObjRefType ();
355 case MONO_TYPE_GENERICINST:
356 if (!mono_type_generic_inst_is_valuetype (t))
357 return ObjRefType ();
359 case MONO_TYPE_VALUETYPE:
360 case MONO_TYPE_TYPEDBYREF: {
364 klass = mono_class_from_mono_type (t);
366 if (MONO_CLASS_IS_SIMD (ctx->cfg, klass))
367 return simd_class_to_llvm_type (ctx, klass);
370 return type_to_llvm_type (ctx, mono_class_enum_basetype (klass));
371 ltype = g_hash_table_lookup (ctx->lmodule->llvm_types, klass);
374 LLVMTypeRef *eltypes;
377 size = get_vtype_size (t);
379 eltypes = g_new (LLVMTypeRef, size);
380 for (i = 0; i < size; ++i)
381 eltypes [i] = LLVMInt8Type ();
383 name = mono_type_full_name (&klass->byval_arg);
384 ltype = LLVMStructCreateNamed (LLVMGetGlobalContext (), name);
385 LLVMStructSetBody (ltype, eltypes, size, FALSE);
386 g_hash_table_insert (ctx->lmodule->llvm_types, klass, ltype);
393 printf ("X: %d\n", t->type);
394 ctx->cfg->exception_message = g_strdup_printf ("type %s", mono_type_full_name (t));
395 ctx->cfg->disable_llvm = TRUE;
403 * Return whenever T is an unsigned int type.
406 type_is_unsigned (EmitContext *ctx, MonoType *t)
422 * type_to_llvm_arg_type:
424 * Same as type_to_llvm_type, but treat i8/i16 as i32.
427 type_to_llvm_arg_type (EmitContext *ctx, MonoType *t)
429 LLVMTypeRef ptype = type_to_llvm_type (ctx, t);
431 if (ptype == LLVMInt8Type () || ptype == LLVMInt16Type ()) {
433 * LLVM generates code which only sets the lower bits, while JITted
434 * code expects all the bits to be set.
436 ptype = LLVMInt32Type ();
443 * llvm_type_to_stack_type:
445 * Return the LLVM type which needs to be used when a value of type TYPE is pushed
448 static G_GNUC_UNUSED LLVMTypeRef
449 llvm_type_to_stack_type (LLVMTypeRef type)
453 if (type == LLVMInt8Type ())
454 return LLVMInt32Type ();
455 else if (type == LLVMInt16Type ())
456 return LLVMInt32Type ();
457 else if (type == LLVMFloatType ())
458 return LLVMDoubleType ();
464 * regtype_to_llvm_type:
466 * Return the LLVM type corresponding to the regtype C used in instruction
470 regtype_to_llvm_type (char c)
474 return LLVMInt32Type ();
476 return LLVMInt64Type ();
478 return LLVMDoubleType ();
487 * Return the LLVM type corresponding to the unary/binary opcode OPCODE.
490 op_to_llvm_type (int opcode)
495 return LLVMInt8Type ();
498 return LLVMInt8Type ();
501 return LLVMInt16Type ();
504 return LLVMInt16Type ();
507 return LLVMInt32Type ();
510 return LLVMInt32Type ();
512 return LLVMInt64Type ();
514 return LLVMFloatType ();
516 return LLVMDoubleType ();
518 return LLVMInt64Type ();
520 return LLVMInt32Type ();
522 return LLVMInt64Type ();
525 return LLVMInt8Type ();
528 return LLVMInt16Type ();
531 return sizeof (gpointer) == 8 ? LLVMInt64Type () : LLVMInt32Type ();
538 return LLVMInt32Type ();
545 return LLVMInt64Type ();
547 printf ("%s\n", mono_inst_name (opcode));
548 g_assert_not_reached ();
554 * load_store_to_llvm_type:
556 * Return the size/sign/zero extension corresponding to the load/store opcode
560 load_store_to_llvm_type (int opcode, int *size, gboolean *sext, gboolean *zext)
566 case OP_LOADI1_MEMBASE:
567 case OP_STOREI1_MEMBASE_REG:
568 case OP_STOREI1_MEMBASE_IMM:
571 return LLVMInt8Type ();
572 case OP_LOADU1_MEMBASE:
576 return LLVMInt8Type ();
577 case OP_LOADI2_MEMBASE:
578 case OP_STOREI2_MEMBASE_REG:
579 case OP_STOREI2_MEMBASE_IMM:
582 return LLVMInt16Type ();
583 case OP_LOADU2_MEMBASE:
587 return LLVMInt16Type ();
588 case OP_LOADI4_MEMBASE:
589 case OP_LOADU4_MEMBASE:
592 case OP_STOREI4_MEMBASE_REG:
593 case OP_STOREI4_MEMBASE_IMM:
595 return LLVMInt32Type ();
596 case OP_LOADI8_MEMBASE:
598 case OP_STOREI8_MEMBASE_REG:
599 case OP_STOREI8_MEMBASE_IMM:
601 return LLVMInt64Type ();
602 case OP_LOADR4_MEMBASE:
603 case OP_STORER4_MEMBASE_REG:
605 return LLVMFloatType ();
606 case OP_LOADR8_MEMBASE:
607 case OP_STORER8_MEMBASE_REG:
609 return LLVMDoubleType ();
610 case OP_LOAD_MEMBASE:
612 case OP_STORE_MEMBASE_REG:
613 case OP_STORE_MEMBASE_IMM:
614 *size = sizeof (gpointer);
615 return IntPtrType ();
617 g_assert_not_reached ();
625 * Return the LLVM intrinsics corresponding to the overflow opcode OPCODE.
628 ovf_op_to_intrins (int opcode)
632 return "llvm.sadd.with.overflow.i32";
634 return "llvm.uadd.with.overflow.i32";
636 return "llvm.ssub.with.overflow.i32";
638 return "llvm.usub.with.overflow.i32";
640 return "llvm.smul.with.overflow.i32";
642 return "llvm.umul.with.overflow.i32";
644 return "llvm.sadd.with.overflow.i64";
646 return "llvm.uadd.with.overflow.i64";
648 return "llvm.ssub.with.overflow.i64";
650 return "llvm.usub.with.overflow.i64";
652 return "llvm.smul.with.overflow.i64";
654 return "llvm.umul.with.overflow.i64";
656 g_assert_not_reached ();
662 simd_op_to_intrins (int opcode)
665 #if defined(TARGET_X86) || defined(TARGET_AMD64)
667 return "llvm.x86.sse2.min.pd";
669 return "llvm.x86.sse.min.ps";
671 return "llvm.x86.sse41.pminud";
673 return "llvm.x86.sse41.pminuw";
675 return "llvm.x86.sse2.pminu.b";
677 return "llvm.x86.sse2.pmins.w";
679 return "llvm.x86.sse2.max.pd";
681 return "llvm.x86.sse.max.ps";
683 return "llvm.x86.sse3.hadd.pd";
685 return "llvm.x86.sse3.hadd.ps";
687 return "llvm.x86.sse3.hsub.pd";
689 return "llvm.x86.sse3.hsub.ps";
691 return "llvm.x86.sse41.pmaxud";
693 return "llvm.x86.sse41.pmaxuw";
695 return "llvm.x86.sse2.pmaxu.b";
697 return "llvm.x86.sse3.addsub.ps";
699 return "llvm.x86.sse3.addsub.pd";
700 case OP_EXTRACT_MASK:
701 return "llvm.x86.sse2.pmovmskb.128";
704 return "llvm.x86.sse2.psrli.w";
707 return "llvm.x86.sse2.psrli.d";
710 return "llvm.x86.sse2.psrli.q";
713 return "llvm.x86.sse2.pslli.w";
716 return "llvm.x86.sse2.pslli.d";
719 return "llvm.x86.sse2.pslli.q";
722 return "llvm.x86.sse2.psrai.w";
725 return "llvm.x86.sse2.psrai.d";
727 return "llvm.x86.sse2.padds.b";
729 return "llvm.x86.sse2.padds.w";
731 return "llvm.x86.sse2.psubs.b";
733 return "llvm.x86.sse2.psubs.w";
734 case OP_PADDB_SAT_UN:
735 return "llvm.x86.sse2.paddus.b";
736 case OP_PADDW_SAT_UN:
737 return "llvm.x86.sse2.paddus.w";
738 case OP_PSUBB_SAT_UN:
739 return "llvm.x86.sse2.psubus.b";
740 case OP_PSUBW_SAT_UN:
741 return "llvm.x86.sse2.psubus.w";
743 return "llvm.x86.sse2.pavg.b";
745 return "llvm.x86.sse2.pavg.w";
747 return "llvm.x86.sse.sqrt.ps";
749 return "llvm.x86.sse2.sqrt.pd";
751 return "llvm.x86.sse.rsqrt.ps";
753 return "llvm.x86.sse.rcp.ps";
755 return "llvm.x86.sse2.cvtdq2pd";
757 return "llvm.x86.sse2.cvtdq2ps";
759 return "llvm.x86.sse2.cvtpd2dq";
761 return "llvm.x86.sse2.cvtps2dq";
763 return "llvm.x86.sse2.cvtpd2ps";
765 return "llvm.x86.sse2.cvtps2pd";
767 return "llvm.x86.sse2.cvttpd2dq";
769 return "llvm.x86.sse2.cvttps2dq";
771 return "llvm.x86.sse.cmp.ps";
773 return "llvm.x86.sse2.cmp.pd";
775 return "llvm.x86.sse2.packsswb.128";
777 return "llvm.x86.sse2.packssdw.128";
779 return "llvm.x86.sse2.packuswb.128";
781 return "llvm.x86.sse41.packusdw";
783 return "llvm.x86.sse2.pmulh.w";
784 case OP_PMULW_HIGH_UN:
785 return "llvm.x86.sse2.pmulhu.w";
788 g_assert_not_reached ();
794 simd_op_to_llvm_type (int opcode)
796 #if defined(TARGET_X86) || defined(TARGET_AMD64)
800 return type_to_simd_type (MONO_TYPE_R8);
803 return type_to_simd_type (MONO_TYPE_I8);
806 return type_to_simd_type (MONO_TYPE_I4);
811 return type_to_simd_type (MONO_TYPE_I2);
815 return type_to_simd_type (MONO_TYPE_I1);
817 return type_to_simd_type (MONO_TYPE_R4);
820 return type_to_simd_type (MONO_TYPE_I4);
824 return type_to_simd_type (MONO_TYPE_R8);
828 return type_to_simd_type (MONO_TYPE_R4);
829 case OP_EXTRACT_MASK:
830 return type_to_simd_type (MONO_TYPE_I1);
836 return type_to_simd_type (MONO_TYPE_R4);
839 return type_to_simd_type (MONO_TYPE_R8);
841 g_assert_not_reached ();
852 * Return the LLVM basic block corresponding to BB.
854 static LLVMBasicBlockRef
855 get_bb (EmitContext *ctx, MonoBasicBlock *bb)
857 char bb_name_buf [128];
860 if (ctx->bblocks [bb->block_num].bblock == NULL) {
861 if (bb->flags & BB_EXCEPTION_HANDLER) {
862 int clause_index = (mono_get_block_region_notry (ctx->cfg, bb->region) >> 8) - 1;
863 sprintf (bb_name_buf, "EH_CLAUSE%d_BB%d", clause_index, bb->block_num);
864 bb_name = bb_name_buf;
865 } else if (bb->block_num < 256) {
866 if (!ctx->lmodule->bb_names)
867 ctx->lmodule->bb_names = g_new0 (char*, 256);
868 if (!ctx->lmodule->bb_names [bb->block_num]) {
871 n = g_strdup_printf ("BB%d", bb->block_num);
872 mono_memory_barrier ();
873 ctx->lmodule->bb_names [bb->block_num] = n;
875 bb_name = ctx->lmodule->bb_names [bb->block_num];
877 sprintf (bb_name_buf, "BB%d", bb->block_num);
878 bb_name = bb_name_buf;
881 ctx->bblocks [bb->block_num].bblock = LLVMAppendBasicBlock (ctx->lmethod, bb_name);
882 ctx->bblocks [bb->block_num].end_bblock = ctx->bblocks [bb->block_num].bblock;
885 return ctx->bblocks [bb->block_num].bblock;
891 * Return the last LLVM bblock corresponding to BB.
892 * This might not be equal to the bb returned by get_bb () since we need to generate
893 * multiple LLVM bblocks for a mono bblock to handle throwing exceptions.
895 static LLVMBasicBlockRef
896 get_end_bb (EmitContext *ctx, MonoBasicBlock *bb)
899 return ctx->bblocks [bb->block_num].end_bblock;
902 static LLVMBasicBlockRef
903 gen_bb (EmitContext *ctx, const char *prefix)
907 sprintf (bb_name, "%s%d", prefix, ++ ctx->ex_index);
908 return LLVMAppendBasicBlock (ctx->lmethod, bb_name);
914 * Return the target of the patch identified by TYPE and TARGET.
917 resolve_patch (MonoCompile *cfg, MonoJumpInfoType type, gconstpointer target)
921 memset (&ji, 0, sizeof (ji));
923 ji.data.target = target;
925 return mono_resolve_patch_target (cfg->method, cfg->domain, NULL, &ji, FALSE);
931 * Emit code to convert the LLVM value V to DTYPE.
934 convert_full (EmitContext *ctx, LLVMValueRef v, LLVMTypeRef dtype, gboolean is_unsigned)
936 LLVMTypeRef stype = LLVMTypeOf (v);
938 if (stype != dtype) {
939 gboolean ext = FALSE;
942 if (dtype == LLVMInt64Type () && (stype == LLVMInt32Type () || stype == LLVMInt16Type () || stype == LLVMInt8Type ()))
944 else if (dtype == LLVMInt32Type () && (stype == LLVMInt16Type () || stype == LLVMInt8Type ()))
946 else if (dtype == LLVMInt16Type () && (stype == LLVMInt8Type ()))
950 return is_unsigned ? LLVMBuildZExt (ctx->builder, v, dtype, "") : LLVMBuildSExt (ctx->builder, v, dtype, "");
952 if (dtype == LLVMDoubleType () && stype == LLVMFloatType ())
953 return LLVMBuildFPExt (ctx->builder, v, dtype, "");
956 if (stype == LLVMInt64Type () && (dtype == LLVMInt32Type () || dtype == LLVMInt16Type () || dtype == LLVMInt8Type ()))
957 return LLVMBuildTrunc (ctx->builder, v, dtype, "");
958 if (stype == LLVMInt32Type () && (dtype == LLVMInt16Type () || dtype == LLVMInt8Type ()))
959 return LLVMBuildTrunc (ctx->builder, v, dtype, "");
960 if (stype == LLVMInt16Type () && dtype == LLVMInt8Type ())
961 return LLVMBuildTrunc (ctx->builder, v, dtype, "");
962 if (stype == LLVMDoubleType () && dtype == LLVMFloatType ())
963 return LLVMBuildFPTrunc (ctx->builder, v, dtype, "");
965 if (LLVMGetTypeKind (stype) == LLVMPointerTypeKind && LLVMGetTypeKind (dtype) == LLVMPointerTypeKind)
966 return LLVMBuildBitCast (ctx->builder, v, dtype, "");
967 if (LLVMGetTypeKind (dtype) == LLVMPointerTypeKind)
968 return LLVMBuildIntToPtr (ctx->builder, v, dtype, "");
969 if (LLVMGetTypeKind (stype) == LLVMPointerTypeKind)
970 return LLVMBuildPtrToInt (ctx->builder, v, dtype, "");
972 if (mono_arch_is_soft_float ()) {
973 if (stype == LLVMInt32Type () && dtype == LLVMFloatType ())
974 return LLVMBuildBitCast (ctx->builder, v, dtype, "");
975 if (stype == LLVMInt32Type () && dtype == LLVMDoubleType ())
976 return LLVMBuildBitCast (ctx->builder, LLVMBuildZExt (ctx->builder, v, LLVMInt64Type (), ""), dtype, "");
979 if (LLVMGetTypeKind (stype) == LLVMVectorTypeKind && LLVMGetTypeKind (dtype) == LLVMVectorTypeKind)
980 return LLVMBuildBitCast (ctx->builder, v, dtype, "");
983 LLVMDumpValue (LLVMConstNull (dtype));
984 g_assert_not_reached ();
992 convert (EmitContext *ctx, LLVMValueRef v, LLVMTypeRef dtype)
994 return convert_full (ctx, v, dtype, FALSE);
998 * emit_volatile_load:
1000 * If vreg is volatile, emit a load from its address.
1003 emit_volatile_load (EmitContext *ctx, int vreg)
1007 LLVMValueRef v = LLVMBuildLoad (ctx->builder, ctx->addresses [vreg], "");
1008 t = ctx->vreg_cli_types [vreg];
1009 if (t && !t->byref) {
1011 * Might have to zero extend since llvm doesn't have
1014 if (t->type == MONO_TYPE_U1 || t->type == MONO_TYPE_U2 || t->type == MONO_TYPE_CHAR || t->type == MONO_TYPE_BOOLEAN)
1015 v = LLVMBuildZExt (ctx->builder, v, LLVMInt32Type (), "");
1016 else if (t->type == MONO_TYPE_U8)
1017 v = LLVMBuildZExt (ctx->builder, v, LLVMInt64Type (), "");
1024 * emit_volatile_store:
1026 * If VREG is volatile, emit a store from its value to its address.
1029 emit_volatile_store (EmitContext *ctx, int vreg)
1031 MonoInst *var = get_vreg_to_inst (ctx->cfg, vreg);
1033 if (var && var->flags & (MONO_INST_VOLATILE|MONO_INST_INDIRECT)) {
1034 g_assert (ctx->addresses [vreg]);
1035 LLVMBuildStore (ctx->builder, convert (ctx, ctx->values [vreg], type_to_llvm_type (ctx, var->inst_vtype)), ctx->addresses [vreg]);
1041 * Maps parameter indexes in the original signature to parameter indexes
1042 * in the LLVM signature.
1045 /* The indexes of various special arguments in the LLVM signature */
1046 int vret_arg_pindex, this_arg_pindex, rgctx_arg_pindex, imt_arg_pindex;
1050 * sig_to_llvm_sig_full:
1052 * Return the LLVM signature corresponding to the mono signature SIG using the
1053 * calling convention information in CINFO. Return parameter mapping information in SINFO.
1056 sig_to_llvm_sig_full (EmitContext *ctx, MonoMethodSignature *sig, LLVMCallInfo *cinfo,
1059 LLVMTypeRef ret_type;
1060 LLVMTypeRef *param_types = NULL;
1062 int i, j, pindex, vret_arg_pindex = 0;
1064 gboolean vretaddr = FALSE;
1067 memset (sinfo, 0, sizeof (LLVMSigInfo));
1069 ret_type = type_to_llvm_type (ctx, sig->ret);
1070 CHECK_FAILURE (ctx);
1072 if (cinfo && cinfo->ret.storage == LLVMArgVtypeInReg) {
1073 /* LLVM models this by returning an aggregate value */
1074 if (cinfo->ret.pair_storage [0] == LLVMArgInIReg && cinfo->ret.pair_storage [1] == LLVMArgNone) {
1075 LLVMTypeRef members [2];
1077 members [0] = IntPtrType ();
1078 ret_type = LLVMStructType (members, 1, FALSE);
1080 g_assert_not_reached ();
1082 } else if (cinfo && mini_type_is_vtype (ctx->cfg, sig->ret)) {
1083 g_assert (cinfo->ret.storage == LLVMArgVtypeRetAddr);
1085 ret_type = LLVMVoidType ();
1088 pindexes = g_new0 (int, sig->param_count);
1089 param_types = g_new0 (LLVMTypeRef, (sig->param_count * 2) + 3);
1091 if (cinfo && cinfo->rgctx_arg) {
1093 sinfo->rgctx_arg_pindex = pindex;
1094 param_types [pindex] = ctx->lmodule->ptr_type;
1097 if (cinfo && cinfo->imt_arg) {
1099 sinfo->imt_arg_pindex = pindex;
1100 param_types [pindex] = ctx->lmodule->ptr_type;
1104 /* Compute the index in the LLVM signature where the vret arg needs to be passed */
1105 vret_arg_pindex = pindex;
1106 if (cinfo->vret_arg_index == 1) {
1107 /* Add the slots consumed by the first argument */
1108 LLVMArgInfo *ainfo = &cinfo->args [0];
1109 switch (ainfo->storage) {
1110 case LLVMArgVtypeInReg:
1111 for (j = 0; j < 2; ++j) {
1112 if (ainfo->pair_storage [j] == LLVMArgInIReg)
1122 sinfo->vret_arg_pindex = vret_arg_pindex;
1125 if (vretaddr && vret_arg_pindex == pindex)
1126 param_types [pindex ++] = IntPtrType ();
1129 sinfo->this_arg_pindex = pindex;
1130 param_types [pindex ++] = ThisType ();
1132 if (vretaddr && vret_arg_pindex == pindex)
1133 param_types [pindex ++] = IntPtrType ();
1134 for (i = 0; i < sig->param_count; ++i) {
1135 if (vretaddr && vret_arg_pindex == pindex)
1136 param_types [pindex ++] = IntPtrType ();
1137 pindexes [i] = pindex;
1138 if (cinfo && cinfo->args [i + sig->hasthis].storage == LLVMArgVtypeInReg) {
1139 for (j = 0; j < 2; ++j) {
1140 switch (cinfo->args [i + sig->hasthis].pair_storage [j]) {
1142 param_types [pindex ++] = LLVMIntType (sizeof (gpointer) * 8);
1147 g_assert_not_reached ();
1150 } else if (cinfo && cinfo->args [i + sig->hasthis].storage == LLVMArgVtypeByVal) {
1151 param_types [pindex] = type_to_llvm_arg_type (ctx, sig->params [i]);
1152 CHECK_FAILURE (ctx);
1153 param_types [pindex] = LLVMPointerType (param_types [pindex], 0);
1156 param_types [pindex ++] = type_to_llvm_arg_type (ctx, sig->params [i]);
1159 if (vretaddr && vret_arg_pindex == pindex)
1160 param_types [pindex ++] = IntPtrType ();
1162 CHECK_FAILURE (ctx);
1164 res = LLVMFunctionType (ret_type, param_types, pindex, FALSE);
1165 g_free (param_types);
1168 sinfo->pindexes = pindexes;
1176 g_free (param_types);
1182 sig_to_llvm_sig (EmitContext *ctx, MonoMethodSignature *sig)
1184 return sig_to_llvm_sig_full (ctx, sig, NULL, NULL);
1188 * LLVMFunctionType1:
1190 * Create an LLVM function type from the arguments.
1192 static G_GNUC_UNUSED LLVMTypeRef
1193 LLVMFunctionType1(LLVMTypeRef ReturnType,
1194 LLVMTypeRef ParamType1,
1197 LLVMTypeRef param_types [1];
1199 param_types [0] = ParamType1;
1201 return LLVMFunctionType (ReturnType, param_types, 1, IsVarArg);
1205 * LLVMFunctionType2:
1207 * Create an LLVM function type from the arguments.
1209 static G_GNUC_UNUSED LLVMTypeRef
1210 LLVMFunctionType2(LLVMTypeRef ReturnType,
1211 LLVMTypeRef ParamType1,
1212 LLVMTypeRef ParamType2,
1215 LLVMTypeRef param_types [2];
1217 param_types [0] = ParamType1;
1218 param_types [1] = ParamType2;
1220 return LLVMFunctionType (ReturnType, param_types, 2, IsVarArg);
1224 * LLVMFunctionType3:
1226 * Create an LLVM function type from the arguments.
1228 static G_GNUC_UNUSED LLVMTypeRef
1229 LLVMFunctionType3(LLVMTypeRef ReturnType,
1230 LLVMTypeRef ParamType1,
1231 LLVMTypeRef ParamType2,
1232 LLVMTypeRef ParamType3,
1235 LLVMTypeRef param_types [3];
1237 param_types [0] = ParamType1;
1238 param_types [1] = ParamType2;
1239 param_types [2] = ParamType3;
1241 return LLVMFunctionType (ReturnType, param_types, 3, IsVarArg);
1247 * Create an LLVM builder and remember it so it can be freed later.
1249 static LLVMBuilderRef
1250 create_builder (EmitContext *ctx)
1252 LLVMBuilderRef builder = LLVMCreateBuilder ();
1254 ctx->builders = g_slist_prepend_mempool (ctx->cfg->mempool, ctx->builders, builder);
1260 get_plt_entry (EmitContext *ctx, LLVMTypeRef llvm_sig, MonoJumpInfoType type, gconstpointer data)
1262 char *callee_name = mono_aot_get_plt_symbol (type, data);
1263 LLVMValueRef callee;
1268 if (ctx->cfg->compile_aot)
1269 /* Add a patch so referenced wrappers can be compiled in full aot mode */
1270 mono_add_patch_info (ctx->cfg, 0, type, data);
1273 callee = g_hash_table_lookup (ctx->lmodule->plt_entries, callee_name);
1275 callee = LLVMAddFunction (ctx->module, callee_name, llvm_sig);
1277 LLVMSetVisibility (callee, LLVMHiddenVisibility);
1279 g_hash_table_insert (ctx->lmodule->plt_entries, (char*)callee_name, callee);
1286 get_handler_clause (MonoCompile *cfg, MonoBasicBlock *bb)
1288 MonoMethodHeader *header = cfg->header;
1289 MonoExceptionClause *clause;
1293 if (bb->region != -1 && MONO_BBLOCK_IS_IN_REGION (bb, MONO_REGION_TRY))
1294 return (bb->region >> 8) - 1;
1297 for (i = 0; i < header->num_clauses; ++i) {
1298 clause = &header->clauses [i];
1300 if (MONO_OFFSET_IN_CLAUSE (clause, bb->real_offset) && clause->flags == MONO_EXCEPTION_CLAUSE_NONE)
1308 set_metadata_flag (LLVMValueRef v, const char *flag_name)
1310 LLVMValueRef md_arg;
1313 md_kind = LLVMGetMDKindID (flag_name, strlen (flag_name));
1314 md_arg = LLVMMDString ("mono", 4);
1315 LLVMSetMetadata (v, md_kind, LLVMMDNode (&md_arg, 1));
1319 set_invariant_load_flag (LLVMValueRef v)
1321 LLVMValueRef md_arg;
1323 const char *flag_name;
1325 // FIXME: Cache this
1326 flag_name = "invariant.load";
1327 md_kind = LLVMGetMDKindID (flag_name, strlen (flag_name));
1328 md_arg = LLVMMDString ("<index>", strlen ("<index>"));
1329 LLVMSetMetadata (v, md_kind, LLVMMDNode (&md_arg, 1));
1335 * Emit an LLVM call or invoke instruction depending on whenever the call is inside
1339 emit_call (EmitContext *ctx, MonoBasicBlock *bb, LLVMBuilderRef *builder_ref, LLVMValueRef callee, LLVMValueRef *args, int pindex)
1341 MonoCompile *cfg = ctx->cfg;
1343 LLVMBuilderRef builder = *builder_ref;
1346 clause_index = get_handler_clause (cfg, bb);
1348 if (clause_index != -1) {
1349 MonoMethodHeader *header = cfg->header;
1350 MonoExceptionClause *ec = &header->clauses [clause_index];
1351 MonoBasicBlock *tblock;
1352 LLVMBasicBlockRef ex_bb, noex_bb;
1355 * Have to use an invoke instead of a call, branching to the
1356 * handler bblock of the clause containing this bblock.
1359 g_assert (ec->flags == MONO_EXCEPTION_CLAUSE_NONE || ec->flags == MONO_EXCEPTION_CLAUSE_FINALLY);
1361 tblock = cfg->cil_offset_to_bb [ec->handler_offset];
1364 ctx->bblocks [tblock->block_num].invoke_target = TRUE;
1366 ex_bb = get_bb (ctx, tblock);
1368 noex_bb = gen_bb (ctx, "NOEX_BB");
1371 lcall = LLVMBuildInvoke (builder, callee, args, pindex, noex_bb, ex_bb, "");
1373 builder = ctx->builder = create_builder (ctx);
1374 LLVMPositionBuilderAtEnd (ctx->builder, noex_bb);
1376 ctx->bblocks [bb->block_num].end_bblock = noex_bb;
1378 lcall = LLVMBuildCall (builder, callee, args, pindex, "");
1379 ctx->builder = builder;
1382 *builder_ref = ctx->builder;
1388 emit_load (EmitContext *ctx, MonoBasicBlock *bb, LLVMBuilderRef *builder_ref, int size, LLVMValueRef addr, const char *name, gboolean is_faulting)
1390 const char *intrins_name;
1391 LLVMValueRef args [16], res;
1392 LLVMTypeRef addr_type;
1394 if (is_faulting && bb->region != -1) {
1396 * We handle loads which can fault by calling a mono specific intrinsic
1397 * using an invoke, so they are handled properly inside try blocks.
1398 * We can't use this outside clauses, since LLVM optimizes intrinsics which
1399 * are marked with IntrReadArgMem.
1403 intrins_name = "llvm.mono.load.i8.p0i8";
1406 intrins_name = "llvm.mono.load.i16.p0i16";
1409 intrins_name = "llvm.mono.load.i32.p0i32";
1412 intrins_name = "llvm.mono.load.i64.p0i64";
1415 g_assert_not_reached ();
1418 addr_type = LLVMTypeOf (addr);
1419 if (addr_type == LLVMPointerType (LLVMDoubleType (), 0) || addr_type == LLVMPointerType (LLVMFloatType (), 0))
1420 addr = LLVMBuildBitCast (*builder_ref, addr, LLVMPointerType (LLVMIntType (size * 8), 0), "");
1423 args [1] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
1424 args [2] = LLVMConstInt (LLVMInt1Type (), TRUE, FALSE);
1425 res = emit_call (ctx, bb, builder_ref, LLVMGetNamedFunction (ctx->module, intrins_name), args, 3);
1427 if (addr_type == LLVMPointerType (LLVMDoubleType (), 0))
1428 res = LLVMBuildBitCast (*builder_ref, res, LLVMDoubleType (), "");
1429 else if (addr_type == LLVMPointerType (LLVMFloatType (), 0))
1430 res = LLVMBuildBitCast (*builder_ref, res, LLVMFloatType (), "");
1437 * We emit volatile loads for loads which can fault, because otherwise
1438 * LLVM will generate invalid code when encountering a load from a
1441 res = mono_llvm_build_load (*builder_ref, addr, name, is_faulting);
1443 /* Mark it with a custom metadata */
1446 set_metadata_flag (res, "mono.faulting.load");
1454 emit_store (EmitContext *ctx, MonoBasicBlock *bb, LLVMBuilderRef *builder_ref, int size, LLVMValueRef value, LLVMValueRef addr, gboolean is_faulting)
1456 const char *intrins_name;
1457 LLVMValueRef args [16];
1459 if (is_faulting && bb->region != -1) {
1462 intrins_name = "llvm.mono.store.i8.p0i8";
1465 intrins_name = "llvm.mono.store.i16.p0i16";
1468 intrins_name = "llvm.mono.store.i32.p0i32";
1471 intrins_name = "llvm.mono.store.i64.p0i64";
1474 g_assert_not_reached ();
1477 if (LLVMTypeOf (value) == LLVMDoubleType () || LLVMTypeOf (value) == LLVMFloatType ()) {
1478 value = LLVMBuildBitCast (*builder_ref, value, LLVMIntType (size * 8), "");
1479 addr = LLVMBuildBitCast (*builder_ref, addr, LLVMPointerType (LLVMIntType (size * 8), 0), "");
1484 args [2] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
1485 args [3] = LLVMConstInt (LLVMInt1Type (), TRUE, FALSE);
1486 emit_call (ctx, bb, builder_ref, LLVMGetNamedFunction (ctx->module, intrins_name), args, 4);
1488 LLVMBuildStore (*builder_ref, value, addr);
1493 * emit_cond_system_exception:
1495 * Emit code to throw the exception EXC_TYPE if the condition CMP is false.
1496 * Might set the ctx exception.
1499 emit_cond_system_exception (EmitContext *ctx, MonoBasicBlock *bb, const char *exc_type, LLVMValueRef cmp)
1501 LLVMBasicBlockRef ex_bb, noex_bb;
1502 LLVMBuilderRef builder;
1503 MonoClass *exc_class;
1504 LLVMValueRef args [2];
1506 ex_bb = gen_bb (ctx, "EX_BB");
1507 noex_bb = gen_bb (ctx, "NOEX_BB");
1509 LLVMBuildCondBr (ctx->builder, cmp, ex_bb, noex_bb);
1511 exc_class = mono_class_from_name (mono_get_corlib (), "System", exc_type);
1512 g_assert (exc_class);
1514 /* Emit exception throwing code */
1515 builder = create_builder (ctx);
1516 LLVMPositionBuilderAtEnd (builder, ex_bb);
1518 if (!ctx->lmodule->throw_corlib_exception) {
1519 LLVMValueRef callee;
1521 const char *icall_name;
1523 MonoMethodSignature *throw_sig = mono_metadata_signature_alloc (mono_get_corlib (), 2);
1524 throw_sig->ret = &mono_get_void_class ()->byval_arg;
1525 throw_sig->params [0] = &mono_get_int32_class ()->byval_arg;
1526 icall_name = "llvm_throw_corlib_exception_abs_trampoline";
1527 /* This will become i8* */
1528 throw_sig->params [1] = &mono_get_byte_class ()->this_arg;
1529 sig = sig_to_llvm_sig (ctx, throw_sig);
1531 if (ctx->cfg->compile_aot) {
1532 callee = get_plt_entry (ctx, sig, MONO_PATCH_INFO_INTERNAL_METHOD, icall_name);
1534 callee = LLVMAddFunction (ctx->module, "llvm_throw_corlib_exception_trampoline", sig_to_llvm_sig (ctx, throw_sig));
1537 * Differences between the LLVM/non-LLVM throw corlib exception trampoline:
1538 * - On x86, LLVM generated code doesn't push the arguments
1539 * - The trampoline takes the throw address as an arguments, not a pc offset.
1541 LLVMAddGlobalMapping (ee, callee, resolve_patch (ctx->cfg, MONO_PATCH_INFO_INTERNAL_METHOD, icall_name));
1544 mono_memory_barrier ();
1545 ctx->lmodule->throw_corlib_exception = callee;
1548 if (IS_TARGET_X86 || IS_TARGET_AMD64)
1549 args [0] = LLVMConstInt (LLVMInt32Type (), exc_class->type_token - MONO_TOKEN_TYPE_DEF, FALSE);
1551 args [0] = LLVMConstInt (LLVMInt32Type (), exc_class->type_token, FALSE);
1554 * The LLVM mono branch contains changes so a block address can be passed as an
1555 * argument to a call.
1557 args [1] = LLVMBlockAddress (ctx->lmethod, ex_bb);
1558 emit_call (ctx, bb, &builder, ctx->lmodule->throw_corlib_exception, args, 2);
1560 LLVMBuildUnreachable (builder);
1562 ctx->builder = create_builder (ctx);
1563 LLVMPositionBuilderAtEnd (ctx->builder, noex_bb);
1565 ctx->bblocks [bb->block_num].end_bblock = noex_bb;
1572 * emit_reg_to_vtype:
1574 * Emit code to store the vtype in the registers REGS to the address ADDRESS.
1577 emit_reg_to_vtype (EmitContext *ctx, LLVMBuilderRef builder, MonoType *t, LLVMValueRef address, LLVMArgInfo *ainfo, LLVMValueRef *regs)
1581 size = get_vtype_size (t);
1583 if (MONO_CLASS_IS_SIMD (ctx->cfg, mono_class_from_mono_type (t))) {
1584 address = LLVMBuildBitCast (ctx->builder, address, LLVMPointerType (LLVMInt8Type (), 0), "");
1587 for (j = 0; j < 2; ++j) {
1588 LLVMValueRef index [2], addr;
1589 int part_size = size > sizeof (gpointer) ? sizeof (gpointer) : size;
1590 LLVMTypeRef part_type;
1592 if (ainfo->pair_storage [j] == LLVMArgNone)
1595 part_type = LLVMIntType (part_size * 8);
1596 if (MONO_CLASS_IS_SIMD (ctx->cfg, mono_class_from_mono_type (t))) {
1597 index [0] = LLVMConstInt (LLVMInt32Type (), j * sizeof (gpointer), FALSE);
1598 addr = LLVMBuildGEP (builder, address, index, 1, "");
1600 index [0] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
1601 index [1] = LLVMConstInt (LLVMInt32Type (), j * sizeof (gpointer), FALSE);
1602 addr = LLVMBuildGEP (builder, address, index, 2, "");
1604 switch (ainfo->pair_storage [j]) {
1606 LLVMBuildStore (builder, convert (ctx, regs [j], part_type), LLVMBuildBitCast (ctx->builder, addr, LLVMPointerType (part_type, 0), ""));
1611 g_assert_not_reached ();
1614 size -= sizeof (gpointer);
1619 * emit_vtype_to_reg:
1621 * Emit code to load a vtype at address ADDRESS into registers. Store the registers
1622 * into REGS, and the number of registers into NREGS.
1625 emit_vtype_to_reg (EmitContext *ctx, LLVMBuilderRef builder, MonoType *t, LLVMValueRef address, LLVMArgInfo *ainfo, LLVMValueRef *regs, guint32 *nregs)
1630 size = get_vtype_size (t);
1632 if (MONO_CLASS_IS_SIMD (ctx->cfg, mono_class_from_mono_type (t))) {
1633 address = LLVMBuildBitCast (ctx->builder, address, LLVMPointerType (LLVMInt8Type (), 0), "");
1636 for (j = 0; j < 2; ++j) {
1637 LLVMValueRef index [2], addr;
1638 int partsize = size > sizeof (gpointer) ? sizeof (gpointer) : size;
1640 if (ainfo->pair_storage [j] == LLVMArgNone)
1643 if (MONO_CLASS_IS_SIMD (ctx->cfg, mono_class_from_mono_type (t))) {
1644 index [0] = LLVMConstInt (LLVMInt32Type (), j * sizeof (gpointer), FALSE);
1645 addr = LLVMBuildGEP (builder, address, index, 1, "");
1647 index [0] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
1648 index [1] = LLVMConstInt (LLVMInt32Type (), j * sizeof (gpointer), FALSE);
1649 addr = LLVMBuildGEP (builder, address, index, 2, "");
1651 switch (ainfo->pair_storage [j]) {
1653 regs [pindex ++] = convert (ctx, LLVMBuildLoad (builder, LLVMBuildBitCast (ctx->builder, addr, LLVMPointerType (LLVMIntType (partsize * 8), 0), ""), ""), IntPtrType ());
1658 g_assert_not_reached ();
1660 size -= sizeof (gpointer);
1667 build_alloca (EmitContext *ctx, MonoType *t)
1669 MonoClass *k = mono_class_from_mono_type (t);
1672 if (MONO_CLASS_IS_SIMD (ctx->cfg, k))
1675 align = mono_class_min_align (k);
1677 /* Sometimes align is not a power of 2 */
1678 while (mono_is_power_of_two (align) == -1)
1682 * Have to place all alloca's at the end of the entry bb, since otherwise they would
1683 * get executed every time control reaches them.
1685 LLVMPositionBuilder (ctx->alloca_builder, get_bb (ctx, ctx->cfg->bb_entry), ctx->last_alloca);
1687 ctx->last_alloca = mono_llvm_build_alloca (ctx->alloca_builder, type_to_llvm_type (ctx, t), NULL, align, "");
1688 return ctx->last_alloca;
1692 * Put the global into the 'llvm.used' array to prevent it from being optimized away.
1695 mark_as_used (MonoLLVMModule *lmodule, LLVMValueRef global)
1698 lmodule->used = g_ptr_array_sized_new (16);
1699 g_ptr_array_add (lmodule->used, global);
1703 emit_llvm_used (MonoLLVMModule *lmodule)
1705 LLVMModuleRef module = lmodule->module;
1706 LLVMTypeRef used_type;
1707 LLVMValueRef used, *used_elem;
1713 used_type = LLVMArrayType (LLVMPointerType (LLVMInt8Type (), 0), lmodule->used->len);
1714 used = LLVMAddGlobal (module, used_type, "llvm.used");
1715 used_elem = g_new0 (LLVMValueRef, lmodule->used->len);
1716 for (i = 0; i < lmodule->used->len; ++i)
1717 used_elem [i] = LLVMConstBitCast (g_ptr_array_index (lmodule->used, i), LLVMPointerType (LLVMInt8Type (), 0));
1718 LLVMSetInitializer (used, LLVMConstArray (LLVMPointerType (LLVMInt8Type (), 0), used_elem, lmodule->used->len));
1719 LLVMSetLinkage (used, LLVMAppendingLinkage);
1720 LLVMSetSection (used, "llvm.metadata");
1726 * Emit code to load/convert arguments.
1729 emit_entry_bb (EmitContext *ctx, LLVMBuilderRef builder)
1732 MonoCompile *cfg = ctx->cfg;
1733 MonoMethodSignature *sig = ctx->sig;
1734 LLVMCallInfo *linfo = ctx->linfo;
1737 ctx->alloca_builder = create_builder (ctx);
1740 * Handle indirect/volatile variables by allocating memory for them
1741 * using 'alloca', and storing their address in a temporary.
1743 for (i = 0; i < cfg->num_varinfo; ++i) {
1744 MonoInst *var = cfg->varinfo [i];
1747 if (var->flags & (MONO_INST_VOLATILE|MONO_INST_INDIRECT) || mini_type_is_vtype (cfg, var->inst_vtype)) {
1748 vtype = type_to_llvm_type (ctx, var->inst_vtype);
1749 CHECK_FAILURE (ctx);
1750 /* Could be already created by an OP_VPHI */
1751 if (!ctx->addresses [var->dreg])
1752 ctx->addresses [var->dreg] = build_alloca (ctx, var->inst_vtype);
1753 ctx->vreg_cli_types [var->dreg] = var->inst_vtype;
1757 for (i = 0; i < sig->param_count; ++i) {
1758 LLVMArgInfo *ainfo = &linfo->args [i + sig->hasthis];
1759 int reg = cfg->args [i + sig->hasthis]->dreg;
1761 if (ainfo->storage == LLVMArgVtypeInReg) {
1762 LLVMValueRef regs [2];
1765 * Emit code to save the argument from the registers to
1766 * the real argument.
1768 pindex = ctx->pindexes [i];
1769 regs [0] = LLVMGetParam (ctx->lmethod, pindex);
1770 if (ainfo->pair_storage [1] != LLVMArgNone)
1771 regs [1] = LLVMGetParam (ctx->lmethod, pindex + 1);
1775 ctx->addresses [reg] = build_alloca (ctx, sig->params [i]);
1777 emit_reg_to_vtype (ctx, builder, sig->params [i], ctx->addresses [reg], ainfo, regs);
1779 if (MONO_CLASS_IS_SIMD (ctx->cfg, mono_class_from_mono_type (sig->params [i]))) {
1780 /* Treat these as normal values */
1781 ctx->values [reg] = LLVMBuildLoad (builder, ctx->addresses [reg], "");
1783 } else if (ainfo->storage == LLVMArgVtypeByVal) {
1784 ctx->addresses [reg] = LLVMGetParam (ctx->lmethod, ctx->pindexes [i]);
1786 if (MONO_CLASS_IS_SIMD (ctx->cfg, mono_class_from_mono_type (sig->params [i]))) {
1787 /* Treat these as normal values */
1788 ctx->values [reg] = LLVMBuildLoad (builder, ctx->addresses [reg], "");
1791 ctx->values [reg] = convert (ctx, ctx->values [reg], llvm_type_to_stack_type (type_to_llvm_type (ctx, sig->params [i])));
1796 emit_volatile_store (ctx, cfg->vret_addr->dreg);
1798 emit_volatile_store (ctx, cfg->args [0]->dreg);
1799 for (i = 0; i < sig->param_count; ++i)
1800 if (!mini_type_is_vtype (cfg, sig->params [i]))
1801 emit_volatile_store (ctx, cfg->args [i + sig->hasthis]->dreg);
1803 if (sig->hasthis && !cfg->rgctx_var && cfg->generic_sharing_context) {
1804 LLVMValueRef this_alloc;
1807 * The exception handling code needs the location where the this argument was
1808 * stored for gshared methods. We create a separate alloca to hold it, and mark it
1809 * with the "mono.this" custom metadata to tell llvm that it needs to save its
1810 * location into the LSDA.
1812 this_alloc = mono_llvm_build_alloca (builder, ThisType (), LLVMConstInt (LLVMInt32Type (), 1, FALSE), 0, "");
1813 /* This volatile store will keep the alloca alive */
1814 mono_llvm_build_store (builder, ctx->values [cfg->args [0]->dreg], this_alloc, TRUE);
1816 set_metadata_flag (this_alloc, "mono.this");
1819 if (cfg->rgctx_var) {
1820 LLVMValueRef rgctx_alloc, store;
1823 * We handle the rgctx arg similarly to the this pointer.
1825 g_assert (ctx->addresses [cfg->rgctx_var->dreg]);
1826 rgctx_alloc = ctx->addresses [cfg->rgctx_var->dreg];
1827 /* This volatile store will keep the alloca alive */
1828 store = mono_llvm_build_store (builder, convert (ctx, ctx->rgctx_arg, IntPtrType ()), rgctx_alloc, TRUE);
1830 set_metadata_flag (rgctx_alloc, "mono.this");
1834 * For finally clauses, create an indicator variable telling OP_ENDFINALLY whenever
1835 * it needs to continue normally, or return back to the exception handling system.
1837 for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
1838 if (bb->region != -1 && (bb->flags & BB_EXCEPTION_HANDLER))
1839 g_hash_table_insert (ctx->region_to_handler, GUINT_TO_POINTER (mono_get_block_region_notry (cfg, bb->region)), bb);
1840 if (bb->region != -1 && (bb->flags & BB_EXCEPTION_HANDLER) && bb->in_scount == 0) {
1844 sprintf (name, "finally_ind_bb%d", bb->block_num);
1845 val = LLVMBuildAlloca (builder, LLVMInt32Type (), name);
1846 LLVMBuildStore (builder, LLVMConstInt (LLVMInt32Type (), 0, FALSE), val);
1848 ctx->bblocks [bb->block_num].finally_ind = val;
1851 * Create a new bblock which CALL_HANDLER can branch to, because branching to the
1852 * LLVM bblock containing the call to llvm.eh.selector causes problems for the
1853 * LLVM optimizer passes.
1855 sprintf (name, "BB_%d_CALL_HANDLER_TARGET", bb->block_num);
1856 ctx->bblocks [bb->block_num].call_handler_target_bb = LLVMAppendBasicBlock (ctx->lmethod, name);
1864 /* Have to export this for AOT */
1866 mono_personality (void);
1869 mono_personality (void)
1872 g_assert_not_reached ();
1876 process_call (EmitContext *ctx, MonoBasicBlock *bb, LLVMBuilderRef *builder_ref, MonoInst *ins)
1878 MonoCompile *cfg = ctx->cfg;
1879 LLVMModuleRef module = ctx->module;
1880 LLVMValueRef *values = ctx->values;
1881 LLVMValueRef *addresses = ctx->addresses;
1882 MonoCallInst *call = (MonoCallInst*)ins;
1883 MonoMethodSignature *sig = call->signature;
1884 LLVMValueRef callee = NULL, lcall;
1886 LLVMCallInfo *cinfo;
1890 LLVMTypeRef llvm_sig;
1892 gboolean virtual, calli;
1893 LLVMBuilderRef builder = *builder_ref;
1896 if (call->signature->call_convention != MONO_CALL_DEFAULT)
1897 LLVM_FAILURE (ctx, "non-default callconv");
1899 cinfo = call->cinfo;
1900 if (call->rgctx_arg_reg)
1901 cinfo->rgctx_arg = TRUE;
1902 if (call->imt_arg_reg)
1903 cinfo->imt_arg = TRUE;
1905 vretaddr = cinfo && cinfo->ret.storage == LLVMArgVtypeRetAddr;
1907 llvm_sig = sig_to_llvm_sig_full (ctx, sig, cinfo, &sinfo);
1908 CHECK_FAILURE (ctx);
1910 virtual = (ins->opcode == OP_VOIDCALL_MEMBASE || ins->opcode == OP_CALL_MEMBASE || ins->opcode == OP_VCALL_MEMBASE || ins->opcode == OP_LCALL_MEMBASE || ins->opcode == OP_FCALL_MEMBASE);
1911 calli = (ins->opcode == OP_VOIDCALL_REG || ins->opcode == OP_CALL_REG || ins->opcode == OP_VCALL_REG || ins->opcode == OP_LCALL_REG || ins->opcode == OP_FCALL_REG);
1913 /* FIXME: Avoid creating duplicate methods */
1915 if (ins->flags & MONO_INST_HAS_METHOD) {
1919 if (cfg->compile_aot) {
1920 callee = get_plt_entry (ctx, llvm_sig, MONO_PATCH_INFO_METHOD, call->method);
1922 LLVM_FAILURE (ctx, "can't encode patch");
1924 callee = LLVMAddFunction (module, "", llvm_sig);
1927 mono_create_jit_trampoline_in_domain (mono_domain_get (),
1929 LLVMAddGlobalMapping (ee, callee, target);
1933 if (call->method && strstr (call->method->klass->name, "AsyncVoidMethodBuilder"))
1934 /* LLVM miscompiles async methods */
1935 LLVM_FAILURE (ctx, "#13734");
1938 MonoJitICallInfo *info = mono_find_jit_icall_by_addr (call->fptr);
1944 memset (&ji, 0, sizeof (ji));
1945 ji.type = MONO_PATCH_INFO_JIT_ICALL_ADDR;
1946 ji.data.target = info->name;
1948 target = mono_resolve_patch_target (cfg->method, cfg->domain, NULL, &ji, FALSE);
1950 if (cfg->compile_aot) {
1951 callee = get_plt_entry (ctx, llvm_sig, MONO_PATCH_INFO_INTERNAL_METHOD, (char*)info->name);
1953 LLVM_FAILURE (ctx, "can't encode patch");
1955 callee = LLVMAddFunction (module, "", llvm_sig);
1956 target = (gpointer)mono_icall_get_wrapper (info);
1957 LLVMAddGlobalMapping (ee, callee, target);
1960 if (cfg->compile_aot) {
1962 if (cfg->abs_patches) {
1963 MonoJumpInfo *abs_ji = g_hash_table_lookup (cfg->abs_patches, call->fptr);
1965 callee = get_plt_entry (ctx, llvm_sig, abs_ji->type, abs_ji->data.target);
1967 LLVM_FAILURE (ctx, "can't encode patch");
1971 LLVM_FAILURE (ctx, "aot");
1973 callee = LLVMAddFunction (module, "", llvm_sig);
1975 if (cfg->abs_patches) {
1976 MonoJumpInfo *abs_ji = g_hash_table_lookup (cfg->abs_patches, call->fptr);
1979 * FIXME: Some trampolines might have
1980 * their own calling convention on some platforms.
1982 #ifndef TARGET_AMD64
1983 if (abs_ji->type == MONO_PATCH_INFO_MONITOR_ENTER || abs_ji->type == MONO_PATCH_INFO_MONITOR_EXIT || abs_ji->type == MONO_PATCH_INFO_GENERIC_CLASS_INIT)
1984 LLVM_FAILURE (ctx, "trampoline with own cconv");
1986 target = mono_resolve_patch_target (cfg->method, cfg->domain, NULL, abs_ji, FALSE);
1987 LLVMAddGlobalMapping (ee, callee, target);
1991 LLVMAddGlobalMapping (ee, callee, (gpointer)call->fptr);
1997 int size = sizeof (gpointer);
2000 g_assert (ins->inst_offset % size == 0);
2001 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset / size, FALSE);
2003 callee = convert (ctx, LLVMBuildLoad (builder, LLVMBuildGEP (builder, convert (ctx, values [ins->inst_basereg], LLVMPointerType (LLVMPointerType (IntPtrType (), 0), 0)), &index, 1, ""), ""), LLVMPointerType (llvm_sig, 0));
2005 callee = convert (ctx, values [ins->sreg1], LLVMPointerType (llvm_sig, 0));
2007 if (ins->flags & MONO_INST_HAS_METHOD) {
2012 * Collect and convert arguments
2014 nargs = (sig->param_count * 2) + sig->hasthis + vretaddr + call->rgctx_reg + call->imt_arg_reg;
2015 len = sizeof (LLVMValueRef) * nargs;
2016 args = alloca (len);
2017 memset (args, 0, len);
2018 l = call->out_ireg_args;
2020 if (call->rgctx_arg_reg) {
2021 g_assert (values [call->rgctx_arg_reg]);
2022 g_assert (sinfo.rgctx_arg_pindex < nargs);
2023 args [sinfo.rgctx_arg_pindex] = convert (ctx, values [call->rgctx_arg_reg], ctx->lmodule->ptr_type);
2025 if (call->imt_arg_reg) {
2026 g_assert (values [call->imt_arg_reg]);
2027 g_assert (sinfo.imt_arg_pindex < nargs);
2028 args [sinfo.imt_arg_pindex] = convert (ctx, values [call->imt_arg_reg], ctx->lmodule->ptr_type);
2032 if (!addresses [call->inst.dreg])
2033 addresses [call->inst.dreg] = build_alloca (ctx, sig->ret);
2034 g_assert (sinfo.vret_arg_pindex < nargs);
2035 args [sinfo.vret_arg_pindex] = LLVMBuildPtrToInt (builder, addresses [call->inst.dreg], IntPtrType (), "");
2038 for (i = 0; i < sig->param_count + sig->hasthis; ++i) {
2041 LLVMArgInfo *ainfo = call->cinfo ? &call->cinfo->args [i] : NULL;
2045 pindex = sinfo.this_arg_pindex;
2047 pindex = sinfo.pindexes [i - 1];
2049 pindex = sinfo.pindexes [i];
2052 regpair = (guint32)(gssize)(l->data);
2053 reg = regpair & 0xffffff;
2054 args [pindex] = values [reg];
2055 if (ainfo->storage == LLVMArgVtypeInReg) {
2057 LLVMValueRef regs [2];
2062 g_assert (addresses [reg]);
2064 emit_vtype_to_reg (ctx, builder, sig->params [i - sig->hasthis], addresses [reg], ainfo, regs, &nregs);
2065 for (j = 0; j < nregs; ++j)
2066 args [pindex ++] = regs [j];
2069 // FIXME: Get rid of the VMOVE
2070 } else if (ainfo->storage == LLVMArgVtypeByVal) {
2071 g_assert (addresses [reg]);
2072 args [pindex] = addresses [reg];
2074 g_assert (args [pindex]);
2075 if (i == 0 && sig->hasthis)
2076 args [pindex] = convert (ctx, args [pindex], ThisType ());
2078 args [pindex] = convert (ctx, args [pindex], type_to_llvm_arg_type (ctx, sig->params [i - sig->hasthis]));
2084 // FIXME: Align call sites
2090 lcall = emit_call (ctx, bb, &builder, callee, args, LLVMCountParamTypes (llvm_sig));
2093 * Modify cconv and parameter attributes to pass rgctx/imt correctly.
2095 #if defined(MONO_ARCH_IMT_REG) && defined(MONO_ARCH_RGCTX_REG)
2096 g_assert (MONO_ARCH_IMT_REG == MONO_ARCH_RGCTX_REG);
2098 /* The two can't be used together, so use only one LLVM calling conv to pass them */
2099 g_assert (!(call->rgctx_arg_reg && call->imt_arg_reg));
2101 LLVMSetInstructionCallConv (lcall, LLVMMono1CallConv);
2103 if (call->rgctx_arg_reg)
2104 LLVMAddInstrAttribute (lcall, 1 + sinfo.rgctx_arg_pindex, LLVMInRegAttribute);
2105 if (call->imt_arg_reg)
2106 LLVMAddInstrAttribute (lcall, 1 + sinfo.imt_arg_pindex, LLVMInRegAttribute);
2108 /* Add byval attributes if needed */
2109 for (i = 0; i < sig->param_count; ++i) {
2110 LLVMArgInfo *ainfo = call->cinfo ? &call->cinfo->args [i + sig->hasthis] : NULL;
2112 if (ainfo && ainfo->storage == LLVMArgVtypeByVal) {
2113 LLVMAddInstrAttribute (lcall, 1 + sinfo.pindexes [i], LLVMByValAttribute);
2118 * Convert the result
2120 if (cinfo && cinfo->ret.storage == LLVMArgVtypeInReg) {
2121 LLVMValueRef regs [2];
2123 if (!addresses [ins->dreg])
2124 addresses [ins->dreg] = build_alloca (ctx, sig->ret);
2126 regs [0] = LLVMBuildExtractValue (builder, lcall, 0, "");
2127 if (cinfo->ret.pair_storage [1] != LLVMArgNone)
2128 regs [1] = LLVMBuildExtractValue (builder, lcall, 1, "");
2130 emit_reg_to_vtype (ctx, builder, sig->ret, addresses [ins->dreg], &cinfo->ret, regs);
2131 } else if (sig->ret->type != MONO_TYPE_VOID && !vretaddr) {
2132 /* If the method returns an unsigned value, need to zext it */
2134 values [ins->dreg] = convert_full (ctx, lcall, llvm_type_to_stack_type (type_to_llvm_type (ctx, sig->ret)), type_is_unsigned (ctx, sig->ret));
2137 *builder_ref = ctx->builder;
2139 g_free (sinfo.pindexes);
2147 process_bb (EmitContext *ctx, MonoBasicBlock *bb)
2149 MonoCompile *cfg = ctx->cfg;
2150 MonoMethodSignature *sig = ctx->sig;
2151 LLVMValueRef method = ctx->lmethod;
2152 LLVMValueRef *values = ctx->values;
2153 LLVMValueRef *addresses = ctx->addresses;
2155 LLVMCallInfo *linfo = ctx->linfo;
2156 LLVMModuleRef module = ctx->module;
2157 BBInfo *bblocks = ctx->bblocks;
2159 LLVMBasicBlockRef cbb;
2160 LLVMBuilderRef builder, starting_builder;
2161 gboolean has_terminator;
2163 LLVMValueRef lhs, rhs;
2166 cbb = get_bb (ctx, bb);
2167 builder = create_builder (ctx);
2168 ctx->builder = builder;
2169 LLVMPositionBuilderAtEnd (builder, cbb);
2171 if (bb == cfg->bb_entry)
2172 emit_entry_bb (ctx, builder);
2173 CHECK_FAILURE (ctx);
2175 if (bb->flags & BB_EXCEPTION_HANDLER) {
2177 LLVMValueRef personality;
2178 LLVMBasicBlockRef target_bb;
2180 static gint32 mapping_inited;
2181 static int ti_generator;
2184 LLVMValueRef type_info;
2187 if (!bblocks [bb->block_num].invoke_target) {
2189 * LLVM asserts if llvm.eh.selector is called from a bblock which
2190 * doesn't have an invoke pointing at it.
2191 * Update: LLVM no longer asserts, but some tests in exceptions.exe now fail.
2193 LLVM_FAILURE (ctx, "handler without invokes");
2196 // <resultval> = landingpad <somety> personality <type> <pers_fn> <clause>+
2198 if (cfg->compile_aot) {
2199 /* Use a dummy personality function */
2200 personality = LLVMGetNamedFunction (module, "mono_aot_personality");
2201 g_assert (personality);
2203 personality = LLVMGetNamedFunction (module, "mono_personality");
2204 if (InterlockedCompareExchange (&mapping_inited, 1, 0) == 0)
2205 LLVMAddGlobalMapping (ee, personality, mono_personality);
2208 i8ptr = LLVMPointerType (LLVMInt8Type (), 0);
2210 clause_index = (mono_get_block_region_notry (cfg, bb->region) >> 8) - 1;
2213 * Create the type info
2215 sprintf (ti_name, "type_info_%d", ti_generator);
2218 if (cfg->compile_aot) {
2219 /* decode_eh_frame () in aot-runtime.c will decode this */
2220 type_info = LLVMAddGlobal (module, LLVMInt32Type (), ti_name);
2221 LLVMSetInitializer (type_info, LLVMConstInt (LLVMInt32Type (), clause_index, FALSE));
2224 * These symbols are not really used, the clause_index is embedded into the EH tables generated by DwarfMonoException in LLVM.
2226 LLVMSetLinkage (type_info, LLVMInternalLinkage);
2229 * Enabling this causes llc to crash:
2230 * http://llvm.org/bugs/show_bug.cgi?id=6102
2232 //LLVM_FAILURE (ctx, "aot+clauses");
2234 // test_0_invalid_unbox_arrays () fails
2235 LLVM_FAILURE (ctx, "aot+clauses");
2239 * After the cfg mempool is freed, the type info will point to stale memory,
2240 * but this is not a problem, since we decode it once in exception_cb during
2243 ti = mono_mempool_alloc (cfg->mempool, sizeof (gint32));
2244 *(gint32*)ti = clause_index;
2246 type_info = LLVMAddGlobal (module, i8ptr, ti_name);
2248 LLVMAddGlobalMapping (ee, type_info, ti);
2252 LLVMTypeRef members [2], ret_type;
2253 LLVMValueRef landing_pad;
2255 members [0] = i8ptr;
2256 members [1] = LLVMInt32Type ();
2257 ret_type = LLVMStructType (members, 2, FALSE);
2259 landing_pad = LLVMBuildLandingPad (builder, ret_type, personality, 1, "");
2260 LLVMAddClause (landing_pad, type_info);
2262 /* Store the exception into the exvar */
2263 if (bb->in_scount == 1) {
2264 g_assert (bb->in_scount == 1);
2265 exvar = bb->in_stack [0];
2267 // FIXME: This is shared with filter clauses ?
2268 g_assert (!values [exvar->dreg]);
2270 values [exvar->dreg] = LLVMBuildExtractValue (builder, landing_pad, 0, "ex_obj");
2271 emit_volatile_store (ctx, exvar->dreg);
2275 /* Start a new bblock which CALL_HANDLER can branch to */
2276 target_bb = bblocks [bb->block_num].call_handler_target_bb;
2278 LLVMBuildBr (builder, target_bb);
2280 ctx->builder = builder = create_builder (ctx);
2281 LLVMPositionBuilderAtEnd (ctx->builder, target_bb);
2283 ctx->bblocks [bb->block_num].end_bblock = target_bb;
2287 has_terminator = FALSE;
2288 starting_builder = builder;
2289 for (ins = bb->code; ins; ins = ins->next) {
2290 const char *spec = LLVM_INS_INFO (ins->opcode);
2292 char dname_buf [128];
2295 if (nins > 5000 && builder == starting_builder) {
2296 /* some steps in llc are non-linear in the size of basic blocks, see #5714 */
2297 LLVM_FAILURE (ctx, "basic block too long");
2301 /* There could be instructions after a terminator, skip them */
2304 if (spec [MONO_INST_DEST] != ' ' && !MONO_IS_STORE_MEMBASE (ins)) {
2305 sprintf (dname_buf, "t%d", ins->dreg);
2309 if (spec [MONO_INST_SRC1] != ' ' && spec [MONO_INST_SRC1] != 'v') {
2310 MonoInst *var = get_vreg_to_inst (cfg, ins->sreg1);
2312 if (var && var->flags & (MONO_INST_VOLATILE|MONO_INST_INDIRECT)) {
2313 lhs = emit_volatile_load (ctx, ins->sreg1);
2315 /* It is ok for SETRET to have an uninitialized argument */
2316 if (!values [ins->sreg1] && ins->opcode != OP_SETRET)
2317 LLVM_FAILURE (ctx, "sreg1");
2318 lhs = values [ins->sreg1];
2324 if (spec [MONO_INST_SRC2] != ' ' && spec [MONO_INST_SRC2] != ' ') {
2325 MonoInst *var = get_vreg_to_inst (cfg, ins->sreg2);
2326 if (var && var->flags & (MONO_INST_VOLATILE|MONO_INST_INDIRECT)) {
2327 rhs = emit_volatile_load (ctx, ins->sreg2);
2329 if (!values [ins->sreg2])
2330 LLVM_FAILURE (ctx, "sreg2");
2331 rhs = values [ins->sreg2];
2337 //mono_print_ins (ins);
2338 switch (ins->opcode) {
2341 case OP_LIVERANGE_START:
2342 case OP_LIVERANGE_END:
2345 values [ins->dreg] = LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE);
2348 #if SIZEOF_VOID_P == 4
2349 values [ins->dreg] = LLVMConstInt (LLVMInt64Type (), GET_LONG_IMM (ins), FALSE);
2351 values [ins->dreg] = LLVMConstInt (LLVMInt64Type (), (gint64)ins->inst_c0, FALSE);
2355 values [ins->dreg] = LLVMConstReal (LLVMDoubleType (), *(double*)ins->inst_p0);
2358 values [ins->dreg] = LLVMConstFPExt (LLVMConstReal (LLVMFloatType (), *(float*)ins->inst_p0), LLVMDoubleType ());
2361 LLVMBuildBr (builder, get_bb (ctx, ins->inst_target_bb));
2362 has_terminator = TRUE;
2368 LLVMBasicBlockRef new_bb;
2369 LLVMBuilderRef new_builder;
2371 // The default branch is already handled
2372 // FIXME: Handle it here
2374 /* Start new bblock */
2375 sprintf (bb_name, "SWITCH_DEFAULT_BB%d", ctx->default_index ++);
2376 new_bb = LLVMAppendBasicBlock (ctx->lmethod, bb_name);
2378 lhs = convert (ctx, lhs, LLVMInt32Type ());
2379 v = LLVMBuildSwitch (builder, lhs, new_bb, GPOINTER_TO_UINT (ins->klass));
2380 for (i = 0; i < GPOINTER_TO_UINT (ins->klass); ++i) {
2381 MonoBasicBlock *target_bb = ins->inst_many_bb [i];
2383 LLVMAddCase (v, LLVMConstInt (LLVMInt32Type (), i, FALSE), get_bb (ctx, target_bb));
2386 new_builder = create_builder (ctx);
2387 LLVMPositionBuilderAtEnd (new_builder, new_bb);
2388 LLVMBuildUnreachable (new_builder);
2390 has_terminator = TRUE;
2391 g_assert (!ins->next);
2397 if (linfo->ret.storage == LLVMArgVtypeInReg) {
2398 LLVMTypeRef ret_type = LLVMGetReturnType (LLVMGetElementType (LLVMTypeOf (method)));
2399 LLVMValueRef part1, retval;
2402 size = get_vtype_size (sig->ret);
2404 g_assert (addresses [ins->sreg1]);
2406 g_assert (linfo->ret.pair_storage [0] == LLVMArgInIReg);
2407 g_assert (linfo->ret.pair_storage [1] == LLVMArgNone);
2409 part1 = convert (ctx, LLVMBuildLoad (builder, LLVMBuildBitCast (builder, addresses [ins->sreg1], LLVMPointerType (LLVMIntType (size * 8), 0), ""), ""), IntPtrType ());
2411 retval = LLVMBuildInsertValue (builder, LLVMGetUndef (ret_type), part1, 0, "");
2413 LLVMBuildRet (builder, retval);
2417 if (linfo->ret.storage == LLVMArgVtypeRetAddr) {
2418 LLVMBuildRetVoid (builder);
2422 if (!lhs || ctx->is_dead [ins->sreg1]) {
2424 * The method did not set its return value, probably because it
2425 * ends with a throw.
2428 LLVMBuildRetVoid (builder);
2430 LLVMBuildRet (builder, LLVMConstNull (type_to_llvm_type (ctx, sig->ret)));
2432 LLVMBuildRet (builder, convert (ctx, lhs, type_to_llvm_type (ctx, sig->ret)));
2434 has_terminator = TRUE;
2440 case OP_ICOMPARE_IMM:
2441 case OP_LCOMPARE_IMM:
2442 case OP_COMPARE_IMM: {
2446 if (ins->next->opcode == OP_NOP)
2449 if (ins->next->opcode == OP_BR)
2450 /* The comparison result is not needed */
2453 rel = mono_opcode_to_cond (ins->next->opcode);
2455 if (ins->opcode == OP_ICOMPARE_IMM) {
2456 lhs = convert (ctx, lhs, LLVMInt32Type ());
2457 rhs = LLVMConstInt (LLVMInt32Type (), ins->inst_imm, FALSE);
2459 if (ins->opcode == OP_LCOMPARE_IMM) {
2460 lhs = convert (ctx, lhs, LLVMInt64Type ());
2461 rhs = LLVMConstInt (LLVMInt64Type (), GET_LONG_IMM (ins), FALSE);
2463 if (ins->opcode == OP_LCOMPARE) {
2464 lhs = convert (ctx, lhs, LLVMInt64Type ());
2465 rhs = convert (ctx, rhs, LLVMInt64Type ());
2467 if (ins->opcode == OP_ICOMPARE) {
2468 lhs = convert (ctx, lhs, LLVMInt32Type ());
2469 rhs = convert (ctx, rhs, LLVMInt32Type ());
2473 if (LLVMGetTypeKind (LLVMTypeOf (lhs)) == LLVMPointerTypeKind)
2474 rhs = convert (ctx, rhs, LLVMTypeOf (lhs));
2475 else if (LLVMGetTypeKind (LLVMTypeOf (rhs)) == LLVMPointerTypeKind)
2476 lhs = convert (ctx, lhs, LLVMTypeOf (rhs));
2479 /* We use COMPARE+SETcc/Bcc, llvm uses SETcc+br cond */
2480 if (ins->opcode == OP_FCOMPARE)
2481 cmp = LLVMBuildFCmp (builder, fpcond_to_llvm_cond [rel], convert (ctx, lhs, LLVMDoubleType ()), convert (ctx, rhs, LLVMDoubleType ()), "");
2482 else if (ins->opcode == OP_COMPARE_IMM) {
2483 if (LLVMGetTypeKind (LLVMTypeOf (lhs)) == LLVMPointerTypeKind && ins->inst_imm == 0)
2484 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], lhs, LLVMConstNull (LLVMTypeOf (lhs)), "");
2486 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], convert (ctx, lhs, IntPtrType ()), LLVMConstInt (IntPtrType (), ins->inst_imm, FALSE), "");
2487 } else if (ins->opcode == OP_LCOMPARE_IMM) {
2488 if (SIZEOF_REGISTER == 4 && COMPILE_LLVM (cfg)) {
2489 /* The immediate is encoded in two fields */
2490 guint64 l = ((guint64)(guint32)ins->inst_offset << 32) | ((guint32)ins->inst_imm);
2491 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], convert (ctx, lhs, LLVMInt64Type ()), LLVMConstInt (LLVMInt64Type (), l, FALSE), "");
2493 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], convert (ctx, lhs, LLVMInt64Type ()), LLVMConstInt (LLVMInt64Type (), ins->inst_imm, FALSE), "");
2496 else if (ins->opcode == OP_COMPARE) {
2497 if (LLVMGetTypeKind (LLVMTypeOf (lhs)) == LLVMPointerTypeKind && LLVMTypeOf (lhs) == LLVMTypeOf (rhs))
2498 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], lhs, rhs, "");
2500 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], convert (ctx, lhs, IntPtrType ()), convert (ctx, rhs, IntPtrType ()), "");
2502 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], lhs, rhs, "");
2504 if (MONO_IS_COND_BRANCH_OP (ins->next)) {
2505 if (ins->next->inst_true_bb == ins->next->inst_false_bb) {
2507 * If the target bb contains PHI instructions, LLVM requires
2508 * two PHI entries for this bblock, while we only generate one.
2509 * So convert this to an unconditional bblock. (bxc #171).
2511 LLVMBuildBr (builder, get_bb (ctx, ins->next->inst_true_bb));
2513 LLVMBuildCondBr (builder, cmp, get_bb (ctx, ins->next->inst_true_bb), get_bb (ctx, ins->next->inst_false_bb));
2515 has_terminator = TRUE;
2516 } else if (MONO_IS_SETCC (ins->next)) {
2517 sprintf (dname_buf, "t%d", ins->next->dreg);
2519 values [ins->next->dreg] = LLVMBuildZExt (builder, cmp, LLVMInt32Type (), dname);
2521 /* Add stores for volatile variables */
2522 emit_volatile_store (ctx, ins->next->dreg);
2523 } else if (MONO_IS_COND_EXC (ins->next)) {
2524 emit_cond_system_exception (ctx, bb, ins->next->inst_p1, cmp);
2525 CHECK_FAILURE (ctx);
2526 builder = ctx->builder;
2528 LLVM_FAILURE (ctx, "next");
2542 rel = mono_opcode_to_cond (ins->opcode);
2544 cmp = LLVMBuildFCmp (builder, fpcond_to_llvm_cond [rel], convert (ctx, lhs, LLVMDoubleType ()), convert (ctx, rhs, LLVMDoubleType ()), "");
2545 values [ins->dreg] = LLVMBuildZExt (builder, cmp, LLVMInt32Type (), dname);
2553 gboolean empty = TRUE;
2555 /* Check that all input bblocks really branch to us */
2556 for (i = 0; i < bb->in_count; ++i) {
2557 if (bb->in_bb [i]->last_ins && bb->in_bb [i]->last_ins->opcode == OP_NOT_REACHED)
2558 ins->inst_phi_args [i + 1] = -1;
2564 /* LLVM doesn't like phi instructions with zero operands */
2565 ctx->is_dead [ins->dreg] = TRUE;
2569 /* Created earlier, insert it now */
2570 LLVMInsertIntoBuilder (builder, values [ins->dreg]);
2572 for (i = 0; i < ins->inst_phi_args [0]; i++) {
2573 int sreg1 = ins->inst_phi_args [i + 1];
2577 * Count the number of times the incoming bblock branches to us,
2578 * since llvm requires a separate entry for each.
2580 if (bb->in_bb [i]->last_ins && bb->in_bb [i]->last_ins->opcode == OP_SWITCH) {
2581 MonoInst *switch_ins = bb->in_bb [i]->last_ins;
2584 for (j = 0; j < GPOINTER_TO_UINT (switch_ins->klass); ++j) {
2585 if (switch_ins->inst_many_bb [j] == bb)
2592 /* Remember for later */
2593 for (j = 0; j < count; ++j) {
2594 PhiNode *node = mono_mempool_alloc0 (ctx->mempool, sizeof (PhiNode));
2597 node->in_bb = bb->in_bb [i];
2599 bblocks [bb->in_bb [i]->block_num].phi_nodes = g_slist_prepend_mempool (ctx->mempool, bblocks [bb->in_bb [i]->block_num].phi_nodes, node);
2609 values [ins->dreg] = lhs;
2612 MonoInst *var = get_vreg_to_inst (cfg, ins->dreg);
2615 values [ins->dreg] = lhs;
2617 if (var && var->klass->byval_arg.type == MONO_TYPE_R4) {
2619 * This is added by the spilling pass in case of the JIT,
2620 * but we have to do it ourselves.
2622 values [ins->dreg] = convert (ctx, values [ins->dreg], LLVMFloatType ());
2656 lhs = convert (ctx, lhs, regtype_to_llvm_type (spec [MONO_INST_DEST]));
2657 rhs = convert (ctx, rhs, regtype_to_llvm_type (spec [MONO_INST_DEST]));
2659 switch (ins->opcode) {
2662 values [ins->dreg] = LLVMBuildAdd (builder, lhs, rhs, dname);
2666 values [ins->dreg] = LLVMBuildSub (builder, lhs, rhs, dname);
2670 values [ins->dreg] = LLVMBuildMul (builder, lhs, rhs, dname);
2674 values [ins->dreg] = LLVMBuildSRem (builder, lhs, rhs, dname);
2678 values [ins->dreg] = LLVMBuildURem (builder, lhs, rhs, dname);
2682 values [ins->dreg] = LLVMBuildSDiv (builder, lhs, rhs, dname);
2686 values [ins->dreg] = LLVMBuildUDiv (builder, lhs, rhs, dname);
2689 values [ins->dreg] = LLVMBuildFDiv (builder, lhs, rhs, dname);
2693 values [ins->dreg] = LLVMBuildAnd (builder, lhs, rhs, dname);
2697 values [ins->dreg] = LLVMBuildOr (builder, lhs, rhs, dname);
2701 values [ins->dreg] = LLVMBuildXor (builder, lhs, rhs, dname);
2705 values [ins->dreg] = LLVMBuildShl (builder, lhs, rhs, dname);
2709 values [ins->dreg] = LLVMBuildAShr (builder, lhs, rhs, dname);
2713 values [ins->dreg] = LLVMBuildLShr (builder, lhs, rhs, dname);
2717 values [ins->dreg] = LLVMBuildFAdd (builder, lhs, rhs, dname);
2720 values [ins->dreg] = LLVMBuildFSub (builder, lhs, rhs, dname);
2723 values [ins->dreg] = LLVMBuildFMul (builder, lhs, rhs, dname);
2727 g_assert_not_reached ();
2734 case OP_IREM_UN_IMM:
2736 case OP_IDIV_UN_IMM:
2742 case OP_ISHR_UN_IMM:
2751 case OP_LSHR_UN_IMM:
2757 case OP_SHR_UN_IMM: {
2760 if (spec [MONO_INST_SRC1] == 'l') {
2761 imm = LLVMConstInt (LLVMInt64Type (), GET_LONG_IMM (ins), FALSE);
2763 imm = LLVMConstInt (LLVMInt32Type (), ins->inst_imm, FALSE);
2766 #if SIZEOF_VOID_P == 4
2767 if (ins->opcode == OP_LSHL_IMM || ins->opcode == OP_LSHR_IMM || ins->opcode == OP_LSHR_UN_IMM)
2768 imm = LLVMConstInt (LLVMInt32Type (), ins->inst_imm, FALSE);
2771 if (LLVMGetTypeKind (LLVMTypeOf (lhs)) == LLVMPointerTypeKind)
2772 lhs = convert (ctx, lhs, IntPtrType ());
2773 imm = convert (ctx, imm, LLVMTypeOf (lhs));
2774 switch (ins->opcode) {
2778 values [ins->dreg] = LLVMBuildAdd (builder, lhs, imm, dname);
2782 values [ins->dreg] = LLVMBuildSub (builder, lhs, imm, dname);
2786 values [ins->dreg] = LLVMBuildMul (builder, lhs, imm, dname);
2790 values [ins->dreg] = LLVMBuildSDiv (builder, lhs, imm, dname);
2792 case OP_IDIV_UN_IMM:
2793 case OP_LDIV_UN_IMM:
2794 values [ins->dreg] = LLVMBuildUDiv (builder, lhs, imm, dname);
2798 values [ins->dreg] = LLVMBuildSRem (builder, lhs, imm, dname);
2800 case OP_IREM_UN_IMM:
2801 values [ins->dreg] = LLVMBuildURem (builder, lhs, imm, dname);
2806 values [ins->dreg] = LLVMBuildAnd (builder, lhs, imm, dname);
2810 values [ins->dreg] = LLVMBuildOr (builder, lhs, imm, dname);
2814 values [ins->dreg] = LLVMBuildXor (builder, lhs, imm, dname);
2819 values [ins->dreg] = LLVMBuildShl (builder, lhs, imm, dname);
2824 values [ins->dreg] = LLVMBuildAShr (builder, lhs, imm, dname);
2826 case OP_ISHR_UN_IMM:
2827 /* This is used to implement conv.u4, so the lhs could be an i8 */
2828 lhs = convert (ctx, lhs, LLVMInt32Type ());
2829 imm = convert (ctx, imm, LLVMInt32Type ());
2830 values [ins->dreg] = LLVMBuildLShr (builder, lhs, imm, dname);
2832 case OP_LSHR_UN_IMM:
2834 values [ins->dreg] = LLVMBuildLShr (builder, lhs, imm, dname);
2837 g_assert_not_reached ();
2842 values [ins->dreg] = LLVMBuildSub (builder, LLVMConstInt (LLVMInt32Type (), 0, FALSE), convert (ctx, lhs, LLVMInt32Type ()), dname);
2845 values [ins->dreg] = LLVMBuildSub (builder, LLVMConstInt (LLVMInt64Type (), 0, FALSE), lhs, dname);
2848 lhs = convert (ctx, lhs, LLVMDoubleType ());
2849 values [ins->dreg] = LLVMBuildFSub (builder, LLVMConstReal (LLVMDoubleType (), 0.0), lhs, dname);
2852 guint32 v = 0xffffffff;
2853 values [ins->dreg] = LLVMBuildXor (builder, LLVMConstInt (LLVMInt32Type (), v, FALSE), convert (ctx, lhs, LLVMInt32Type ()), dname);
2857 guint64 v = 0xffffffffffffffffLL;
2858 values [ins->dreg] = LLVMBuildXor (builder, LLVMConstInt (LLVMInt64Type (), v, FALSE), lhs, dname);
2861 #if defined(TARGET_X86) || defined(TARGET_AMD64)
2863 LLVMValueRef v1, v2;
2865 v1 = LLVMBuildMul (builder, convert (ctx, rhs, IntPtrType ()), LLVMConstInt (IntPtrType (), (1 << ins->backend.shift_amount), FALSE), "");
2866 v2 = LLVMBuildAdd (builder, convert (ctx, lhs, IntPtrType ()), v1, "");
2867 values [ins->dreg] = LLVMBuildAdd (builder, v2, LLVMConstInt (IntPtrType (), ins->inst_imm, FALSE), dname);
2872 case OP_ICONV_TO_I1:
2873 case OP_ICONV_TO_I2:
2874 case OP_ICONV_TO_I4:
2875 case OP_ICONV_TO_U1:
2876 case OP_ICONV_TO_U2:
2877 case OP_ICONV_TO_U4:
2878 case OP_LCONV_TO_I1:
2879 case OP_LCONV_TO_I2:
2880 case OP_LCONV_TO_U1:
2881 case OP_LCONV_TO_U2:
2882 case OP_LCONV_TO_U4: {
2885 sign = (ins->opcode == OP_ICONV_TO_I1) || (ins->opcode == OP_ICONV_TO_I2) || (ins->opcode == OP_ICONV_TO_I4) || (ins->opcode == OP_LCONV_TO_I1) || (ins->opcode == OP_LCONV_TO_I2);
2887 /* Have to do two casts since our vregs have type int */
2888 v = LLVMBuildTrunc (builder, lhs, op_to_llvm_type (ins->opcode), "");
2890 values [ins->dreg] = LLVMBuildSExt (builder, v, LLVMInt32Type (), dname);
2892 values [ins->dreg] = LLVMBuildZExt (builder, v, LLVMInt32Type (), dname);
2895 case OP_ICONV_TO_I8:
2896 values [ins->dreg] = LLVMBuildSExt (builder, lhs, LLVMInt64Type (), dname);
2898 case OP_ICONV_TO_U8:
2899 values [ins->dreg] = LLVMBuildZExt (builder, lhs, LLVMInt64Type (), dname);
2901 case OP_FCONV_TO_I4:
2902 values [ins->dreg] = LLVMBuildFPToSI (builder, lhs, LLVMInt32Type (), dname);
2904 case OP_FCONV_TO_I1:
2905 values [ins->dreg] = LLVMBuildSExt (builder, LLVMBuildFPToSI (builder, lhs, LLVMInt8Type (), dname), LLVMInt32Type (), "");
2907 case OP_FCONV_TO_U1:
2908 values [ins->dreg] = LLVMBuildZExt (builder, LLVMBuildFPToUI (builder, lhs, LLVMInt8Type (), dname), LLVMInt32Type (), "");
2910 case OP_FCONV_TO_I2:
2911 values [ins->dreg] = LLVMBuildSExt (builder, LLVMBuildFPToSI (builder, lhs, LLVMInt16Type (), dname), LLVMInt32Type (), "");
2913 case OP_FCONV_TO_U2:
2914 values [ins->dreg] = LLVMBuildZExt (builder, LLVMBuildFPToUI (builder, lhs, LLVMInt16Type (), dname), LLVMInt32Type (), "");
2916 case OP_FCONV_TO_I8:
2917 values [ins->dreg] = LLVMBuildFPToSI (builder, lhs, LLVMInt64Type (), dname);
2920 values [ins->dreg] = LLVMBuildFPToSI (builder, lhs, IntPtrType (), dname);
2922 case OP_ICONV_TO_R8:
2923 case OP_LCONV_TO_R8:
2924 values [ins->dreg] = LLVMBuildSIToFP (builder, lhs, LLVMDoubleType (), dname);
2926 case OP_LCONV_TO_R_UN:
2927 values [ins->dreg] = LLVMBuildUIToFP (builder, lhs, LLVMDoubleType (), dname);
2929 #if SIZEOF_VOID_P == 4
2932 case OP_LCONV_TO_I4:
2933 values [ins->dreg] = LLVMBuildTrunc (builder, lhs, LLVMInt32Type (), dname);
2935 case OP_ICONV_TO_R4:
2936 case OP_LCONV_TO_R4:
2937 v = LLVMBuildSIToFP (builder, lhs, LLVMFloatType (), "");
2938 values [ins->dreg] = LLVMBuildFPExt (builder, v, LLVMDoubleType (), dname);
2940 case OP_FCONV_TO_R4:
2941 v = LLVMBuildFPTrunc (builder, lhs, LLVMFloatType (), "");
2942 values [ins->dreg] = LLVMBuildFPExt (builder, v, LLVMDoubleType (), dname);
2945 values [ins->dreg] = LLVMBuildSExt (builder, convert (ctx, lhs, LLVMInt32Type ()), LLVMInt64Type (), dname);
2948 values [ins->dreg] = LLVMBuildZExt (builder, convert (ctx, lhs, LLVMInt32Type ()), LLVMInt64Type (), dname);
2951 values [ins->dreg] = LLVMBuildTrunc (builder, lhs, LLVMInt32Type (), dname);
2953 case OP_LOCALLOC_IMM: {
2956 guint32 size = ins->inst_imm;
2957 size = (size + (MONO_ARCH_FRAME_ALIGNMENT - 1)) & ~ (MONO_ARCH_FRAME_ALIGNMENT - 1);
2959 v = mono_llvm_build_alloca (builder, LLVMInt8Type (), LLVMConstInt (LLVMInt32Type (), size, FALSE), MONO_ARCH_FRAME_ALIGNMENT, "");
2961 if (ins->flags & MONO_INST_INIT) {
2962 LLVMValueRef args [5];
2965 args [1] = LLVMConstInt (LLVMInt8Type (), 0, FALSE);
2966 args [2] = LLVMConstInt (LLVMInt32Type (), size, FALSE);
2967 args [3] = LLVMConstInt (LLVMInt32Type (), MONO_ARCH_FRAME_ALIGNMENT, FALSE);
2968 args [4] = LLVMConstInt (LLVMInt1Type (), 0, FALSE);
2969 LLVMBuildCall (builder, LLVMGetNamedFunction (module, memset_func_name), args, memset_param_count, "");
2972 values [ins->dreg] = v;
2976 LLVMValueRef v, size;
2978 size = LLVMBuildAnd (builder, LLVMBuildAdd (builder, convert (ctx, lhs, LLVMInt32Type ()), LLVMConstInt (LLVMInt32Type (), MONO_ARCH_FRAME_ALIGNMENT - 1, FALSE), ""), LLVMConstInt (LLVMInt32Type (), ~ (MONO_ARCH_FRAME_ALIGNMENT - 1), FALSE), "");
2980 v = mono_llvm_build_alloca (builder, LLVMInt8Type (), size, MONO_ARCH_FRAME_ALIGNMENT, "");
2982 if (ins->flags & MONO_INST_INIT) {
2983 LLVMValueRef args [5];
2986 args [1] = LLVMConstInt (LLVMInt8Type (), 0, FALSE);
2988 args [3] = LLVMConstInt (LLVMInt32Type (), MONO_ARCH_FRAME_ALIGNMENT, FALSE);
2989 args [4] = LLVMConstInt (LLVMInt1Type (), 0, FALSE);
2990 LLVMBuildCall (builder, LLVMGetNamedFunction (module, memset_func_name), args, memset_param_count, "");
2992 values [ins->dreg] = v;
2996 case OP_LOADI1_MEMBASE:
2997 case OP_LOADU1_MEMBASE:
2998 case OP_LOADI2_MEMBASE:
2999 case OP_LOADU2_MEMBASE:
3000 case OP_LOADI4_MEMBASE:
3001 case OP_LOADU4_MEMBASE:
3002 case OP_LOADI8_MEMBASE:
3003 case OP_LOADR4_MEMBASE:
3004 case OP_LOADR8_MEMBASE:
3005 case OP_LOAD_MEMBASE:
3013 LLVMValueRef base, index, addr;
3015 gboolean sext = FALSE, zext = FALSE;
3016 gboolean is_volatile = (ins->flags & MONO_INST_FAULT);
3018 t = load_store_to_llvm_type (ins->opcode, &size, &sext, &zext);
3023 if ((ins->opcode == OP_LOADI8_MEM) || (ins->opcode == OP_LOAD_MEM) || (ins->opcode == OP_LOADI4_MEM) || (ins->opcode == OP_LOADU4_MEM) || (ins->opcode == OP_LOADU1_MEM) || (ins->opcode == OP_LOADU2_MEM)) {
3024 addr = LLVMConstInt (IntPtrType (), ins->inst_imm, FALSE);
3029 if (ins->inst_offset == 0) {
3031 } else if (ins->inst_offset % size != 0) {
3032 /* Unaligned load */
3033 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset, FALSE);
3034 addr = LLVMBuildGEP (builder, convert (ctx, base, LLVMPointerType (LLVMInt8Type (), 0)), &index, 1, "");
3036 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset / size, FALSE);
3037 addr = LLVMBuildGEP (builder, convert (ctx, base, LLVMPointerType (t, 0)), &index, 1, "");
3041 addr = convert (ctx, addr, LLVMPointerType (t, 0));
3043 values [ins->dreg] = emit_load (ctx, bb, &builder, size, addr, dname, is_volatile);
3045 if (!is_volatile && (ins->flags & MONO_INST_INVARIANT_LOAD)) {
3047 * These will signal LLVM that these loads do not alias any stores, and
3048 * they can't fail, allowing them to be hoisted out of loops.
3050 set_invariant_load_flag (values [ins->dreg]);
3051 set_metadata_flag (values [ins->dreg], "mono.nofail.load");
3055 values [ins->dreg] = LLVMBuildSExt (builder, values [ins->dreg], LLVMInt32Type (), dname);
3057 values [ins->dreg] = LLVMBuildZExt (builder, values [ins->dreg], LLVMInt32Type (), dname);
3058 else if (ins->opcode == OP_LOADR4_MEMBASE)
3059 values [ins->dreg] = LLVMBuildFPExt (builder, values [ins->dreg], LLVMDoubleType (), dname);
3063 case OP_STOREI1_MEMBASE_REG:
3064 case OP_STOREI2_MEMBASE_REG:
3065 case OP_STOREI4_MEMBASE_REG:
3066 case OP_STOREI8_MEMBASE_REG:
3067 case OP_STORER4_MEMBASE_REG:
3068 case OP_STORER8_MEMBASE_REG:
3069 case OP_STORE_MEMBASE_REG: {
3071 LLVMValueRef index, addr;
3073 gboolean sext = FALSE, zext = FALSE;
3074 gboolean is_volatile = (ins->flags & MONO_INST_FAULT);
3076 if (!values [ins->inst_destbasereg])
3077 LLVM_FAILURE (ctx, "inst_destbasereg");
3079 t = load_store_to_llvm_type (ins->opcode, &size, &sext, &zext);
3081 if (ins->inst_offset % size != 0) {
3082 /* Unaligned store */
3083 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset, FALSE);
3084 addr = LLVMBuildGEP (builder, convert (ctx, values [ins->inst_destbasereg], LLVMPointerType (LLVMInt8Type (), 0)), &index, 1, "");
3086 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset / size, FALSE);
3087 addr = LLVMBuildGEP (builder, convert (ctx, values [ins->inst_destbasereg], LLVMPointerType (t, 0)), &index, 1, "");
3089 emit_store (ctx, bb, &builder, size, convert (ctx, values [ins->sreg1], t), convert (ctx, addr, LLVMPointerType (t, 0)), is_volatile);
3093 case OP_STOREI1_MEMBASE_IMM:
3094 case OP_STOREI2_MEMBASE_IMM:
3095 case OP_STOREI4_MEMBASE_IMM:
3096 case OP_STOREI8_MEMBASE_IMM:
3097 case OP_STORE_MEMBASE_IMM: {
3099 LLVMValueRef index, addr;
3101 gboolean sext = FALSE, zext = FALSE;
3102 gboolean is_volatile = (ins->flags & MONO_INST_FAULT);
3104 t = load_store_to_llvm_type (ins->opcode, &size, &sext, &zext);
3106 if (ins->inst_offset % size != 0) {
3107 /* Unaligned store */
3108 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset, FALSE);
3109 addr = LLVMBuildGEP (builder, convert (ctx, values [ins->inst_destbasereg], LLVMPointerType (LLVMInt8Type (), 0)), &index, 1, "");
3111 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset / size, FALSE);
3112 addr = LLVMBuildGEP (builder, convert (ctx, values [ins->inst_destbasereg], LLVMPointerType (t, 0)), &index, 1, "");
3114 emit_store (ctx, bb, &builder, size, convert (ctx, LLVMConstInt (IntPtrType (), ins->inst_imm, FALSE), t), addr, is_volatile);
3119 emit_load (ctx, bb, &builder, sizeof (gpointer), convert (ctx, lhs, LLVMPointerType (IntPtrType (), 0)), "", TRUE);
3121 case OP_OUTARG_VTRETADDR:
3128 case OP_VOIDCALL_MEMBASE:
3129 case OP_CALL_MEMBASE:
3130 case OP_LCALL_MEMBASE:
3131 case OP_FCALL_MEMBASE:
3132 case OP_VCALL_MEMBASE:
3133 case OP_VOIDCALL_REG:
3137 case OP_VCALL_REG: {
3138 process_call (ctx, bb, &builder, ins);
3139 CHECK_FAILURE (ctx);
3144 LLVMValueRef indexes [2];
3146 LLVMValueRef got_entry_addr;
3149 * FIXME: Can't allocate from the cfg mempool since that is freed if
3150 * the LLVM compile fails.
3152 ji = g_new0 (MonoJumpInfo, 1);
3153 ji->type = (MonoJumpInfoType)ins->inst_i1;
3154 ji->data.target = ins->inst_p0;
3156 ji = mono_aot_patch_info_dup (ji);
3158 ji->next = cfg->patch_info;
3159 cfg->patch_info = ji;
3161 //mono_add_patch_info (cfg, 0, (MonoJumpInfoType)ins->inst_i1, ins->inst_p0);
3162 got_offset = mono_aot_get_got_offset (cfg->patch_info);
3164 indexes [0] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
3165 indexes [1] = LLVMConstInt (LLVMInt32Type (), (gssize)got_offset, FALSE);
3166 got_entry_addr = LLVMBuildGEP (builder, ctx->lmodule->got_var, indexes, 2, "");
3168 values [ins->dreg] = LLVMBuildLoad (builder, got_entry_addr, dname);
3169 set_invariant_load_flag (values [ins->dreg]);
3172 case OP_NOT_REACHED:
3173 LLVMBuildUnreachable (builder);
3174 has_terminator = TRUE;
3175 g_assert (bb->block_num < cfg->max_block_num);
3176 ctx->unreachable [bb->block_num] = TRUE;
3177 /* Might have instructions after this */
3179 MonoInst *next = ins->next;
3181 * FIXME: If later code uses the regs defined by these instructions,
3182 * compilation will fail.
3184 MONO_DELETE_INS (bb, next);
3188 MonoInst *var = ins->inst_p0;
3190 values [ins->dreg] = addresses [var->dreg];
3194 LLVMValueRef args [1];
3196 args [0] = convert (ctx, lhs, LLVMDoubleType ());
3197 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, "llvm.sin.f64"), args, 1, dname);
3201 LLVMValueRef args [1];
3203 args [0] = convert (ctx, lhs, LLVMDoubleType ());
3204 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, "llvm.cos.f64"), args, 1, dname);
3208 LLVMValueRef args [1];
3211 /* This no longer seems to happen */
3213 * LLVM optimizes sqrt(nan) into undefined in
3214 * lib/Analysis/ConstantFolding.cpp
3215 * Also, sqrt(NegativeInfinity) is optimized into 0.
3217 LLVM_FAILURE (ctx, "sqrt");
3219 args [0] = convert (ctx, lhs, LLVMDoubleType ());
3220 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, "llvm.sqrt.f64"), args, 1, dname);
3224 LLVMValueRef args [1];
3226 args [0] = convert (ctx, lhs, LLVMDoubleType ());
3227 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, "fabs"), args, 1, dname);
3241 lhs = convert (ctx, lhs, regtype_to_llvm_type (spec [MONO_INST_DEST]));
3242 rhs = convert (ctx, rhs, regtype_to_llvm_type (spec [MONO_INST_DEST]));
3244 switch (ins->opcode) {
3247 v = LLVMBuildICmp (builder, LLVMIntSLE, lhs, rhs, "");
3251 v = LLVMBuildICmp (builder, LLVMIntSGE, lhs, rhs, "");
3255 v = LLVMBuildICmp (builder, LLVMIntULE, lhs, rhs, "");
3259 v = LLVMBuildICmp (builder, LLVMIntUGE, lhs, rhs, "");
3262 g_assert_not_reached ();
3265 values [ins->dreg] = LLVMBuildSelect (builder, v, lhs, rhs, dname);
3268 case OP_ATOMIC_EXCHANGE_I4:
3269 case OP_ATOMIC_EXCHANGE_I8: {
3270 LLVMValueRef args [2];
3273 if (ins->opcode == OP_ATOMIC_EXCHANGE_I4)
3274 t = LLVMInt32Type ();
3276 t = LLVMInt64Type ();
3278 g_assert (ins->inst_offset == 0);
3280 args [0] = convert (ctx, lhs, LLVMPointerType (t, 0));
3281 args [1] = convert (ctx, rhs, t);
3283 values [ins->dreg] = mono_llvm_build_atomic_rmw (builder, LLVM_ATOMICRMW_OP_XCHG, args [0], args [1]);
3286 case OP_ATOMIC_ADD_NEW_I4:
3287 case OP_ATOMIC_ADD_NEW_I8: {
3288 LLVMValueRef args [2];
3291 if (ins->opcode == OP_ATOMIC_ADD_NEW_I4)
3292 t = LLVMInt32Type ();
3294 t = LLVMInt64Type ();
3296 g_assert (ins->inst_offset == 0);
3298 args [0] = convert (ctx, lhs, LLVMPointerType (t, 0));
3299 args [1] = convert (ctx, rhs, t);
3300 values [ins->dreg] = LLVMBuildAdd (builder, mono_llvm_build_atomic_rmw (builder, LLVM_ATOMICRMW_OP_ADD, args [0], args [1]), args [1], dname);
3303 case OP_ATOMIC_CAS_I4:
3304 case OP_ATOMIC_CAS_I8: {
3305 LLVMValueRef args [3];
3308 if (ins->opcode == OP_ATOMIC_CAS_I4)
3309 t = LLVMInt32Type ();
3311 t = LLVMInt64Type ();
3313 args [0] = convert (ctx, lhs, LLVMPointerType (t, 0));
3315 args [1] = convert (ctx, values [ins->sreg3], t);
3317 args [2] = convert (ctx, values [ins->sreg2], t);
3318 values [ins->dreg] = mono_llvm_build_cmpxchg (builder, args [0], args [1], args [2]);
3321 case OP_MEMORY_BARRIER: {
3322 mono_llvm_build_fence (builder);
3325 case OP_RELAXED_NOP: {
3326 #if defined(TARGET_AMD64) || defined(TARGET_X86)
3327 emit_call (ctx, bb, &builder, LLVMGetNamedFunction (ctx->module, "llvm.x86.sse2.pause"), NULL, 0);
3334 #if (defined(TARGET_AMD64) || defined(TARGET_X86)) && defined(__linux__)
3336 // 257 == FS segment register
3337 LLVMTypeRef ptrtype = LLVMPointerType (IntPtrType (), 257);
3339 // 256 == GS segment register
3340 LLVMTypeRef ptrtype = LLVMPointerType (IntPtrType (), 256);
3343 values [ins->dreg] = LLVMBuildLoad (builder, LLVMBuildIntToPtr (builder, LLVMConstInt (IntPtrType (), ins->inst_offset, TRUE), ptrtype, ""), "");
3344 #elif defined(TARGET_AMD64) && defined(TARGET_OSX)
3345 /* See mono_amd64_emit_tls_get () */
3346 int offset = mono_amd64_get_tls_gs_offset () + (ins->inst_offset * 8);
3348 // 256 == GS segment register
3349 LLVMTypeRef ptrtype = LLVMPointerType (IntPtrType (), 256);
3350 values [ins->dreg] = LLVMBuildLoad (builder, LLVMBuildIntToPtr (builder, LLVMConstInt (IntPtrType (), offset, TRUE), ptrtype, ""), "");
3352 LLVM_FAILURE (ctx, "opcode tls-get");
3357 case OP_TLS_GET_REG: {
3358 #if defined(TARGET_AMD64) && defined(TARGET_OSX)
3359 /* See emit_tls_get_reg () */
3360 LLVMValueRef base, shifted_offset, offset;
3362 base = LLVMConstInt (LLVMInt32Type (), mono_amd64_get_tls_gs_offset (), TRUE);
3363 shifted_offset = LLVMBuildMul (builder, convert (ctx, lhs, LLVMInt32Type ()), LLVMConstInt (LLVMInt32Type (), 8, TRUE), "");
3364 offset = LLVMBuildAdd (builder, base, shifted_offset, "");
3365 // 256 == GS segment register
3366 LLVMTypeRef ptrtype = LLVMPointerType (IntPtrType (), 256);
3367 values [ins->dreg] = LLVMBuildLoad (builder, LLVMBuildIntToPtr (builder, offset, ptrtype, ""), "");
3369 LLVM_FAILURE (ctx, "opcode tls-get");
3378 case OP_IADD_OVF_UN:
3380 case OP_ISUB_OVF_UN:
3382 case OP_IMUL_OVF_UN:
3383 #if SIZEOF_VOID_P == 8
3385 case OP_LADD_OVF_UN:
3387 case OP_LSUB_OVF_UN:
3389 case OP_LMUL_OVF_UN:
3392 LLVMValueRef args [2], val, ovf, func;
3394 args [0] = convert (ctx, lhs, op_to_llvm_type (ins->opcode));
3395 args [1] = convert (ctx, rhs, op_to_llvm_type (ins->opcode));
3396 func = LLVMGetNamedFunction (module, ovf_op_to_intrins (ins->opcode));
3398 val = LLVMBuildCall (builder, func, args, 2, "");
3399 values [ins->dreg] = LLVMBuildExtractValue (builder, val, 0, dname);
3400 ovf = LLVMBuildExtractValue (builder, val, 1, "");
3401 emit_cond_system_exception (ctx, bb, "OverflowException", ovf);
3402 CHECK_FAILURE (ctx);
3403 builder = ctx->builder;
3409 * We currently model them using arrays. Promotion to local vregs is
3410 * disabled for them in mono_handle_global_vregs () in the LLVM case,
3411 * so we always have an entry in cfg->varinfo for them.
3412 * FIXME: Is this needed ?
3415 MonoClass *klass = ins->klass;
3416 LLVMValueRef args [5];
3420 LLVM_FAILURE (ctx, "!klass");
3424 if (!addresses [ins->dreg])
3425 addresses [ins->dreg] = build_alloca (ctx, &klass->byval_arg);
3426 args [0] = LLVMBuildBitCast (builder, addresses [ins->dreg], LLVMPointerType (LLVMInt8Type (), 0), "");
3427 args [1] = LLVMConstInt (LLVMInt8Type (), 0, FALSE);
3428 args [2] = LLVMConstInt (LLVMInt32Type (), mono_class_value_size (klass, NULL), FALSE);
3430 args [3] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
3431 args [4] = LLVMConstInt (LLVMInt1Type (), 0, FALSE);
3432 LLVMBuildCall (builder, LLVMGetNamedFunction (module, memset_func_name), args, memset_param_count, "");
3436 case OP_STOREV_MEMBASE:
3437 case OP_LOADV_MEMBASE:
3439 MonoClass *klass = ins->klass;
3440 LLVMValueRef src = NULL, dst, args [5];
3441 gboolean done = FALSE;
3445 LLVM_FAILURE (ctx, "!klass");
3449 if (mini_is_gsharedvt_klass (cfg, klass)) {
3451 LLVM_FAILURE (ctx, "gsharedvt");
3455 switch (ins->opcode) {
3456 case OP_STOREV_MEMBASE:
3457 if (cfg->gen_write_barriers && klass->has_references && ins->inst_destbasereg != cfg->frame_reg &&
3458 LLVMGetInstructionOpcode (values [ins->inst_destbasereg]) != LLVMAlloca) {
3459 /* Decomposed earlier */
3460 g_assert_not_reached ();
3463 if (!addresses [ins->sreg1]) {
3465 g_assert (values [ins->sreg1]);
3466 dst = convert (ctx, LLVMBuildAdd (builder, convert (ctx, values [ins->inst_destbasereg], IntPtrType ()), LLVMConstInt (IntPtrType (), ins->inst_offset, FALSE), ""), LLVMPointerType (type_to_llvm_type (ctx, &klass->byval_arg), 0));
3467 LLVMBuildStore (builder, values [ins->sreg1], dst);
3470 src = LLVMBuildBitCast (builder, addresses [ins->sreg1], LLVMPointerType (LLVMInt8Type (), 0), "");
3471 dst = convert (ctx, LLVMBuildAdd (builder, convert (ctx, values [ins->inst_destbasereg], IntPtrType ()), LLVMConstInt (IntPtrType (), ins->inst_offset, FALSE), ""), LLVMPointerType (LLVMInt8Type (), 0));
3474 case OP_LOADV_MEMBASE:
3475 if (!addresses [ins->dreg])
3476 addresses [ins->dreg] = build_alloca (ctx, &klass->byval_arg);
3477 src = convert (ctx, LLVMBuildAdd (builder, convert (ctx, values [ins->inst_basereg], IntPtrType ()), LLVMConstInt (IntPtrType (), ins->inst_offset, FALSE), ""), LLVMPointerType (LLVMInt8Type (), 0));
3478 dst = LLVMBuildBitCast (builder, addresses [ins->dreg], LLVMPointerType (LLVMInt8Type (), 0), "");
3481 if (!addresses [ins->sreg1])
3482 addresses [ins->sreg1] = build_alloca (ctx, &klass->byval_arg);
3483 if (!addresses [ins->dreg])
3484 addresses [ins->dreg] = build_alloca (ctx, &klass->byval_arg);
3485 src = LLVMBuildBitCast (builder, addresses [ins->sreg1], LLVMPointerType (LLVMInt8Type (), 0), "");
3486 dst = LLVMBuildBitCast (builder, addresses [ins->dreg], LLVMPointerType (LLVMInt8Type (), 0), "");
3489 g_assert_not_reached ();
3491 CHECK_FAILURE (ctx);
3498 args [2] = LLVMConstInt (LLVMInt32Type (), mono_class_value_size (klass, NULL), FALSE);
3499 args [3] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
3501 args [3] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
3502 args [4] = LLVMConstInt (LLVMInt1Type (), 0, FALSE);
3503 LLVMBuildCall (builder, LLVMGetNamedFunction (module, memcpy_func_name), args, memcpy_param_count, "");
3506 case OP_LLVM_OUTARG_VT:
3507 if (!addresses [ins->sreg1]) {
3508 addresses [ins->sreg1] = build_alloca (ctx, &ins->klass->byval_arg);
3509 g_assert (values [ins->sreg1]);
3510 LLVMBuildStore (builder, values [ins->sreg1], addresses [ins->sreg1]);
3512 addresses [ins->dreg] = addresses [ins->sreg1];
3518 #if defined(TARGET_X86) || defined(TARGET_AMD64)
3520 values [ins->dreg] = LLVMConstNull (type_to_llvm_type (ctx, &ins->klass->byval_arg));
3523 case OP_LOADX_MEMBASE: {
3524 LLVMTypeRef t = type_to_llvm_type (ctx, &ins->klass->byval_arg);
3527 src = convert (ctx, LLVMBuildAdd (builder, convert (ctx, values [ins->inst_basereg], IntPtrType ()), LLVMConstInt (IntPtrType (), ins->inst_offset, FALSE), ""), LLVMPointerType (t, 0));
3528 values [ins->dreg] = mono_llvm_build_aligned_load (builder, src, "", FALSE, 1);
3531 case OP_STOREX_MEMBASE: {
3532 LLVMTypeRef t = LLVMTypeOf (values [ins->sreg1]);
3535 dest = convert (ctx, LLVMBuildAdd (builder, convert (ctx, values [ins->inst_destbasereg], IntPtrType ()), LLVMConstInt (IntPtrType (), ins->inst_offset, FALSE), ""), LLVMPointerType (t, 0));
3536 mono_llvm_build_aligned_store (builder, values [ins->sreg1], dest, FALSE, 1);
3543 values [ins->dreg] = LLVMBuildAdd (builder, lhs, rhs, "");
3547 values [ins->dreg] = LLVMBuildFAdd (builder, lhs, rhs, "");
3553 values [ins->dreg] = LLVMBuildSub (builder, lhs, rhs, "");
3557 values [ins->dreg] = LLVMBuildFSub (builder, lhs, rhs, "");
3561 values [ins->dreg] = LLVMBuildFMul (builder, lhs, rhs, "");
3565 values [ins->dreg] = LLVMBuildFDiv (builder, lhs, rhs, "");
3568 values [ins->dreg] = LLVMBuildAnd (builder, lhs, rhs, "");
3571 values [ins->dreg] = LLVMBuildOr (builder, lhs, rhs, "");
3574 values [ins->dreg] = LLVMBuildXor (builder, lhs, rhs, "");
3578 values [ins->dreg] = LLVMBuildMul (builder, lhs, rhs, "");
3589 LLVMValueRef v = NULL;
3591 switch (ins->opcode) {
3596 t = LLVMVectorType (LLVMInt32Type (), 4);
3597 rt = LLVMVectorType (LLVMFloatType (), 4);
3603 t = LLVMVectorType (LLVMInt64Type (), 2);
3604 rt = LLVMVectorType (LLVMDoubleType (), 2);
3607 t = LLVMInt32Type ();
3608 rt = LLVMInt32Type ();
3609 g_assert_not_reached ();
3612 lhs = LLVMBuildBitCast (builder, lhs, t, "");
3613 rhs = LLVMBuildBitCast (builder, rhs, t, "");
3614 switch (ins->opcode) {
3617 v = LLVMBuildAnd (builder, lhs, rhs, "");
3621 v = LLVMBuildOr (builder, lhs, rhs, "");
3625 v = LLVMBuildXor (builder, lhs, rhs, "");
3629 v = LLVMBuildAnd (builder, rhs, LLVMBuildNot (builder, lhs, ""), "");
3632 values [ins->dreg] = LLVMBuildBitCast (builder, v, rt, "");
3656 case OP_PADDB_SAT_UN:
3657 case OP_PADDW_SAT_UN:
3658 case OP_PSUBB_SAT_UN:
3659 case OP_PSUBW_SAT_UN:
3667 case OP_PMULW_HIGH_UN: {
3668 LLVMValueRef args [2];
3673 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, simd_op_to_intrins (ins->opcode)), args, 2, dname);
3680 values [ins->dreg] = LLVMBuildSExt (builder, LLVMBuildICmp (builder, LLVMIntEQ, lhs, rhs, ""), LLVMTypeOf (lhs), "");
3684 values [ins->dreg] = LLVMBuildSExt (builder, LLVMBuildICmp (builder, LLVMIntSGT, lhs, rhs, ""), LLVMTypeOf (lhs), "");
3692 case OP_EXTRACTX_U2:
3694 case OP_EXTRACT_U1: {
3696 gboolean zext = FALSE;
3698 t = simd_op_to_llvm_type (ins->opcode);
3700 switch (ins->opcode) {
3708 case OP_EXTRACTX_U2:
3713 t = LLVMInt32Type ();
3714 g_assert_not_reached ();
3717 lhs = LLVMBuildBitCast (builder, lhs, t, "");
3718 values [ins->dreg] = LLVMBuildExtractElement (builder, lhs, LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), "");
3720 values [ins->dreg] = LLVMBuildZExt (builder, values [ins->dreg], LLVMInt32Type (), "");
3729 case OP_EXPAND_R8: {
3730 LLVMTypeRef t = simd_op_to_llvm_type (ins->opcode);
3731 LLVMValueRef mask [16], v;
3733 for (i = 0; i < 16; ++i)
3734 mask [i] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
3736 v = convert (ctx, values [ins->sreg1], LLVMGetElementType (t));
3738 values [ins->dreg] = LLVMBuildInsertElement (builder, LLVMConstNull (t), v, LLVMConstInt (LLVMInt32Type (), 0, FALSE), "");
3739 values [ins->dreg] = LLVMBuildShuffleVector (builder, values [ins->dreg], LLVMGetUndef (t), LLVMConstVector (mask, LLVMGetVectorSize (t)), "");
3744 values [ins->dreg] = LLVMBuildInsertElement (builder, values [ins->sreg1], convert (ctx, values [ins->sreg2], LLVMInt8Type ()), LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), dname);
3747 values [ins->dreg] = LLVMBuildInsertElement (builder, values [ins->sreg1], convert (ctx, values [ins->sreg2], LLVMInt16Type ()), LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), dname);
3750 values [ins->dreg] = LLVMBuildInsertElement (builder, values [ins->sreg1], convert (ctx, values [ins->sreg2], LLVMInt32Type ()), LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), dname);
3753 values [ins->dreg] = LLVMBuildInsertElement (builder, values [ins->sreg1], convert (ctx, values [ins->sreg2], LLVMInt64Type ()), LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), dname);
3756 values [ins->dreg] = LLVMBuildInsertElement (builder, values [ins->sreg1], convert (ctx, values [ins->sreg2], LLVMFloatType ()), LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), dname);
3759 values [ins->dreg] = LLVMBuildInsertElement (builder, values [ins->sreg1], convert (ctx, values [ins->sreg2], LLVMDoubleType ()), LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), dname);
3770 case OP_EXTRACT_MASK:
3777 v = convert (ctx, values [ins->sreg1], simd_op_to_llvm_type (ins->opcode));
3779 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, simd_op_to_intrins (ins->opcode)), &v, 1, dname);
3783 case OP_ICONV_TO_R8_RAW:
3784 /* Same as OP_ICONV_TO_R8 */
3785 values [ins->dreg] = convert (ctx, LLVMBuildBitCast (builder, lhs, LLVMFloatType (), ""), LLVMDoubleType ());
3790 LLVMValueRef args [3];
3794 args [2] = LLVMConstInt (LLVMInt8Type (), ins->inst_c0, FALSE);
3796 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, simd_op_to_intrins (ins->opcode)), args, 3, dname);
3801 /* This is only used for implementing shifts by non-immediate */
3802 values [ins->dreg] = lhs;
3813 LLVMValueRef args [3];
3816 args [1] = LLVMConstInt (LLVMInt32Type (), ins->inst_imm, FALSE);
3818 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, simd_op_to_intrins (ins->opcode)), args, 2, dname);
3829 case OP_PSHLQ_REG: {
3830 LLVMValueRef args [3];
3833 args [1] = values [ins->sreg2];
3835 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, simd_op_to_intrins (ins->opcode)), args, 2, dname);
3842 case OP_PSHUFLEW_LOW:
3843 case OP_PSHUFLEW_HIGH: {
3845 LLVMValueRef v1 = NULL, v2 = NULL, mask_values [16];
3846 int i, mask_size = 0;
3847 int imask = ins->inst_c0;
3849 /* Convert the x86 shuffle mask to LLVM's */
3850 switch (ins->opcode) {
3853 mask [0] = ((imask >> 0) & 3);
3854 mask [1] = ((imask >> 2) & 3);
3855 mask [2] = ((imask >> 4) & 3) + 4;
3856 mask [3] = ((imask >> 6) & 3) + 4;
3857 v1 = values [ins->sreg1];
3858 v2 = values [ins->sreg2];
3862 mask [0] = ((imask >> 0) & 1);
3863 mask [1] = ((imask >> 1) & 1) + 2;
3864 v1 = values [ins->sreg1];
3865 v2 = values [ins->sreg2];
3867 case OP_PSHUFLEW_LOW:
3869 mask [0] = ((imask >> 0) & 3);
3870 mask [1] = ((imask >> 2) & 3);
3871 mask [2] = ((imask >> 4) & 3);
3872 mask [3] = ((imask >> 6) & 3);
3877 v1 = values [ins->sreg1];
3878 v2 = LLVMGetUndef (LLVMTypeOf (v1));
3880 case OP_PSHUFLEW_HIGH:
3886 mask [4] = 4 + ((imask >> 0) & 3);
3887 mask [5] = 4 + ((imask >> 2) & 3);
3888 mask [6] = 4 + ((imask >> 4) & 3);
3889 mask [7] = 4 + ((imask >> 6) & 3);
3890 v1 = values [ins->sreg1];
3891 v2 = LLVMGetUndef (LLVMTypeOf (v1));
3895 mask [0] = ((imask >> 0) & 3);
3896 mask [1] = ((imask >> 2) & 3);
3897 mask [2] = ((imask >> 4) & 3);
3898 mask [3] = ((imask >> 6) & 3);
3899 v1 = values [ins->sreg1];
3900 v2 = LLVMGetUndef (LLVMTypeOf (v1));
3903 g_assert_not_reached ();
3905 for (i = 0; i < mask_size; ++i)
3906 mask_values [i] = LLVMConstInt (LLVMInt32Type (), mask [i], FALSE);
3908 values [ins->dreg] =
3909 LLVMBuildShuffleVector (builder, v1, v2,
3910 LLVMConstVector (mask_values, mask_size), dname);
3914 case OP_UNPACK_LOWB:
3915 case OP_UNPACK_LOWW:
3916 case OP_UNPACK_LOWD:
3917 case OP_UNPACK_LOWQ:
3918 case OP_UNPACK_LOWPS:
3919 case OP_UNPACK_LOWPD:
3920 case OP_UNPACK_HIGHB:
3921 case OP_UNPACK_HIGHW:
3922 case OP_UNPACK_HIGHD:
3923 case OP_UNPACK_HIGHQ:
3924 case OP_UNPACK_HIGHPS:
3925 case OP_UNPACK_HIGHPD: {
3927 LLVMValueRef mask_values [16];
3928 int i, mask_size = 0;
3929 gboolean low = FALSE;
3931 switch (ins->opcode) {
3932 case OP_UNPACK_LOWB:
3936 case OP_UNPACK_LOWW:
3940 case OP_UNPACK_LOWD:
3941 case OP_UNPACK_LOWPS:
3945 case OP_UNPACK_LOWQ:
3946 case OP_UNPACK_LOWPD:
3950 case OP_UNPACK_HIGHB:
3953 case OP_UNPACK_HIGHW:
3956 case OP_UNPACK_HIGHD:
3957 case OP_UNPACK_HIGHPS:
3960 case OP_UNPACK_HIGHQ:
3961 case OP_UNPACK_HIGHPD:
3965 g_assert_not_reached ();
3969 for (i = 0; i < (mask_size / 2); ++i) {
3971 mask [(i * 2) + 1] = mask_size + i;
3974 for (i = 0; i < (mask_size / 2); ++i) {
3975 mask [(i * 2)] = (mask_size / 2) + i;
3976 mask [(i * 2) + 1] = mask_size + (mask_size / 2) + i;
3980 for (i = 0; i < mask_size; ++i)
3981 mask_values [i] = LLVMConstInt (LLVMInt32Type (), mask [i], FALSE);
3983 values [ins->dreg] =
3984 LLVMBuildShuffleVector (builder, values [ins->sreg1], values [ins->sreg2],
3985 LLVMConstVector (mask_values, mask_size), dname);
3990 LLVMTypeRef t = simd_op_to_llvm_type (ins->opcode);
3991 LLVMValueRef v, val;
3993 v = LLVMBuildExtractElement (builder, lhs, LLVMConstInt (LLVMInt32Type (), 0, FALSE), "");
3994 val = LLVMConstNull (t);
3995 val = LLVMBuildInsertElement (builder, val, v, LLVMConstInt (LLVMInt32Type (), 0, FALSE), "");
3996 val = LLVMBuildInsertElement (builder, val, v, LLVMConstInt (LLVMInt32Type (), 1, FALSE), dname);
3998 values [ins->dreg] = val;
4002 case OP_DUPPS_HIGH: {
4003 LLVMTypeRef t = simd_op_to_llvm_type (ins->opcode);
4004 LLVMValueRef v1, v2, val;
4007 if (ins->opcode == OP_DUPPS_LOW) {
4008 v1 = LLVMBuildExtractElement (builder, lhs, LLVMConstInt (LLVMInt32Type (), 0, FALSE), "");
4009 v2 = LLVMBuildExtractElement (builder, lhs, LLVMConstInt (LLVMInt32Type (), 2, FALSE), "");
4011 v1 = LLVMBuildExtractElement (builder, lhs, LLVMConstInt (LLVMInt32Type (), 1, FALSE), "");
4012 v2 = LLVMBuildExtractElement (builder, lhs, LLVMConstInt (LLVMInt32Type (), 3, FALSE), "");
4014 val = LLVMConstNull (t);
4015 val = LLVMBuildInsertElement (builder, val, v1, LLVMConstInt (LLVMInt32Type (), 0, FALSE), "");
4016 val = LLVMBuildInsertElement (builder, val, v1, LLVMConstInt (LLVMInt32Type (), 1, FALSE), "");
4017 val = LLVMBuildInsertElement (builder, val, v2, LLVMConstInt (LLVMInt32Type (), 2, FALSE), "");
4018 val = LLVMBuildInsertElement (builder, val, v2, LLVMConstInt (LLVMInt32Type (), 3, FALSE), "");
4020 values [ins->dreg] = val;
4030 * EXCEPTION HANDLING
4032 case OP_IMPLICIT_EXCEPTION:
4033 /* This marks a place where an implicit exception can happen */
4034 if (bb->region != -1)
4035 LLVM_FAILURE (ctx, "implicit-exception");
4039 MonoMethodSignature *throw_sig;
4040 LLVMValueRef callee, arg;
4041 gboolean rethrow = (ins->opcode == OP_RETHROW);
4042 const char *icall_name;
4044 callee = rethrow ? ctx->lmodule->rethrow : ctx->lmodule->throw;
4045 icall_name = rethrow ? "mono_arch_rethrow_exception" : "mono_arch_throw_exception";
4048 throw_sig = mono_metadata_signature_alloc (mono_get_corlib (), 1);
4049 throw_sig->ret = &mono_get_void_class ()->byval_arg;
4050 throw_sig->params [0] = &mono_get_object_class ()->byval_arg;
4051 if (cfg->compile_aot) {
4052 callee = get_plt_entry (ctx, sig_to_llvm_sig (ctx, throw_sig), MONO_PATCH_INFO_INTERNAL_METHOD, icall_name);
4054 callee = LLVMAddFunction (module, icall_name, sig_to_llvm_sig (ctx, throw_sig));
4058 * LLVM doesn't push the exception argument, so we need a different
4061 LLVMAddGlobalMapping (ee, callee, resolve_patch (cfg, MONO_PATCH_INFO_INTERNAL_METHOD, rethrow ? "llvm_rethrow_exception_trampoline" : "llvm_throw_exception_trampoline"));
4063 LLVMAddGlobalMapping (ee, callee, resolve_patch (cfg, MONO_PATCH_INFO_INTERNAL_METHOD, icall_name));
4067 mono_memory_barrier ();
4069 ctx->lmodule->rethrow = callee;
4071 ctx->lmodule->throw = callee;
4073 arg = convert (ctx, lhs, type_to_llvm_type (ctx, &mono_get_object_class ()->byval_arg));
4074 emit_call (ctx, bb, &builder, callee, &arg, 1);
4077 case OP_CALL_HANDLER: {
4079 * We don't 'call' handlers, but instead simply branch to them.
4080 * The code generated by ENDFINALLY will branch back to us.
4082 LLVMBasicBlockRef noex_bb;
4084 BBInfo *info = &bblocks [ins->inst_target_bb->block_num];
4086 bb_list = info->call_handler_return_bbs;
4089 * Set the indicator variable for the finally clause.
4091 lhs = info->finally_ind;
4093 LLVMBuildStore (builder, LLVMConstInt (LLVMInt32Type (), g_slist_length (bb_list) + 1, FALSE), lhs);
4095 /* Branch to the finally clause */
4096 LLVMBuildBr (builder, info->call_handler_target_bb);
4098 noex_bb = gen_bb (ctx, "CALL_HANDLER_CONT_BB");
4099 info->call_handler_return_bbs = g_slist_append_mempool (cfg->mempool, info->call_handler_return_bbs, noex_bb);
4101 builder = ctx->builder = create_builder (ctx);
4102 LLVMPositionBuilderAtEnd (ctx->builder, noex_bb);
4104 bblocks [bb->block_num].end_bblock = noex_bb;
4107 case OP_START_HANDLER: {
4110 case OP_ENDFINALLY: {
4111 LLVMBasicBlockRef resume_bb;
4112 MonoBasicBlock *handler_bb;
4113 LLVMValueRef val, switch_ins, callee;
4117 handler_bb = g_hash_table_lookup (ctx->region_to_handler, GUINT_TO_POINTER (mono_get_block_region_notry (cfg, bb->region)));
4118 g_assert (handler_bb);
4119 info = &bblocks [handler_bb->block_num];
4120 lhs = info->finally_ind;
4123 bb_list = info->call_handler_return_bbs;
4125 resume_bb = gen_bb (ctx, "ENDFINALLY_RESUME_BB");
4127 /* Load the finally variable */
4128 val = LLVMBuildLoad (builder, lhs, "");
4130 /* Reset the variable */
4131 LLVMBuildStore (builder, LLVMConstInt (LLVMInt32Type (), 0, FALSE), lhs);
4133 /* Branch to either resume_bb, or to the bblocks in bb_list */
4134 switch_ins = LLVMBuildSwitch (builder, val, resume_bb, g_slist_length (bb_list));
4136 * The other targets are added at the end to handle OP_CALL_HANDLER
4137 * opcodes processed later.
4139 info->endfinally_switch_ins_list = g_slist_append_mempool (cfg->mempool, info->endfinally_switch_ins_list, switch_ins);
4141 builder = ctx->builder = create_builder (ctx);
4142 LLVMPositionBuilderAtEnd (ctx->builder, resume_bb);
4144 if (ctx->cfg->compile_aot) {
4145 callee = get_plt_entry (ctx, LLVMFunctionType (LLVMVoidType (), NULL, 0, FALSE), MONO_PATCH_INFO_INTERNAL_METHOD, "llvm_resume_unwind_trampoline");
4147 callee = LLVMGetNamedFunction (module, "llvm_resume_unwind_trampoline");
4149 LLVMBuildCall (builder, callee, NULL, 0, "");
4151 LLVMBuildUnreachable (builder);
4152 has_terminator = TRUE;
4158 sprintf (reason, "opcode %s", mono_inst_name (ins->opcode));
4159 LLVM_FAILURE (ctx, reason);
4164 /* Convert the value to the type required by phi nodes */
4165 if (spec [MONO_INST_DEST] != ' ' && !MONO_IS_STORE_MEMBASE (ins) && ctx->vreg_types [ins->dreg]) {
4166 if (!values [ins->dreg])
4168 values [ins->dreg] = addresses [ins->dreg];
4170 values [ins->dreg] = convert (ctx, values [ins->dreg], ctx->vreg_types [ins->dreg]);
4173 /* Add stores for volatile variables */
4174 if (spec [MONO_INST_DEST] != ' ' && spec [MONO_INST_DEST] != 'v' && !MONO_IS_STORE_MEMBASE (ins))
4175 emit_volatile_store (ctx, ins->dreg);
4178 if (!has_terminator && bb->next_bb && (bb == cfg->bb_entry || bb->in_count > 0))
4179 LLVMBuildBr (builder, get_bb (ctx, bb->next_bb));
4181 if (bb == cfg->bb_exit && sig->ret->type == MONO_TYPE_VOID)
4182 LLVMBuildRetVoid (builder);
4184 if (bb == cfg->bb_entry)
4185 ctx->last_alloca = LLVMGetLastInstruction (get_bb (ctx, cfg->bb_entry));
4194 * mono_llvm_check_method_supported:
4196 * Do some quick checks to decide whenever cfg->method can be compiled by LLVM, to avoid
4197 * compiling a method twice.
4200 mono_llvm_check_method_supported (MonoCompile *cfg)
4202 MonoMethodHeader *header = cfg->header;
4203 MonoExceptionClause *clause;
4206 if (cfg->method->save_lmf) {
4207 cfg->exception_message = g_strdup ("lmf");
4208 cfg->disable_llvm = TRUE;
4212 for (i = 0; i < header->num_clauses; ++i) {
4213 clause = &header->clauses [i];
4215 if (i > 0 && clause->try_offset <= header->clauses [i - 1].handler_offset + header->clauses [i - 1].handler_len) {
4217 * FIXME: Some tests still fail with nested clauses.
4219 cfg->exception_message = g_strdup ("nested clauses");
4220 cfg->disable_llvm = TRUE;
4226 if (cfg->method->dynamic) {
4227 cfg->exception_message = g_strdup ("dynamic.");
4228 cfg->disable_llvm = TRUE;
4233 * mono_llvm_emit_method:
4235 * Emit LLVM IL from the mono IL, and compile it to native code using LLVM.
4238 mono_llvm_emit_method (MonoCompile *cfg)
4241 MonoMethodSignature *sig;
4243 LLVMTypeRef method_type;
4244 LLVMValueRef method = NULL;
4246 LLVMValueRef *values;
4247 int i, max_block_num, bb_index;
4248 gboolean last = FALSE;
4249 GPtrArray *phi_values;
4250 LLVMCallInfo *linfo;
4252 LLVMModuleRef module;
4254 GPtrArray *bblock_list;
4255 MonoMethodHeader *header;
4256 MonoExceptionClause *clause;
4260 /* The code below might acquire the loader lock, so use it for global locking */
4261 mono_loader_lock ();
4263 /* Used to communicate with the callbacks */
4264 mono_native_tls_set_value (current_cfg_tls_id, cfg);
4266 ctx = g_new0 (EmitContext, 1);
4268 ctx->mempool = cfg->mempool;
4271 * This maps vregs to the LLVM instruction defining them
4273 values = g_new0 (LLVMValueRef, cfg->next_vreg);
4275 * This maps vregs for volatile variables to the LLVM instruction defining their
4278 ctx->addresses = g_new0 (LLVMValueRef, cfg->next_vreg);
4279 ctx->vreg_types = g_new0 (LLVMTypeRef, cfg->next_vreg);
4280 ctx->vreg_cli_types = g_new0 (MonoType*, cfg->next_vreg);
4281 phi_values = g_ptr_array_sized_new (256);
4283 * This signals whenever the vreg was defined by a phi node with no input vars
4284 * (i.e. all its input bblocks end with NOT_REACHABLE).
4286 ctx->is_dead = g_new0 (gboolean, cfg->next_vreg);
4287 /* Whenever the bblock is unreachable */
4288 ctx->unreachable = g_new0 (gboolean, cfg->max_block_num);
4290 bblock_list = g_ptr_array_sized_new (256);
4292 ctx->values = values;
4293 ctx->region_to_handler = g_hash_table_new (NULL, NULL);
4295 if (cfg->compile_aot) {
4296 ctx->lmodule = &aot_module;
4297 method_name = mono_aot_get_method_name (cfg);
4298 cfg->llvm_method_name = g_strdup (method_name);
4301 ctx->lmodule = &jit_module;
4302 method_name = mono_method_full_name (cfg->method, TRUE);
4305 module = ctx->module = ctx->lmodule->module;
4308 LLVM_FAILURE (ctx, "gsharedvt");
4312 static int count = 0;
4315 if (g_getenv ("LLVM_COUNT")) {
4316 if (count == atoi (g_getenv ("LLVM_COUNT"))) {
4317 printf ("LAST: %s\n", mono_method_full_name (cfg->method, TRUE));
4321 if (count > atoi (g_getenv ("LLVM_COUNT")))
4322 LLVM_FAILURE (ctx, "");
4327 sig = mono_method_signature (cfg->method);
4330 linfo = mono_arch_get_llvm_call_info (cfg, sig);
4332 CHECK_FAILURE (ctx);
4335 linfo->rgctx_arg = TRUE;
4336 method_type = sig_to_llvm_sig_full (ctx, sig, linfo, &sinfo);
4337 CHECK_FAILURE (ctx);
4340 * This maps parameter indexes in the original signature to the indexes in
4341 * the LLVM signature.
4343 ctx->pindexes = sinfo.pindexes;
4345 method = LLVMAddFunction (module, method_name, method_type);
4346 ctx->lmethod = method;
4348 LLVMSetFunctionCallConv (method, LLVMMono1CallConv);
4349 LLVMSetLinkage (method, LLVMPrivateLinkage);
4351 LLVMAddFunctionAttr (method, LLVMUWTable);
4353 if (cfg->compile_aot) {
4354 LLVMSetLinkage (method, LLVMInternalLinkage);
4355 LLVMSetVisibility (method, LLVMHiddenVisibility);
4357 LLVMSetLinkage (method, LLVMPrivateLinkage);
4360 if (cfg->method->save_lmf)
4361 LLVM_FAILURE (ctx, "lmf");
4363 if (sig->pinvoke && cfg->method->wrapper_type != MONO_WRAPPER_RUNTIME_INVOKE)
4364 LLVM_FAILURE (ctx, "pinvoke signature");
4366 header = cfg->header;
4367 for (i = 0; i < header->num_clauses; ++i) {
4368 clause = &header->clauses [i];
4369 if (clause->flags != MONO_EXCEPTION_CLAUSE_FINALLY && clause->flags != MONO_EXCEPTION_CLAUSE_NONE)
4370 LLVM_FAILURE (ctx, "non-finally/catch clause.");
4373 if (linfo->rgctx_arg) {
4374 ctx->rgctx_arg = LLVMGetParam (method, sinfo.rgctx_arg_pindex);
4376 * We mark the rgctx parameter with the inreg attribute, which is mapped to
4377 * MONO_ARCH_RGCTX_REG in the Mono calling convention in llvm, i.e.
4378 * CC_X86_64_Mono in X86CallingConv.td.
4380 LLVMAddAttribute (ctx->rgctx_arg, LLVMInRegAttribute);
4381 LLVMSetValueName (ctx->rgctx_arg, "rgctx");
4383 if (cfg->vret_addr) {
4384 values [cfg->vret_addr->dreg] = LLVMGetParam (method, sinfo.vret_arg_pindex);
4385 LLVMSetValueName (values [cfg->vret_addr->dreg], "vret");
4388 values [cfg->args [0]->dreg] = LLVMGetParam (method, sinfo.this_arg_pindex);
4389 LLVMSetValueName (values [cfg->args [0]->dreg], "this");
4392 names = g_new (char *, sig->param_count);
4393 mono_method_get_param_names (cfg->method, (const char **) names);
4395 for (i = 0; i < sig->param_count; ++i) {
4398 values [cfg->args [i + sig->hasthis]->dreg] = LLVMGetParam (method, sinfo.pindexes [i]);
4399 if (names [i] && names [i][0] != '\0')
4400 name = g_strdup_printf ("arg_%s", names [i]);
4402 name = g_strdup_printf ("arg_%d", i);
4403 LLVMSetValueName (values [cfg->args [i + sig->hasthis]->dreg], name);
4405 if (linfo->args [i + sig->hasthis].storage == LLVMArgVtypeByVal)
4406 LLVMAddAttribute (LLVMGetParam (method, sinfo.pindexes [i]), LLVMByValAttribute);
4411 for (bb = cfg->bb_entry; bb; bb = bb->next_bb)
4412 max_block_num = MAX (max_block_num, bb->block_num);
4413 ctx->bblocks = bblocks = g_new0 (BBInfo, max_block_num + 1);
4415 /* Add branches between non-consecutive bblocks */
4416 for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
4417 if (bb->last_ins && MONO_IS_COND_BRANCH_OP (bb->last_ins) &&
4418 bb->next_bb != bb->last_ins->inst_false_bb) {
4420 MonoInst *inst = mono_mempool_alloc0 (cfg->mempool, sizeof (MonoInst));
4421 inst->opcode = OP_BR;
4422 inst->inst_target_bb = bb->last_ins->inst_false_bb;
4423 mono_bblock_add_inst (bb, inst);
4428 * The INDIRECT flag added by OP_LDADDR inhibits optimizations, even if the LDADDR
4429 * was later optimized away, so clear these flags, and add them back for the still
4430 * present OP_LDADDR instructions.
4432 for (i = 0; i < cfg->next_vreg; ++i) {
4435 ins = get_vreg_to_inst (cfg, i);
4436 if (ins && ins != cfg->rgctx_var)
4437 ins->flags &= ~MONO_INST_INDIRECT;
4441 * Make a first pass over the code to precreate PHI nodes/set INDIRECT flags.
4443 for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
4445 LLVMBuilderRef builder;
4447 char dname_buf[128];
4449 builder = create_builder (ctx);
4451 for (ins = bb->code; ins; ins = ins->next) {
4452 switch (ins->opcode) {
4457 LLVMTypeRef phi_type = llvm_type_to_stack_type (type_to_llvm_type (ctx, &ins->klass->byval_arg));
4459 CHECK_FAILURE (ctx);
4461 if (ins->opcode == OP_VPHI) {
4462 /* Treat valuetype PHI nodes as operating on the address itself */
4463 g_assert (ins->klass);
4464 phi_type = LLVMPointerType (type_to_llvm_type (ctx, &ins->klass->byval_arg), 0);
4468 * Have to precreate these, as they can be referenced by
4469 * earlier instructions.
4471 sprintf (dname_buf, "t%d", ins->dreg);
4473 values [ins->dreg] = LLVMBuildPhi (builder, phi_type, dname);
4475 if (ins->opcode == OP_VPHI)
4476 ctx->addresses [ins->dreg] = values [ins->dreg];
4478 g_ptr_array_add (phi_values, values [ins->dreg]);
4481 * Set the expected type of the incoming arguments since these have
4482 * to have the same type.
4484 for (i = 0; i < ins->inst_phi_args [0]; i++) {
4485 int sreg1 = ins->inst_phi_args [i + 1];
4488 ctx->vreg_types [sreg1] = phi_type;
4493 ((MonoInst*)ins->inst_p0)->flags |= MONO_INST_INDIRECT;
4502 * Create an ordering for bblocks, use the depth first order first, then
4503 * put the exception handling bblocks last.
4505 for (bb_index = 0; bb_index < cfg->num_bblocks; ++bb_index) {
4506 bb = cfg->bblocks [bb_index];
4507 if (!(bb->region != -1 && !MONO_BBLOCK_IS_IN_REGION (bb, MONO_REGION_TRY))) {
4508 g_ptr_array_add (bblock_list, bb);
4509 bblocks [bb->block_num].added = TRUE;
4513 for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
4514 if (!bblocks [bb->block_num].added)
4515 g_ptr_array_add (bblock_list, bb);
4519 * Second pass: generate code.
4521 for (bb_index = 0; bb_index < bblock_list->len; ++bb_index) {
4522 bb = g_ptr_array_index (bblock_list, bb_index);
4524 if (!(bb == cfg->bb_entry || bb->in_count > 0))
4527 process_bb (ctx, bb);
4528 CHECK_FAILURE (ctx);
4531 /* Add incoming phi values */
4532 for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
4533 GSList *l, *ins_list;
4535 ins_list = bblocks [bb->block_num].phi_nodes;
4537 for (l = ins_list; l; l = l->next) {
4538 PhiNode *node = l->data;
4539 MonoInst *phi = node->phi;
4540 int sreg1 = node->sreg;
4541 LLVMBasicBlockRef in_bb;
4546 in_bb = get_end_bb (ctx, node->in_bb);
4548 if (ctx->unreachable [node->in_bb->block_num])
4551 if (!values [sreg1])
4552 /* Can happen with values in EH clauses */
4553 LLVM_FAILURE (ctx, "incoming phi sreg1");
4555 if (phi->opcode == OP_VPHI) {
4556 g_assert (LLVMTypeOf (ctx->addresses [sreg1]) == LLVMTypeOf (values [phi->dreg]));
4557 LLVMAddIncoming (values [phi->dreg], &ctx->addresses [sreg1], &in_bb, 1);
4559 g_assert (LLVMTypeOf (values [sreg1]) == LLVMTypeOf (values [phi->dreg]));
4560 LLVMAddIncoming (values [phi->dreg], &values [sreg1], &in_bb, 1);
4565 /* Create the SWITCH statements for ENDFINALLY instructions */
4566 for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
4567 BBInfo *info = &bblocks [bb->block_num];
4569 for (l = info->endfinally_switch_ins_list; l; l = l->next) {
4570 LLVMValueRef switch_ins = l->data;
4571 GSList *bb_list = info->call_handler_return_bbs;
4573 for (i = 0; i < g_slist_length (bb_list); ++i)
4574 LLVMAddCase (switch_ins, LLVMConstInt (LLVMInt32Type (), i + 1, FALSE), g_slist_nth (bb_list, i)->data);
4578 if (cfg->verbose_level > 1)
4579 mono_llvm_dump_value (method);
4581 if (cfg->compile_aot)
4582 mark_as_used (ctx->lmodule, method);
4584 if (cfg->compile_aot) {
4585 LLVMValueRef md_args [16];
4586 LLVMValueRef md_node;
4589 method_index = mono_aot_get_method_index (cfg->orig_method);
4590 md_args [0] = LLVMMDString (method_name, strlen (method_name));
4591 md_args [1] = LLVMConstInt (LLVMInt32Type (), method_index, FALSE);
4592 md_node = LLVMMDNode (md_args, 2);
4593 LLVMAddNamedMetadataOperand (module, "mono.function_indexes", md_node);
4594 //LLVMSetMetadata (method, md_kind, LLVMMDNode (&md_arg, 1));
4597 if (cfg->compile_aot) {
4598 /* Don't generate native code, keep the LLVM IR */
4599 if (cfg->compile_aot && cfg->verbose_level)
4600 printf ("%s emitted as %s\n", mono_method_full_name (cfg->method, TRUE), method_name);
4602 //LLVMVerifyFunction(method, 0);
4604 mono_llvm_optimize_method (method);
4606 if (cfg->verbose_level > 1)
4607 mono_llvm_dump_value (method);
4609 cfg->native_code = LLVMGetPointerToGlobal (ee, method);
4611 /* Set by emit_cb */
4612 g_assert (cfg->code_len);
4614 /* FIXME: Free the LLVM IL for the function */
4622 /* Need to add unused phi nodes as they can be referenced by other values */
4623 LLVMBasicBlockRef phi_bb = LLVMAppendBasicBlock (method, "PHI_BB");
4624 LLVMBuilderRef builder;
4626 builder = create_builder (ctx);
4627 LLVMPositionBuilderAtEnd (builder, phi_bb);
4629 for (i = 0; i < phi_values->len; ++i) {
4630 LLVMValueRef v = g_ptr_array_index (phi_values, i);
4631 if (LLVMGetInstructionParent (v) == NULL)
4632 LLVMInsertIntoBuilder (builder, v);
4635 LLVMDeleteFunction (method);
4640 g_free (ctx->addresses);
4641 g_free (ctx->vreg_types);
4642 g_free (ctx->vreg_cli_types);
4643 g_free (ctx->pindexes);
4644 g_free (ctx->is_dead);
4645 g_free (ctx->unreachable);
4646 g_ptr_array_free (phi_values, TRUE);
4647 g_free (ctx->bblocks);
4648 g_hash_table_destroy (ctx->region_to_handler);
4649 g_free (method_name);
4650 g_ptr_array_free (bblock_list, TRUE);
4652 for (l = ctx->builders; l; l = l->next) {
4653 LLVMBuilderRef builder = l->data;
4654 LLVMDisposeBuilder (builder);
4659 mono_native_tls_set_value (current_cfg_tls_id, NULL);
4661 mono_loader_unlock ();
4665 * mono_llvm_emit_call:
4667 * Same as mono_arch_emit_call () for LLVM.
4670 mono_llvm_emit_call (MonoCompile *cfg, MonoCallInst *call)
4673 MonoMethodSignature *sig;
4674 int i, n, stack_size;
4679 sig = call->signature;
4680 n = sig->param_count + sig->hasthis;
4682 call->cinfo = mono_arch_get_llvm_call_info (cfg, sig);
4684 if (cfg->disable_llvm)
4687 if (sig->call_convention == MONO_CALL_VARARG) {
4688 cfg->exception_message = g_strdup ("varargs");
4689 cfg->disable_llvm = TRUE;
4692 for (i = 0; i < n; ++i) {
4695 ainfo = call->cinfo->args + i;
4697 in = call->args [i];
4699 /* Simply remember the arguments */
4700 switch (ainfo->storage) {
4702 case LLVMArgInFPReg: {
4703 MonoType *t = (sig->hasthis && i == 0) ? &mono_get_intptr_class ()->byval_arg : sig->params [i - sig->hasthis];
4705 if (!t->byref && (t->type == MONO_TYPE_R8 || t->type == MONO_TYPE_R4)) {
4706 MONO_INST_NEW (cfg, ins, OP_FMOVE);
4707 ins->dreg = mono_alloc_freg (cfg);
4709 MONO_INST_NEW (cfg, ins, OP_MOVE);
4710 ins->dreg = mono_alloc_ireg (cfg);
4712 ins->sreg1 = in->dreg;
4715 case LLVMArgVtypeByVal:
4716 case LLVMArgVtypeInReg:
4717 MONO_INST_NEW (cfg, ins, OP_LLVM_OUTARG_VT);
4718 ins->dreg = mono_alloc_ireg (cfg);
4719 ins->sreg1 = in->dreg;
4720 ins->klass = mono_class_from_mono_type (sig->params [i - sig->hasthis]);
4723 call->cinfo = mono_arch_get_llvm_call_info (cfg, sig);
4724 cfg->exception_message = g_strdup ("ainfo->storage");
4725 cfg->disable_llvm = TRUE;
4729 if (!cfg->disable_llvm) {
4730 MONO_ADD_INS (cfg->cbb, ins);
4731 mono_call_inst_add_outarg_reg (cfg, call, ins->dreg, 0, FALSE);
4736 static unsigned char*
4737 alloc_cb (LLVMValueRef function, int size)
4741 cfg = mono_native_tls_get_value (current_cfg_tls_id);
4745 return mono_domain_code_reserve (cfg->domain, size);
4747 return mono_domain_code_reserve (mono_domain_get (), size);
4752 emitted_cb (LLVMValueRef function, void *start, void *end)
4756 cfg = mono_native_tls_get_value (current_cfg_tls_id);
4758 cfg->code_len = (guint8*)end - (guint8*)start;
4762 exception_cb (void *data)
4765 MonoJitExceptionInfo *ei;
4766 guint32 ei_len, i, j, nested_len, nindex;
4767 gpointer *type_info;
4768 int this_reg, this_offset;
4770 cfg = mono_native_tls_get_value (current_cfg_tls_id);
4774 * data points to a DWARF FDE structure, convert it to our unwind format and
4776 * An alternative would be to save it directly, and modify our unwinder to work
4779 cfg->encoded_unwind_ops = mono_unwind_decode_fde ((guint8*)data, &cfg->encoded_unwind_ops_len, NULL, &ei, &ei_len, &type_info, &this_reg, &this_offset);
4780 if (cfg->verbose_level > 1)
4781 mono_print_unwind_info (cfg->encoded_unwind_ops, cfg->encoded_unwind_ops_len);
4783 /* Count nested clauses */
4785 for (i = 0; i < ei_len; ++i) {
4786 for (j = 0; j < ei_len; ++j) {
4787 gint32 cindex1 = *(gint32*)type_info [i];
4788 MonoExceptionClause *clause1 = &cfg->header->clauses [cindex1];
4789 gint32 cindex2 = *(gint32*)type_info [j];
4790 MonoExceptionClause *clause2 = &cfg->header->clauses [cindex2];
4792 if (cindex1 != cindex2 && clause1->try_offset >= clause2->try_offset && clause1->handler_offset <= clause2->handler_offset) {
4798 cfg->llvm_ex_info = mono_mempool_alloc0 (cfg->mempool, (ei_len + nested_len) * sizeof (MonoJitExceptionInfo));
4799 cfg->llvm_ex_info_len = ei_len + nested_len;
4800 memcpy (cfg->llvm_ex_info, ei, ei_len * sizeof (MonoJitExceptionInfo));
4801 /* Fill the rest of the information from the type info */
4802 for (i = 0; i < ei_len; ++i) {
4803 gint32 clause_index = *(gint32*)type_info [i];
4804 MonoExceptionClause *clause = &cfg->header->clauses [clause_index];
4806 cfg->llvm_ex_info [i].flags = clause->flags;
4807 cfg->llvm_ex_info [i].data.catch_class = clause->data.catch_class;
4811 * For nested clauses, the LLVM produced exception info associates the try interval with
4812 * the innermost handler, while mono expects it to be associated with all nesting clauses.
4814 /* FIXME: These should be order with the normal clauses */
4816 for (i = 0; i < ei_len; ++i) {
4817 for (j = 0; j < ei_len; ++j) {
4818 gint32 cindex1 = *(gint32*)type_info [i];
4819 MonoExceptionClause *clause1 = &cfg->header->clauses [cindex1];
4820 gint32 cindex2 = *(gint32*)type_info [j];
4821 MonoExceptionClause *clause2 = &cfg->header->clauses [cindex2];
4823 if (cindex1 != cindex2 && clause1->try_offset >= clause2->try_offset && clause1->handler_offset <= clause2->handler_offset) {
4825 * The try interval comes from the nested clause, everything else from the
4828 memcpy (&cfg->llvm_ex_info [nindex], &cfg->llvm_ex_info [j], sizeof (MonoJitExceptionInfo));
4829 cfg->llvm_ex_info [nindex].try_start = cfg->llvm_ex_info [i].try_start;
4830 cfg->llvm_ex_info [nindex].try_end = cfg->llvm_ex_info [i].try_end;
4835 g_assert (nindex == ei_len + nested_len);
4836 cfg->llvm_this_reg = this_reg;
4837 cfg->llvm_this_offset = this_offset;
4839 /* type_info [i] is cfg mempool allocated, no need to free it */
4846 dlsym_cb (const char *name, void **symbol)
4852 if (!strcmp (name, "__bzero")) {
4853 *symbol = (void*)bzero;
4855 current = mono_dl_open (NULL, 0, NULL);
4858 err = mono_dl_symbol (current, name, symbol);
4860 #ifdef MONO_ARCH_HAVE_CREATE_LLVM_NATIVE_THUNK
4861 *symbol = (char*)mono_arch_create_llvm_native_thunk (mono_domain_get (), (guint8*)(*symbol));
4867 AddFunc (LLVMModuleRef module, const char *name, LLVMTypeRef ret_type, LLVMTypeRef *param_types, int nparams)
4869 LLVMAddFunction (module, name, LLVMFunctionType (ret_type, param_types, nparams, FALSE));
4873 AddFunc2 (LLVMModuleRef module, const char *name, LLVMTypeRef ret_type, LLVMTypeRef param_type1, LLVMTypeRef param_type2)
4875 LLVMTypeRef param_types [4];
4877 param_types [0] = param_type1;
4878 param_types [1] = param_type2;
4880 AddFunc (module, name, ret_type, param_types, 2);
4884 add_intrinsics (LLVMModuleRef module)
4886 /* Emit declarations of instrinsics */
4888 * It would be nicer to emit only the intrinsics actually used, but LLVM's Module
4889 * type doesn't seem to do any locking.
4892 LLVMTypeRef memset_params [] = { LLVMPointerType (LLVMInt8Type (), 0), LLVMInt8Type (), LLVMInt32Type (), LLVMInt32Type (), LLVMInt1Type () };
4894 memset_param_count = 5;
4895 memset_func_name = "llvm.memset.p0i8.i32";
4897 LLVMAddFunction (module, memset_func_name, LLVMFunctionType (LLVMVoidType (), memset_params, memset_param_count, FALSE));
4901 LLVMTypeRef memcpy_params [] = { LLVMPointerType (LLVMInt8Type (), 0), LLVMPointerType (LLVMInt8Type (), 0), LLVMInt32Type (), LLVMInt32Type (), LLVMInt1Type () };
4903 memcpy_param_count = 5;
4904 memcpy_func_name = "llvm.memcpy.p0i8.p0i8.i32";
4906 LLVMAddFunction (module, memcpy_func_name, LLVMFunctionType (LLVMVoidType (), memcpy_params, memcpy_param_count, FALSE));
4910 LLVMTypeRef params [] = { LLVMDoubleType () };
4912 LLVMAddFunction (module, "llvm.sin.f64", LLVMFunctionType (LLVMDoubleType (), params, 1, FALSE));
4913 LLVMAddFunction (module, "llvm.cos.f64", LLVMFunctionType (LLVMDoubleType (), params, 1, FALSE));
4914 LLVMAddFunction (module, "llvm.sqrt.f64", LLVMFunctionType (LLVMDoubleType (), params, 1, FALSE));
4916 /* This isn't an intrinsic, instead llvm seems to special case it by name */
4917 LLVMAddFunction (module, "fabs", LLVMFunctionType (LLVMDoubleType (), params, 1, FALSE));
4921 LLVMTypeRef ovf_res_i32 [] = { LLVMInt32Type (), LLVMInt1Type () };
4922 LLVMTypeRef ovf_params_i32 [] = { LLVMInt32Type (), LLVMInt32Type () };
4924 LLVMAddFunction (module, "llvm.sadd.with.overflow.i32", LLVMFunctionType (LLVMStructType (ovf_res_i32, 2, FALSE), ovf_params_i32, 2, FALSE));
4925 LLVMAddFunction (module, "llvm.uadd.with.overflow.i32", LLVMFunctionType (LLVMStructType (ovf_res_i32, 2, FALSE), ovf_params_i32, 2, FALSE));
4926 LLVMAddFunction (module, "llvm.ssub.with.overflow.i32", LLVMFunctionType (LLVMStructType (ovf_res_i32, 2, FALSE), ovf_params_i32, 2, FALSE));
4927 LLVMAddFunction (module, "llvm.usub.with.overflow.i32", LLVMFunctionType (LLVMStructType (ovf_res_i32, 2, FALSE), ovf_params_i32, 2, FALSE));
4928 LLVMAddFunction (module, "llvm.smul.with.overflow.i32", LLVMFunctionType (LLVMStructType (ovf_res_i32, 2, FALSE), ovf_params_i32, 2, FALSE));
4929 LLVMAddFunction (module, "llvm.umul.with.overflow.i32", LLVMFunctionType (LLVMStructType (ovf_res_i32, 2, FALSE), ovf_params_i32, 2, FALSE));
4933 LLVMTypeRef ovf_res_i64 [] = { LLVMInt64Type (), LLVMInt1Type () };
4934 LLVMTypeRef ovf_params_i64 [] = { LLVMInt64Type (), LLVMInt64Type () };
4936 LLVMAddFunction (module, "llvm.sadd.with.overflow.i64", LLVMFunctionType (LLVMStructType (ovf_res_i64, 2, FALSE), ovf_params_i64, 2, FALSE));
4937 LLVMAddFunction (module, "llvm.uadd.with.overflow.i64", LLVMFunctionType (LLVMStructType (ovf_res_i64, 2, FALSE), ovf_params_i64, 2, FALSE));
4938 LLVMAddFunction (module, "llvm.ssub.with.overflow.i64", LLVMFunctionType (LLVMStructType (ovf_res_i64, 2, FALSE), ovf_params_i64, 2, FALSE));
4939 LLVMAddFunction (module, "llvm.usub.with.overflow.i64", LLVMFunctionType (LLVMStructType (ovf_res_i64, 2, FALSE), ovf_params_i64, 2, FALSE));
4940 LLVMAddFunction (module, "llvm.smul.with.overflow.i64", LLVMFunctionType (LLVMStructType (ovf_res_i64, 2, FALSE), ovf_params_i64, 2, FALSE));
4941 LLVMAddFunction (module, "llvm.umul.with.overflow.i64", LLVMFunctionType (LLVMStructType (ovf_res_i64, 2, FALSE), ovf_params_i64, 2, FALSE));
4946 LLVMTypeRef arg_types [2];
4947 LLVMTypeRef ret_type;
4949 arg_types [0] = LLVMPointerType (LLVMInt8Type (), 0);
4950 arg_types [1] = LLVMPointerType (LLVMInt8Type (), 0);
4951 ret_type = LLVMInt32Type ();
4953 LLVMAddFunction (module, "mono_personality", LLVMFunctionType (LLVMVoidType (), NULL, 0, FALSE));
4955 LLVMAddFunction (module, "llvm_resume_unwind_trampoline", LLVMFunctionType (LLVMVoidType (), NULL, 0, FALSE));
4958 /* SSE intrinsics */
4959 #if defined(TARGET_X86) || defined(TARGET_AMD64)
4961 LLVMTypeRef ret_type, arg_types [16];
4964 ret_type = type_to_simd_type (MONO_TYPE_I4);
4965 arg_types [0] = ret_type;
4966 arg_types [1] = ret_type;
4967 AddFunc (module, "llvm.x86.sse41.pminud", ret_type, arg_types, 2);
4968 AddFunc (module, "llvm.x86.sse41.pmaxud", ret_type, arg_types, 2);
4970 ret_type = type_to_simd_type (MONO_TYPE_I2);
4971 arg_types [0] = ret_type;
4972 arg_types [1] = ret_type;
4973 AddFunc (module, "llvm.x86.sse41.pminuw", ret_type, arg_types, 2);
4974 AddFunc (module, "llvm.x86.sse2.pmins.w", ret_type, arg_types, 2);
4975 AddFunc (module, "llvm.x86.sse41.pmaxuw", ret_type, arg_types, 2);
4976 AddFunc (module, "llvm.x86.sse2.padds.w", ret_type, arg_types, 2);
4977 AddFunc (module, "llvm.x86.sse2.psubs.w", ret_type, arg_types, 2);
4978 AddFunc (module, "llvm.x86.sse2.paddus.w", ret_type, arg_types, 2);
4979 AddFunc (module, "llvm.x86.sse2.psubus.w", ret_type, arg_types, 2);
4980 AddFunc (module, "llvm.x86.sse2.pavg.w", ret_type, arg_types, 2);
4981 AddFunc (module, "llvm.x86.sse2.pmulh.w", ret_type, arg_types, 2);
4982 AddFunc (module, "llvm.x86.sse2.pmulhu.w", ret_type, arg_types, 2);
4984 ret_type = type_to_simd_type (MONO_TYPE_I1);
4985 arg_types [0] = ret_type;
4986 arg_types [1] = ret_type;
4987 AddFunc (module, "llvm.x86.sse2.pminu.b", ret_type, arg_types, 2);
4988 AddFunc (module, "llvm.x86.sse2.pmaxu.b", ret_type, arg_types, 2);
4989 AddFunc (module, "llvm.x86.sse2.padds.b", ret_type, arg_types, 2);
4990 AddFunc (module, "llvm.x86.sse2.psubs.b", ret_type, arg_types, 2);
4991 AddFunc (module, "llvm.x86.sse2.paddus.b", ret_type, arg_types, 2);
4992 AddFunc (module, "llvm.x86.sse2.psubus.b", ret_type, arg_types, 2);
4993 AddFunc (module, "llvm.x86.sse2.pavg.b", ret_type, arg_types, 2);
4995 ret_type = type_to_simd_type (MONO_TYPE_R8);
4996 arg_types [0] = ret_type;
4997 arg_types [1] = ret_type;
4998 AddFunc (module, "llvm.x86.sse2.min.pd", ret_type, arg_types, 2);
4999 AddFunc (module, "llvm.x86.sse2.max.pd", ret_type, arg_types, 2);
5000 AddFunc (module, "llvm.x86.sse3.hadd.pd", ret_type, arg_types, 2);
5001 AddFunc (module, "llvm.x86.sse3.hsub.pd", ret_type, arg_types, 2);
5002 AddFunc (module, "llvm.x86.sse3.addsub.pd", ret_type, arg_types, 2);
5004 ret_type = type_to_simd_type (MONO_TYPE_R4);
5005 arg_types [0] = ret_type;
5006 arg_types [1] = ret_type;
5007 AddFunc (module, "llvm.x86.sse.min.ps", ret_type, arg_types, 2);
5008 AddFunc (module, "llvm.x86.sse.max.ps", ret_type, arg_types, 2);
5009 AddFunc (module, "llvm.x86.sse3.hadd.ps", ret_type, arg_types, 2);
5010 AddFunc (module, "llvm.x86.sse3.hsub.ps", ret_type, arg_types, 2);
5011 AddFunc (module, "llvm.x86.sse3.addsub.ps", ret_type, arg_types, 2);
5014 ret_type = type_to_simd_type (MONO_TYPE_I1);
5015 arg_types [0] = type_to_simd_type (MONO_TYPE_I2);
5016 arg_types [1] = type_to_simd_type (MONO_TYPE_I2);
5017 AddFunc (module, "llvm.x86.sse2.packsswb.128", ret_type, arg_types, 2);
5018 AddFunc (module, "llvm.x86.sse2.packuswb.128", ret_type, arg_types, 2);
5019 ret_type = type_to_simd_type (MONO_TYPE_I2);
5020 arg_types [0] = type_to_simd_type (MONO_TYPE_I4);
5021 arg_types [1] = type_to_simd_type (MONO_TYPE_I4);
5022 AddFunc (module, "llvm.x86.sse2.packssdw.128", ret_type, arg_types, 2);
5023 AddFunc (module, "llvm.x86.sse41.packusdw", ret_type, arg_types, 2);
5026 ret_type = type_to_simd_type (MONO_TYPE_R8);
5027 arg_types [0] = ret_type;
5028 arg_types [1] = ret_type;
5029 arg_types [2] = LLVMInt8Type ();
5030 AddFunc (module, "llvm.x86.sse2.cmp.pd", ret_type, arg_types, 3);
5031 ret_type = type_to_simd_type (MONO_TYPE_R4);
5032 arg_types [0] = ret_type;
5033 arg_types [1] = ret_type;
5034 arg_types [2] = LLVMInt8Type ();
5035 AddFunc (module, "llvm.x86.sse.cmp.ps", ret_type, arg_types, 3);
5037 /* Conversion ops */
5038 ret_type = type_to_simd_type (MONO_TYPE_R8);
5039 arg_types [0] = type_to_simd_type (MONO_TYPE_I4);
5040 AddFunc (module, "llvm.x86.sse2.cvtdq2pd", ret_type, arg_types, 1);
5041 ret_type = type_to_simd_type (MONO_TYPE_R4);
5042 arg_types [0] = type_to_simd_type (MONO_TYPE_I4);
5043 AddFunc (module, "llvm.x86.sse2.cvtdq2ps", ret_type, arg_types, 1);
5044 ret_type = type_to_simd_type (MONO_TYPE_I4);
5045 arg_types [0] = type_to_simd_type (MONO_TYPE_R8);
5046 AddFunc (module, "llvm.x86.sse2.cvtpd2dq", ret_type, arg_types, 1);
5047 ret_type = type_to_simd_type (MONO_TYPE_I4);
5048 arg_types [0] = type_to_simd_type (MONO_TYPE_R4);
5049 AddFunc (module, "llvm.x86.sse2.cvtps2dq", ret_type, arg_types, 1);
5050 ret_type = type_to_simd_type (MONO_TYPE_R4);
5051 arg_types [0] = type_to_simd_type (MONO_TYPE_R8);
5052 AddFunc (module, "llvm.x86.sse2.cvtpd2ps", ret_type, arg_types, 1);
5053 ret_type = type_to_simd_type (MONO_TYPE_R8);
5054 arg_types [0] = type_to_simd_type (MONO_TYPE_R4);
5055 AddFunc (module, "llvm.x86.sse2.cvtps2pd", ret_type, arg_types, 1);
5057 ret_type = type_to_simd_type (MONO_TYPE_I4);
5058 arg_types [0] = type_to_simd_type (MONO_TYPE_R8);
5059 AddFunc (module, "llvm.x86.sse2.cvttpd2dq", ret_type, arg_types, 1);
5060 ret_type = type_to_simd_type (MONO_TYPE_I4);
5061 arg_types [0] = type_to_simd_type (MONO_TYPE_R4);
5062 AddFunc (module, "llvm.x86.sse2.cvttps2dq", ret_type, arg_types, 1);
5065 ret_type = type_to_simd_type (MONO_TYPE_R8);
5066 arg_types [0] = ret_type;
5067 AddFunc (module, "llvm.x86.sse2.sqrt.pd", ret_type, arg_types, 1);
5068 ret_type = type_to_simd_type (MONO_TYPE_R4);
5069 arg_types [0] = ret_type;
5070 AddFunc (module, "llvm.x86.sse.sqrt.ps", ret_type, arg_types, 1);
5071 ret_type = type_to_simd_type (MONO_TYPE_R4);
5072 arg_types [0] = ret_type;
5073 AddFunc (module, "llvm.x86.sse.rsqrt.ps", ret_type, arg_types, 1);
5074 ret_type = type_to_simd_type (MONO_TYPE_R4);
5075 arg_types [0] = ret_type;
5076 AddFunc (module, "llvm.x86.sse.rcp.ps", ret_type, arg_types, 1);
5079 ret_type = type_to_simd_type (MONO_TYPE_I2);
5080 arg_types [0] = ret_type;
5081 arg_types [1] = LLVMInt32Type ();
5082 AddFunc (module, "llvm.x86.sse2.psrli.w", ret_type, arg_types, 2);
5083 AddFunc (module, "llvm.x86.sse2.psrai.w", ret_type, arg_types, 2);
5084 AddFunc (module, "llvm.x86.sse2.pslli.w", ret_type, arg_types, 2);
5085 ret_type = type_to_simd_type (MONO_TYPE_I4);
5086 arg_types [0] = ret_type;
5087 arg_types [1] = LLVMInt32Type ();
5088 AddFunc (module, "llvm.x86.sse2.psrli.d", ret_type, arg_types, 2);
5089 AddFunc (module, "llvm.x86.sse2.psrai.d", ret_type, arg_types, 2);
5090 AddFunc (module, "llvm.x86.sse2.pslli.d", ret_type, arg_types, 2);
5091 ret_type = type_to_simd_type (MONO_TYPE_I8);
5092 arg_types [0] = ret_type;
5093 arg_types [1] = LLVMInt32Type ();
5094 AddFunc (module, "llvm.x86.sse2.psrli.q", ret_type, arg_types, 2);
5095 AddFunc (module, "llvm.x86.sse2.pslli.q", ret_type, arg_types, 2);
5098 ret_type = LLVMInt32Type ();
5099 arg_types [0] = type_to_simd_type (MONO_TYPE_I1);
5100 AddFunc (module, "llvm.x86.sse2.pmovmskb.128", ret_type, arg_types, 1);
5103 AddFunc (module, "llvm.x86.sse2.pause", LLVMVoidType (), NULL, 0);
5106 /* Load/Store intrinsics */
5108 LLVMTypeRef arg_types [5];
5112 for (i = 1; i <= 8; i *= 2) {
5113 arg_types [0] = LLVMPointerType (LLVMIntType (i * 8), 0);
5114 arg_types [1] = LLVMInt32Type ();
5115 arg_types [2] = LLVMInt1Type ();
5116 sprintf (name, "llvm.mono.load.i%d.p0i%d", i * 8, i * 8);
5117 LLVMAddFunction (module, name, LLVMFunctionType (LLVMIntType (i * 8), arg_types, 3, FALSE));
5119 arg_types [0] = LLVMIntType (i * 8);
5120 arg_types [1] = LLVMPointerType (LLVMIntType (i * 8), 0);
5121 arg_types [2] = LLVMInt32Type ();
5122 arg_types [3] = LLVMInt1Type ();
5123 sprintf (name, "llvm.mono.store.i%d.p0i%d", i * 8, i * 8);
5124 LLVMAddFunction (module, name, LLVMFunctionType (LLVMVoidType (), arg_types, 4, FALSE));
5130 add_types (MonoLLVMModule *lmodule)
5132 lmodule->ptr_type = LLVMPointerType (sizeof (gpointer) == 8 ? LLVMInt64Type () : LLVMInt32Type (), 0);
5136 mono_llvm_init (void)
5138 mono_native_tls_alloc (¤t_cfg_tls_id, NULL);
5142 init_jit_module (void)
5144 MonoJitICallInfo *info;
5146 if (jit_module_inited)
5149 mono_loader_lock ();
5151 if (jit_module_inited) {
5152 mono_loader_unlock ();
5156 jit_module.module = LLVMModuleCreateWithName ("mono");
5158 ee = mono_llvm_create_ee (LLVMCreateModuleProviderForExistingModule (jit_module.module), alloc_cb, emitted_cb, exception_cb, dlsym_cb);
5160 add_intrinsics (jit_module.module);
5161 add_types (&jit_module);
5163 jit_module.llvm_types = g_hash_table_new (NULL, NULL);
5165 info = mono_find_jit_icall_by_name ("llvm_resume_unwind_trampoline");
5167 LLVMAddGlobalMapping (ee, LLVMGetNamedFunction (jit_module.module, "llvm_resume_unwind_trampoline"), (void*)info->func);
5169 jit_module_inited = TRUE;
5171 mono_loader_unlock ();
5175 mono_llvm_cleanup (void)
5178 mono_llvm_dispose_ee (ee);
5180 if (jit_module.llvm_types)
5181 g_hash_table_destroy (jit_module.llvm_types);
5183 if (aot_module.module)
5184 LLVMDisposeModule (aot_module.module);
5186 LLVMContextDispose (LLVMGetGlobalContext ());
5190 mono_llvm_create_aot_module (const char *got_symbol)
5192 /* Delete previous module */
5193 if (aot_module.plt_entries)
5194 g_hash_table_destroy (aot_module.plt_entries);
5195 if (aot_module.module)
5196 LLVMDisposeModule (aot_module.module);
5198 memset (&aot_module, 0, sizeof (aot_module));
5200 aot_module.module = LLVMModuleCreateWithName ("aot");
5201 aot_module.got_symbol = got_symbol;
5203 add_intrinsics (aot_module.module);
5204 add_types (&aot_module);
5208 * We couldn't compute the type of the LLVM global representing the got because
5209 * its size is only known after all the methods have been emitted. So create
5210 * a dummy variable, and replace all uses it with the real got variable when
5211 * its size is known in mono_llvm_emit_aot_module ().
5214 LLVMTypeRef got_type = LLVMArrayType (aot_module.ptr_type, 0);
5216 aot_module.got_var = LLVMAddGlobal (aot_module.module, got_type, "mono_dummy_got");
5217 LLVMSetInitializer (aot_module.got_var, LLVMConstNull (got_type));
5220 /* Add a dummy personality function */
5222 LLVMBasicBlockRef lbb;
5223 LLVMBuilderRef lbuilder;
5224 LLVMValueRef personality;
5226 personality = LLVMAddFunction (aot_module.module, "mono_aot_personality", LLVMFunctionType (LLVMVoidType (), NULL, 0, FALSE));
5227 LLVMSetLinkage (personality, LLVMInternalLinkage);
5228 lbb = LLVMAppendBasicBlock (personality, "BB0");
5229 lbuilder = LLVMCreateBuilder ();
5230 LLVMPositionBuilderAtEnd (lbuilder, lbb);
5231 LLVMBuildRetVoid (lbuilder);
5234 aot_module.llvm_types = g_hash_table_new (NULL, NULL);
5235 aot_module.plt_entries = g_hash_table_new (g_str_hash, g_str_equal);
5239 * Emit the aot module into the LLVM bitcode file FILENAME.
5242 mono_llvm_emit_aot_module (const char *filename, int got_size)
5244 LLVMTypeRef got_type;
5245 LLVMValueRef real_got;
5248 * Create the real got variable and replace all uses of the dummy variable with
5251 got_type = LLVMArrayType (aot_module.ptr_type, got_size);
5252 real_got = LLVMAddGlobal (aot_module.module, got_type, aot_module.got_symbol);
5253 LLVMSetInitializer (real_got, LLVMConstNull (got_type));
5254 LLVMSetLinkage (real_got, LLVMInternalLinkage);
5256 mono_llvm_replace_uses_of (aot_module.got_var, real_got);
5258 mark_as_used (&aot_module, real_got);
5260 /* Delete the dummy got so it doesn't become a global */
5261 LLVMDeleteGlobal (aot_module.got_var);
5263 emit_llvm_used (&aot_module);
5269 if (LLVMVerifyModule (aot_module.module, LLVMReturnStatusAction, &verifier_err)) {
5270 g_assert_not_reached ();
5275 LLVMWriteBitcodeToFile (aot_module.module, filename);
5280 - Emit LLVM IR from the mono IR using the LLVM C API.
5281 - The original arch specific code remains, so we can fall back to it if we run
5282 into something we can't handle.
5286 A partial list of issues:
5287 - Handling of opcodes which can throw exceptions.
5289 In the mono JIT, these are implemented using code like this:
5296 push throw_pos - method
5297 call <exception trampoline>
5299 The problematic part is push throw_pos - method, which cannot be represented
5300 in the LLVM IR, since it does not support label values.
5301 -> this can be implemented in AOT mode using inline asm + labels, but cannot
5302 be implemented in JIT mode ?
5303 -> a possible but slower implementation would use the normal exception
5304 throwing code but it would need to control the placement of the throw code
5305 (it needs to be exactly after the compare+branch).
5306 -> perhaps add a PC offset intrinsics ?
5308 - efficient implementation of .ovf opcodes.
5310 These are currently implemented as:
5311 <ins which sets the condition codes>
5314 Some overflow opcodes are now supported by LLVM SVN.
5316 - exception handling, unwinding.
5317 - SSA is disabled for methods with exception handlers
5318 - How to obtain unwind info for LLVM compiled methods ?
5319 -> this is now solved by converting the unwind info generated by LLVM
5321 - LLVM uses the c++ exception handling framework, while we use our home grown
5322 code, and couldn't use the c++ one:
5323 - its not supported under VC++, other exotic platforms.
5324 - it might be impossible to support filter clauses with it.
5328 The trampolines need a predictable call sequence, since they need to disasm
5329 the calling code to obtain register numbers / offsets.
5331 LLVM currently generates this code in non-JIT mode:
5332 mov -0x98(%rax),%eax
5334 Here, the vtable pointer is lost.
5335 -> solution: use one vtable trampoline per class.
5337 - passing/receiving the IMT pointer/RGCTX.
5338 -> solution: pass them as normal arguments ?
5342 LLVM does not allow the specification of argument registers etc. This means
5343 that all calls are made according to the platform ABI.
5345 - passing/receiving vtypes.
5347 Vtypes passed/received in registers are handled by the front end by using
5348 a signature with scalar arguments, and loading the parts of the vtype into those
5351 Vtypes passed on the stack are handled using the 'byval' attribute.
5355 Supported though alloca, we need to emit the load/store code.
5359 The mono JIT uses pointer sized iregs/double fregs, while LLVM uses precisely
5360 typed registers, so we have to keep track of the precise LLVM type of each vreg.
5361 This is made easier because the IR is already in SSA form.
5362 An additional problem is that our IR is not consistent with types, i.e. i32/ia64
5363 types are frequently used incorrectly.
5368 Emit LLVM bytecode into a .bc file, compile it using llc into a .s file, then
5369 append the AOT data structures to that file. For methods which cannot be
5370 handled by LLVM, the normal JIT compiled versions are used.
5373 /* FIXME: Normalize some aspects of the mono IR to allow easier translation, like:
5374 * - each bblock should end with a branch
5375 * - setting the return value, making cfg->ret non-volatile
5376 * - avoid some transformations in the JIT which make it harder for us to generate
5378 * - use pointer types to help optimizations.