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/debug-mono-symfile.h>
11 #include <mono/metadata/mempool-internals.h>
12 #include <mono/utils/mono-tls.h>
13 #include <mono/utils/mono-dl.h>
14 #include <mono/utils/mono-time.h>
15 #include <mono/utils/freebsd-dwarf.h>
17 #ifndef __STDC_LIMIT_MACROS
18 #define __STDC_LIMIT_MACROS
20 #ifndef __STDC_CONSTANT_MACROS
21 #define __STDC_CONSTANT_MACROS
24 #include "llvm-c/Core.h"
25 #include "llvm-c/ExecutionEngine.h"
26 #include "llvm-c/BitWriter.h"
27 #include "llvm-c/Analysis.h"
29 #include "mini-llvm-cpp.h"
34 extern void *memset(void *, int, size_t);
35 void bzero (void *to, size_t count) { memset (to, 0, count); }
40 * Information associated by mono with LLVM modules.
44 LLVMValueRef throw, rethrow, throw_corlib_exception;
45 GHashTable *llvm_types;
47 const char *got_symbol;
48 GHashTable *plt_entries;
49 GHashTable *plt_entries_ji;
50 GHashTable *method_to_lmethod;
55 GPtrArray *subprogram_mds;
57 LLVMExecutionEngineRef ee;
58 gboolean external_symbols;
64 * Information associated by the backend with mono basic blocks.
67 LLVMBasicBlockRef bblock, end_bblock;
68 LLVMValueRef finally_ind;
69 gboolean added, invoke_target;
71 * If this bblock is the start of a finally clause, this is a list of bblocks it
72 * needs to branch to in ENDFINALLY.
74 GSList *call_handler_return_bbs;
76 * If this bblock is the start of a finally clause, this is the bblock that
77 * CALL_HANDLER needs to branch to.
79 LLVMBasicBlockRef call_handler_target_bb;
80 /* The list of switch statements generated by ENDFINALLY instructions */
81 GSList *endfinally_switch_ins_list;
86 * Structure containing emit state
91 /* Maps method names to the corresponding LLVMValueRef */
92 GHashTable *emitted_method_decls;
96 MonoLLVMModule *lmodule;
99 int sindex, default_index, ex_index;
100 LLVMBuilderRef builder;
101 LLVMValueRef *values, *addresses;
102 MonoType **vreg_cli_types;
104 MonoMethodSignature *sig;
106 GHashTable *region_to_handler;
107 LLVMBuilderRef alloca_builder;
108 LLVMValueRef last_alloca;
109 LLVMValueRef rgctx_arg;
110 LLVMTypeRef *vreg_types;
112 gboolean *unreachable;
114 LLVMValueRef imt_rgctx_loc;
115 GHashTable *llvm_types;
117 MonoDebugMethodInfo *minfo;
124 MonoBasicBlock *in_bb;
129 * Instruction metadata
130 * This is the same as ins_info, but LREG != IREG.
138 #define MINI_OP(a,b,dest,src1,src2) dest, src1, src2, ' ',
139 #define MINI_OP3(a,b,dest,src1,src2,src3) dest, src1, src2, src3,
146 /* keep in sync with the enum in mini.h */
149 #include "mini-ops.h"
154 #if SIZEOF_VOID_P == 4
155 #define GET_LONG_IMM(ins) (((guint64)(ins)->inst_ms_word << 32) | (guint64)(guint32)(ins)->inst_ls_word)
157 #define GET_LONG_IMM(ins) ((ins)->inst_imm)
160 #define LLVM_INS_INFO(opcode) (&llvm_ins_info [((opcode) - OP_START - 1) * 4])
163 #define TRACE_FAILURE(msg) do { printf ("%s\n", msg); } while (0)
165 #define TRACE_FAILURE(msg)
169 #define IS_TARGET_X86 1
171 #define IS_TARGET_X86 0
175 #define IS_TARGET_AMD64 1
177 #define IS_TARGET_AMD64 0
180 #define LLVM_FAILURE(ctx, reason) do { \
181 TRACE_FAILURE (reason); \
182 (ctx)->cfg->exception_message = g_strdup (reason); \
183 (ctx)->cfg->disable_llvm = TRUE; \
187 #define CHECK_FAILURE(ctx) do { \
188 if ((ctx)->cfg->disable_llvm) \
192 static LLVMIntPredicate cond_to_llvm_cond [] = {
205 static LLVMRealPredicate fpcond_to_llvm_cond [] = {
218 static MonoNativeTlsKey current_cfg_tls_id;
220 static MonoLLVMModule aot_module;
221 static int memset_param_count, memcpy_param_count;
222 static const char *memset_func_name;
223 static const char *memcpy_func_name;
225 static void init_jit_module (MonoDomain *domain);
227 static void emit_dbg_loc (EmitContext *ctx, LLVMBuilderRef builder, const unsigned char *cil_code);
228 static LLVMValueRef emit_dbg_subprogram (EmitContext *ctx, MonoCompile *cfg, LLVMValueRef method, const char *name);
229 static void emit_dbg_info (MonoLLVMModule *lmodule, const char *filename, const char *cu_name);
234 * The LLVM type with width == sizeof (gpointer)
239 return sizeof (gpointer) == 8 ? LLVMInt64Type () : LLVMInt32Type ();
245 return sizeof (gpointer) == 8 ? LLVMPointerType (LLVMInt64Type (), 0) : LLVMPointerType (LLVMInt32Type (), 0);
251 return sizeof (gpointer) == 8 ? LLVMPointerType (LLVMInt64Type (), 0) : LLVMPointerType (LLVMInt32Type (), 0);
257 * Return the size of the LLVM representation of the vtype T.
260 get_vtype_size (MonoType *t)
264 size = mono_class_value_size (mono_class_from_mono_type (t), NULL);
266 while (size < 2 * sizeof (gpointer) && mono_is_power_of_two (size) == -1)
273 * simd_class_to_llvm_type:
275 * Return the LLVM type corresponding to the Mono.SIMD class KLASS
278 simd_class_to_llvm_type (EmitContext *ctx, MonoClass *klass)
280 if (!strcmp (klass->name, "Vector2d")) {
281 return LLVMVectorType (LLVMDoubleType (), 2);
282 } else if (!strcmp (klass->name, "Vector2l")) {
283 return LLVMVectorType (LLVMInt64Type (), 2);
284 } else if (!strcmp (klass->name, "Vector2ul")) {
285 return LLVMVectorType (LLVMInt64Type (), 2);
286 } else if (!strcmp (klass->name, "Vector4i")) {
287 return LLVMVectorType (LLVMInt32Type (), 4);
288 } else if (!strcmp (klass->name, "Vector4ui")) {
289 return LLVMVectorType (LLVMInt32Type (), 4);
290 } else if (!strcmp (klass->name, "Vector4f")) {
291 return LLVMVectorType (LLVMFloatType (), 4);
292 } else if (!strcmp (klass->name, "Vector8s")) {
293 return LLVMVectorType (LLVMInt16Type (), 8);
294 } else if (!strcmp (klass->name, "Vector8us")) {
295 return LLVMVectorType (LLVMInt16Type (), 8);
296 } else if (!strcmp (klass->name, "Vector16sb")) {
297 return LLVMVectorType (LLVMInt8Type (), 16);
298 } else if (!strcmp (klass->name, "Vector16b")) {
299 return LLVMVectorType (LLVMInt8Type (), 16);
301 printf ("%s\n", klass->name);
307 /* Return the 128 bit SIMD type corresponding to the mono type TYPE */
308 static inline G_GNUC_UNUSED LLVMTypeRef
309 type_to_simd_type (int type)
313 return LLVMVectorType (LLVMInt8Type (), 16);
315 return LLVMVectorType (LLVMInt16Type (), 8);
317 return LLVMVectorType (LLVMInt32Type (), 4);
319 return LLVMVectorType (LLVMInt64Type (), 2);
321 return LLVMVectorType (LLVMDoubleType (), 2);
323 return LLVMVectorType (LLVMFloatType (), 4);
325 g_assert_not_reached ();
333 * Return the LLVM type corresponding to T.
336 type_to_llvm_type (EmitContext *ctx, MonoType *t)
338 t = mini_replace_type (t);
341 return LLVMPointerType (LLVMInt8Type (), 0);
344 return LLVMVoidType ();
346 return LLVMInt8Type ();
348 return LLVMInt16Type ();
350 return LLVMInt32Type ();
352 return LLVMInt8Type ();
354 return LLVMInt16Type ();
356 return LLVMInt32Type ();
357 case MONO_TYPE_BOOLEAN:
358 return LLVMInt8Type ();
361 return LLVMInt64Type ();
363 return LLVMInt16Type ();
365 return LLVMFloatType ();
367 return LLVMDoubleType ();
370 return IntPtrType ();
371 case MONO_TYPE_OBJECT:
372 case MONO_TYPE_CLASS:
373 case MONO_TYPE_ARRAY:
374 case MONO_TYPE_SZARRAY:
375 case MONO_TYPE_STRING:
377 return ObjRefType ();
380 /* Because of generic sharing */
381 return ObjRefType ();
382 case MONO_TYPE_GENERICINST:
383 if (!mono_type_generic_inst_is_valuetype (t))
384 return ObjRefType ();
386 case MONO_TYPE_VALUETYPE:
387 case MONO_TYPE_TYPEDBYREF: {
391 klass = mono_class_from_mono_type (t);
393 if (MONO_CLASS_IS_SIMD (ctx->cfg, klass))
394 return simd_class_to_llvm_type (ctx, klass);
397 return type_to_llvm_type (ctx, mono_class_enum_basetype (klass));
399 ltype = g_hash_table_lookup (ctx->lmodule->llvm_types, klass);
402 LLVMTypeRef *eltypes;
405 size = get_vtype_size (t);
407 eltypes = g_new (LLVMTypeRef, size);
408 for (i = 0; i < size; ++i)
409 eltypes [i] = LLVMInt8Type ();
411 name = mono_type_full_name (&klass->byval_arg);
412 ltype = LLVMStructCreateNamed (LLVMGetGlobalContext (), name);
413 LLVMStructSetBody (ltype, eltypes, size, FALSE);
414 g_hash_table_insert (ctx->lmodule->llvm_types, klass, ltype);
422 printf ("X: %d\n", t->type);
423 ctx->cfg->exception_message = g_strdup_printf ("type %s", mono_type_full_name (t));
424 ctx->cfg->disable_llvm = TRUE;
432 * Return whenever T is an unsigned int type.
435 type_is_unsigned (EmitContext *ctx, MonoType *t)
452 * type_to_llvm_arg_type:
454 * Same as type_to_llvm_type, but treat i8/i16 as i32.
457 type_to_llvm_arg_type (EmitContext *ctx, MonoType *t)
459 LLVMTypeRef ptype = type_to_llvm_type (ctx, t);
462 * This works on all abis except arm64/ios which passes multiple
463 * arguments in one stack slot.
466 if (ptype == LLVMInt8Type () || ptype == LLVMInt16Type ()) {
468 * LLVM generates code which only sets the lower bits, while JITted
469 * code expects all the bits to be set.
471 ptype = LLVMInt32Type ();
479 * llvm_type_to_stack_type:
481 * Return the LLVM type which needs to be used when a value of type TYPE is pushed
484 static G_GNUC_UNUSED LLVMTypeRef
485 llvm_type_to_stack_type (LLVMTypeRef type)
489 if (type == LLVMInt8Type ())
490 return LLVMInt32Type ();
491 else if (type == LLVMInt16Type ())
492 return LLVMInt32Type ();
493 else if (type == LLVMFloatType ())
494 return LLVMDoubleType ();
500 * regtype_to_llvm_type:
502 * Return the LLVM type corresponding to the regtype C used in instruction
506 regtype_to_llvm_type (char c)
510 return LLVMInt32Type ();
512 return LLVMInt64Type ();
514 return LLVMDoubleType ();
523 * Return the LLVM type corresponding to the unary/binary opcode OPCODE.
526 op_to_llvm_type (int opcode)
531 return LLVMInt8Type ();
534 return LLVMInt8Type ();
537 return LLVMInt16Type ();
540 return LLVMInt16Type ();
543 return LLVMInt32Type ();
546 return LLVMInt32Type ();
548 return LLVMInt64Type ();
550 return LLVMFloatType ();
552 return LLVMDoubleType ();
554 return LLVMInt64Type ();
556 return LLVMInt32Type ();
558 return LLVMInt64Type ();
561 return LLVMInt8Type ();
564 return LLVMInt16Type ();
567 return sizeof (gpointer) == 8 ? LLVMInt64Type () : LLVMInt32Type ();
574 return LLVMInt32Type ();
581 return LLVMInt64Type ();
583 printf ("%s\n", mono_inst_name (opcode));
584 g_assert_not_reached ();
590 * load_store_to_llvm_type:
592 * Return the size/sign/zero extension corresponding to the load/store opcode
596 load_store_to_llvm_type (int opcode, int *size, gboolean *sext, gboolean *zext)
602 case OP_LOADI1_MEMBASE:
603 case OP_STOREI1_MEMBASE_REG:
604 case OP_STOREI1_MEMBASE_IMM:
605 case OP_ATOMIC_LOAD_I1:
606 case OP_ATOMIC_STORE_I1:
609 return LLVMInt8Type ();
610 case OP_LOADU1_MEMBASE:
612 case OP_ATOMIC_LOAD_U1:
613 case OP_ATOMIC_STORE_U1:
616 return LLVMInt8Type ();
617 case OP_LOADI2_MEMBASE:
618 case OP_STOREI2_MEMBASE_REG:
619 case OP_STOREI2_MEMBASE_IMM:
620 case OP_ATOMIC_LOAD_I2:
621 case OP_ATOMIC_STORE_I2:
624 return LLVMInt16Type ();
625 case OP_LOADU2_MEMBASE:
627 case OP_ATOMIC_LOAD_U2:
628 case OP_ATOMIC_STORE_U2:
631 return LLVMInt16Type ();
632 case OP_LOADI4_MEMBASE:
633 case OP_LOADU4_MEMBASE:
636 case OP_STOREI4_MEMBASE_REG:
637 case OP_STOREI4_MEMBASE_IMM:
638 case OP_ATOMIC_LOAD_I4:
639 case OP_ATOMIC_STORE_I4:
640 case OP_ATOMIC_LOAD_U4:
641 case OP_ATOMIC_STORE_U4:
643 return LLVMInt32Type ();
644 case OP_LOADI8_MEMBASE:
646 case OP_STOREI8_MEMBASE_REG:
647 case OP_STOREI8_MEMBASE_IMM:
648 case OP_ATOMIC_LOAD_I8:
649 case OP_ATOMIC_STORE_I8:
650 case OP_ATOMIC_LOAD_U8:
651 case OP_ATOMIC_STORE_U8:
653 return LLVMInt64Type ();
654 case OP_LOADR4_MEMBASE:
655 case OP_STORER4_MEMBASE_REG:
656 case OP_ATOMIC_LOAD_R4:
657 case OP_ATOMIC_STORE_R4:
659 return LLVMFloatType ();
660 case OP_LOADR8_MEMBASE:
661 case OP_STORER8_MEMBASE_REG:
662 case OP_ATOMIC_LOAD_R8:
663 case OP_ATOMIC_STORE_R8:
665 return LLVMDoubleType ();
666 case OP_LOAD_MEMBASE:
668 case OP_STORE_MEMBASE_REG:
669 case OP_STORE_MEMBASE_IMM:
670 *size = sizeof (gpointer);
671 return IntPtrType ();
673 g_assert_not_reached ();
681 * Return the LLVM intrinsics corresponding to the overflow opcode OPCODE.
684 ovf_op_to_intrins (int opcode)
688 return "llvm.sadd.with.overflow.i32";
690 return "llvm.uadd.with.overflow.i32";
692 return "llvm.ssub.with.overflow.i32";
694 return "llvm.usub.with.overflow.i32";
696 return "llvm.smul.with.overflow.i32";
698 return "llvm.umul.with.overflow.i32";
700 return "llvm.sadd.with.overflow.i64";
702 return "llvm.uadd.with.overflow.i64";
704 return "llvm.ssub.with.overflow.i64";
706 return "llvm.usub.with.overflow.i64";
708 return "llvm.smul.with.overflow.i64";
710 return "llvm.umul.with.overflow.i64";
712 g_assert_not_reached ();
718 simd_op_to_intrins (int opcode)
721 #if defined(TARGET_X86) || defined(TARGET_AMD64)
723 return "llvm.x86.sse2.min.pd";
725 return "llvm.x86.sse.min.ps";
727 return "llvm.x86.sse41.pminud";
729 return "llvm.x86.sse41.pminuw";
731 return "llvm.x86.sse2.pminu.b";
733 return "llvm.x86.sse2.pmins.w";
735 return "llvm.x86.sse2.max.pd";
737 return "llvm.x86.sse.max.ps";
739 return "llvm.x86.sse3.hadd.pd";
741 return "llvm.x86.sse3.hadd.ps";
743 return "llvm.x86.sse3.hsub.pd";
745 return "llvm.x86.sse3.hsub.ps";
747 return "llvm.x86.sse41.pmaxud";
749 return "llvm.x86.sse41.pmaxuw";
751 return "llvm.x86.sse2.pmaxu.b";
753 return "llvm.x86.sse3.addsub.ps";
755 return "llvm.x86.sse3.addsub.pd";
756 case OP_EXTRACT_MASK:
757 return "llvm.x86.sse2.pmovmskb.128";
760 return "llvm.x86.sse2.psrli.w";
763 return "llvm.x86.sse2.psrli.d";
766 return "llvm.x86.sse2.psrli.q";
769 return "llvm.x86.sse2.pslli.w";
772 return "llvm.x86.sse2.pslli.d";
775 return "llvm.x86.sse2.pslli.q";
778 return "llvm.x86.sse2.psrai.w";
781 return "llvm.x86.sse2.psrai.d";
783 return "llvm.x86.sse2.padds.b";
785 return "llvm.x86.sse2.padds.w";
787 return "llvm.x86.sse2.psubs.b";
789 return "llvm.x86.sse2.psubs.w";
790 case OP_PADDB_SAT_UN:
791 return "llvm.x86.sse2.paddus.b";
792 case OP_PADDW_SAT_UN:
793 return "llvm.x86.sse2.paddus.w";
794 case OP_PSUBB_SAT_UN:
795 return "llvm.x86.sse2.psubus.b";
796 case OP_PSUBW_SAT_UN:
797 return "llvm.x86.sse2.psubus.w";
799 return "llvm.x86.sse2.pavg.b";
801 return "llvm.x86.sse2.pavg.w";
803 return "llvm.x86.sse.sqrt.ps";
805 return "llvm.x86.sse2.sqrt.pd";
807 return "llvm.x86.sse.rsqrt.ps";
809 return "llvm.x86.sse.rcp.ps";
811 return "llvm.x86.sse2.cvtdq2pd";
813 return "llvm.x86.sse2.cvtdq2ps";
815 return "llvm.x86.sse2.cvtpd2dq";
817 return "llvm.x86.sse2.cvtps2dq";
819 return "llvm.x86.sse2.cvtpd2ps";
821 return "llvm.x86.sse2.cvtps2pd";
823 return "llvm.x86.sse2.cvttpd2dq";
825 return "llvm.x86.sse2.cvttps2dq";
827 return "llvm.x86.sse.cmp.ps";
829 return "llvm.x86.sse2.cmp.pd";
831 return "llvm.x86.sse2.packsswb.128";
833 return "llvm.x86.sse2.packssdw.128";
835 return "llvm.x86.sse2.packuswb.128";
837 return "llvm.x86.sse41.packusdw";
839 return "llvm.x86.sse2.pmulh.w";
840 case OP_PMULW_HIGH_UN:
841 return "llvm.x86.sse2.pmulhu.w";
844 g_assert_not_reached ();
850 simd_op_to_llvm_type (int opcode)
852 #if defined(TARGET_X86) || defined(TARGET_AMD64)
856 return type_to_simd_type (MONO_TYPE_R8);
859 return type_to_simd_type (MONO_TYPE_I8);
862 return type_to_simd_type (MONO_TYPE_I4);
867 return type_to_simd_type (MONO_TYPE_I2);
871 return type_to_simd_type (MONO_TYPE_I1);
873 return type_to_simd_type (MONO_TYPE_R4);
876 return type_to_simd_type (MONO_TYPE_I4);
880 return type_to_simd_type (MONO_TYPE_R8);
884 return type_to_simd_type (MONO_TYPE_R4);
885 case OP_EXTRACT_MASK:
886 return type_to_simd_type (MONO_TYPE_I1);
892 return type_to_simd_type (MONO_TYPE_R4);
895 return type_to_simd_type (MONO_TYPE_R8);
897 g_assert_not_reached ();
908 * Return the LLVM basic block corresponding to BB.
910 static LLVMBasicBlockRef
911 get_bb (EmitContext *ctx, MonoBasicBlock *bb)
913 char bb_name_buf [128];
916 if (ctx->bblocks [bb->block_num].bblock == NULL) {
917 if (bb->flags & BB_EXCEPTION_HANDLER) {
918 int clause_index = (mono_get_block_region_notry (ctx->cfg, bb->region) >> 8) - 1;
919 sprintf (bb_name_buf, "EH_CLAUSE%d_BB%d", clause_index, bb->block_num);
920 bb_name = bb_name_buf;
921 } else if (bb->block_num < 256) {
922 if (!ctx->lmodule->bb_names) {
923 ctx->lmodule->bb_names_len = 256;
924 ctx->lmodule->bb_names = g_new0 (char*, ctx->lmodule->bb_names_len);
926 if (!ctx->lmodule->bb_names [bb->block_num]) {
929 n = g_strdup_printf ("BB%d", bb->block_num);
930 mono_memory_barrier ();
931 ctx->lmodule->bb_names [bb->block_num] = n;
933 bb_name = ctx->lmodule->bb_names [bb->block_num];
935 sprintf (bb_name_buf, "BB%d", bb->block_num);
936 bb_name = bb_name_buf;
939 ctx->bblocks [bb->block_num].bblock = LLVMAppendBasicBlock (ctx->lmethod, bb_name);
940 ctx->bblocks [bb->block_num].end_bblock = ctx->bblocks [bb->block_num].bblock;
943 return ctx->bblocks [bb->block_num].bblock;
949 * Return the last LLVM bblock corresponding to BB.
950 * This might not be equal to the bb returned by get_bb () since we need to generate
951 * multiple LLVM bblocks for a mono bblock to handle throwing exceptions.
953 static LLVMBasicBlockRef
954 get_end_bb (EmitContext *ctx, MonoBasicBlock *bb)
957 return ctx->bblocks [bb->block_num].end_bblock;
960 static LLVMBasicBlockRef
961 gen_bb (EmitContext *ctx, const char *prefix)
965 sprintf (bb_name, "%s%d", prefix, ++ ctx->ex_index);
966 return LLVMAppendBasicBlock (ctx->lmethod, bb_name);
972 * Return the target of the patch identified by TYPE and TARGET.
975 resolve_patch (MonoCompile *cfg, MonoJumpInfoType type, gconstpointer target)
979 memset (&ji, 0, sizeof (ji));
981 ji.data.target = target;
983 return mono_resolve_patch_target (cfg->method, cfg->domain, NULL, &ji, FALSE);
989 * Emit code to convert the LLVM value V to DTYPE.
992 convert_full (EmitContext *ctx, LLVMValueRef v, LLVMTypeRef dtype, gboolean is_unsigned)
994 LLVMTypeRef stype = LLVMTypeOf (v);
996 if (stype != dtype) {
997 gboolean ext = FALSE;
1000 if (dtype == LLVMInt64Type () && (stype == LLVMInt32Type () || stype == LLVMInt16Type () || stype == LLVMInt8Type ()))
1002 else if (dtype == LLVMInt32Type () && (stype == LLVMInt16Type () || stype == LLVMInt8Type ()))
1004 else if (dtype == LLVMInt16Type () && (stype == LLVMInt8Type ()))
1008 return is_unsigned ? LLVMBuildZExt (ctx->builder, v, dtype, "") : LLVMBuildSExt (ctx->builder, v, dtype, "");
1010 if (dtype == LLVMDoubleType () && stype == LLVMFloatType ())
1011 return LLVMBuildFPExt (ctx->builder, v, dtype, "");
1014 if (stype == LLVMInt64Type () && (dtype == LLVMInt32Type () || dtype == LLVMInt16Type () || dtype == LLVMInt8Type ()))
1015 return LLVMBuildTrunc (ctx->builder, v, dtype, "");
1016 if (stype == LLVMInt32Type () && (dtype == LLVMInt16Type () || dtype == LLVMInt8Type ()))
1017 return LLVMBuildTrunc (ctx->builder, v, dtype, "");
1018 if (stype == LLVMInt16Type () && dtype == LLVMInt8Type ())
1019 return LLVMBuildTrunc (ctx->builder, v, dtype, "");
1020 if (stype == LLVMDoubleType () && dtype == LLVMFloatType ())
1021 return LLVMBuildFPTrunc (ctx->builder, v, dtype, "");
1023 if (LLVMGetTypeKind (stype) == LLVMPointerTypeKind && LLVMGetTypeKind (dtype) == LLVMPointerTypeKind)
1024 return LLVMBuildBitCast (ctx->builder, v, dtype, "");
1025 if (LLVMGetTypeKind (dtype) == LLVMPointerTypeKind)
1026 return LLVMBuildIntToPtr (ctx->builder, v, dtype, "");
1027 if (LLVMGetTypeKind (stype) == LLVMPointerTypeKind)
1028 return LLVMBuildPtrToInt (ctx->builder, v, dtype, "");
1030 if (mono_arch_is_soft_float ()) {
1031 if (stype == LLVMInt32Type () && dtype == LLVMFloatType ())
1032 return LLVMBuildBitCast (ctx->builder, v, dtype, "");
1033 if (stype == LLVMInt32Type () && dtype == LLVMDoubleType ())
1034 return LLVMBuildBitCast (ctx->builder, LLVMBuildZExt (ctx->builder, v, LLVMInt64Type (), ""), dtype, "");
1037 if (LLVMGetTypeKind (stype) == LLVMVectorTypeKind && LLVMGetTypeKind (dtype) == LLVMVectorTypeKind)
1038 return LLVMBuildBitCast (ctx->builder, v, dtype, "");
1041 LLVMDumpValue (LLVMConstNull (dtype));
1042 g_assert_not_reached ();
1050 convert (EmitContext *ctx, LLVMValueRef v, LLVMTypeRef dtype)
1052 return convert_full (ctx, v, dtype, FALSE);
1056 * emit_volatile_load:
1058 * If vreg is volatile, emit a load from its address.
1061 emit_volatile_load (EmitContext *ctx, int vreg)
1065 LLVMValueRef v = LLVMBuildLoad (ctx->builder, ctx->addresses [vreg], "");
1066 t = ctx->vreg_cli_types [vreg];
1067 if (t && !t->byref) {
1069 * Might have to zero extend since llvm doesn't have
1072 if (t->type == MONO_TYPE_U1 || t->type == MONO_TYPE_U2 || t->type == MONO_TYPE_CHAR || t->type == MONO_TYPE_BOOLEAN)
1073 v = LLVMBuildZExt (ctx->builder, v, LLVMInt32Type (), "");
1074 else if (t->type == MONO_TYPE_U8)
1075 v = LLVMBuildZExt (ctx->builder, v, LLVMInt64Type (), "");
1082 * emit_volatile_store:
1084 * If VREG is volatile, emit a store from its value to its address.
1087 emit_volatile_store (EmitContext *ctx, int vreg)
1089 MonoInst *var = get_vreg_to_inst (ctx->cfg, vreg);
1091 if (var && var->flags & (MONO_INST_VOLATILE|MONO_INST_INDIRECT)) {
1092 g_assert (ctx->addresses [vreg]);
1093 LLVMBuildStore (ctx->builder, convert (ctx, ctx->values [vreg], type_to_llvm_type (ctx, var->inst_vtype)), ctx->addresses [vreg]);
1099 * Maps parameter indexes in the original signature to parameter indexes
1100 * in the LLVM signature.
1103 /* The indexes of various special arguments in the LLVM signature */
1104 int vret_arg_pindex, this_arg_pindex, rgctx_arg_pindex, imt_arg_pindex;
1108 * sig_to_llvm_sig_full:
1110 * Return the LLVM signature corresponding to the mono signature SIG using the
1111 * calling convention information in CINFO. Return parameter mapping information in SINFO.
1114 sig_to_llvm_sig_full (EmitContext *ctx, MonoMethodSignature *sig, LLVMCallInfo *cinfo,
1117 LLVMTypeRef ret_type;
1118 LLVMTypeRef *param_types = NULL;
1120 int i, j, pindex, vret_arg_pindex = 0;
1122 gboolean vretaddr = FALSE;
1126 memset (sinfo, 0, sizeof (LLVMSigInfo));
1128 rtype = mini_replace_type (sig->ret);
1129 ret_type = type_to_llvm_type (ctx, rtype);
1130 CHECK_FAILURE (ctx);
1132 if (cinfo && cinfo->ret.storage == LLVMArgVtypeInReg) {
1133 /* LLVM models this by returning an aggregate value */
1134 if (cinfo->ret.pair_storage [0] == LLVMArgInIReg && cinfo->ret.pair_storage [1] == LLVMArgNone) {
1135 LLVMTypeRef members [2];
1137 members [0] = IntPtrType ();
1138 ret_type = LLVMStructType (members, 1, FALSE);
1140 g_assert_not_reached ();
1142 } else if (cinfo && mini_type_is_vtype (ctx->cfg, rtype)) {
1143 g_assert (cinfo->ret.storage == LLVMArgVtypeRetAddr);
1145 ret_type = LLVMVoidType ();
1148 pindexes = g_new0 (int, sig->param_count);
1149 param_types = g_new0 (LLVMTypeRef, (sig->param_count * 2) + 3);
1151 if (cinfo && cinfo->rgctx_arg) {
1153 sinfo->rgctx_arg_pindex = pindex;
1154 param_types [pindex] = ctx->lmodule->ptr_type;
1157 if (cinfo && cinfo->imt_arg) {
1159 sinfo->imt_arg_pindex = pindex;
1160 param_types [pindex] = ctx->lmodule->ptr_type;
1164 /* Compute the index in the LLVM signature where the vret arg needs to be passed */
1165 vret_arg_pindex = pindex;
1166 if (cinfo->vret_arg_index == 1) {
1167 /* Add the slots consumed by the first argument */
1168 LLVMArgInfo *ainfo = &cinfo->args [0];
1169 switch (ainfo->storage) {
1170 case LLVMArgVtypeInReg:
1171 for (j = 0; j < 2; ++j) {
1172 if (ainfo->pair_storage [j] == LLVMArgInIReg)
1182 sinfo->vret_arg_pindex = vret_arg_pindex;
1185 if (vretaddr && vret_arg_pindex == pindex)
1186 param_types [pindex ++] = IntPtrType ();
1189 sinfo->this_arg_pindex = pindex;
1190 param_types [pindex ++] = ThisType ();
1192 if (vretaddr && vret_arg_pindex == pindex)
1193 param_types [pindex ++] = IntPtrType ();
1194 for (i = 0; i < sig->param_count; ++i) {
1195 if (vretaddr && vret_arg_pindex == pindex)
1196 param_types [pindex ++] = IntPtrType ();
1197 pindexes [i] = pindex;
1198 if (cinfo && cinfo->args [i + sig->hasthis].storage == LLVMArgVtypeInReg) {
1199 for (j = 0; j < 2; ++j) {
1200 switch (cinfo->args [i + sig->hasthis].pair_storage [j]) {
1202 param_types [pindex ++] = LLVMIntType (sizeof (gpointer) * 8);
1207 g_assert_not_reached ();
1210 } else if (cinfo && cinfo->args [i + sig->hasthis].storage == LLVMArgVtypeByVal) {
1211 param_types [pindex] = type_to_llvm_arg_type (ctx, sig->params [i]);
1212 CHECK_FAILURE (ctx);
1213 param_types [pindex] = LLVMPointerType (param_types [pindex], 0);
1216 param_types [pindex ++] = type_to_llvm_arg_type (ctx, sig->params [i]);
1219 if (vretaddr && vret_arg_pindex == pindex)
1220 param_types [pindex ++] = IntPtrType ();
1222 CHECK_FAILURE (ctx);
1224 res = LLVMFunctionType (ret_type, param_types, pindex, FALSE);
1225 g_free (param_types);
1228 sinfo->pindexes = pindexes;
1236 g_free (param_types);
1242 sig_to_llvm_sig (EmitContext *ctx, MonoMethodSignature *sig)
1244 return sig_to_llvm_sig_full (ctx, sig, NULL, NULL);
1248 * LLVMFunctionType1:
1250 * Create an LLVM function type from the arguments.
1252 static G_GNUC_UNUSED LLVMTypeRef
1253 LLVMFunctionType1(LLVMTypeRef ReturnType,
1254 LLVMTypeRef ParamType1,
1257 LLVMTypeRef param_types [1];
1259 param_types [0] = ParamType1;
1261 return LLVMFunctionType (ReturnType, param_types, 1, IsVarArg);
1265 * LLVMFunctionType2:
1267 * Create an LLVM function type from the arguments.
1269 static G_GNUC_UNUSED LLVMTypeRef
1270 LLVMFunctionType2(LLVMTypeRef ReturnType,
1271 LLVMTypeRef ParamType1,
1272 LLVMTypeRef ParamType2,
1275 LLVMTypeRef param_types [2];
1277 param_types [0] = ParamType1;
1278 param_types [1] = ParamType2;
1280 return LLVMFunctionType (ReturnType, param_types, 2, IsVarArg);
1284 * LLVMFunctionType3:
1286 * Create an LLVM function type from the arguments.
1288 static G_GNUC_UNUSED LLVMTypeRef
1289 LLVMFunctionType3(LLVMTypeRef ReturnType,
1290 LLVMTypeRef ParamType1,
1291 LLVMTypeRef ParamType2,
1292 LLVMTypeRef ParamType3,
1295 LLVMTypeRef param_types [3];
1297 param_types [0] = ParamType1;
1298 param_types [1] = ParamType2;
1299 param_types [2] = ParamType3;
1301 return LLVMFunctionType (ReturnType, param_types, 3, IsVarArg);
1307 * Create an LLVM builder and remember it so it can be freed later.
1309 static LLVMBuilderRef
1310 create_builder (EmitContext *ctx)
1312 LLVMBuilderRef builder = LLVMCreateBuilder ();
1314 ctx->builders = g_slist_prepend_mempool (ctx->cfg->mempool, ctx->builders, builder);
1320 get_plt_entry (EmitContext *ctx, LLVMTypeRef llvm_sig, MonoJumpInfoType type, gconstpointer data)
1322 char *callee_name = mono_aot_get_plt_symbol (type, data);
1323 LLVMValueRef callee;
1324 MonoJumpInfo *ji = NULL;
1329 if (ctx->cfg->compile_aot)
1330 /* Add a patch so referenced wrappers can be compiled in full aot mode */
1331 mono_add_patch_info (ctx->cfg, 0, type, data);
1334 callee = g_hash_table_lookup (ctx->lmodule->plt_entries, callee_name);
1336 callee = LLVMAddFunction (ctx->module, callee_name, llvm_sig);
1338 LLVMSetVisibility (callee, LLVMHiddenVisibility);
1340 g_hash_table_insert (ctx->lmodule->plt_entries, (char*)callee_name, callee);
1343 if (ctx->cfg->compile_aot) {
1344 ji = g_new0 (MonoJumpInfo, 1);
1346 ji->data.target = data;
1348 g_hash_table_insert (ctx->lmodule->plt_entries_ji, ji, callee);
1355 get_handler_clause (MonoCompile *cfg, MonoBasicBlock *bb)
1357 MonoMethodHeader *header = cfg->header;
1358 MonoExceptionClause *clause;
1362 if (bb->region != -1 && MONO_BBLOCK_IS_IN_REGION (bb, MONO_REGION_TRY))
1363 return (bb->region >> 8) - 1;
1366 for (i = 0; i < header->num_clauses; ++i) {
1367 clause = &header->clauses [i];
1369 if (MONO_OFFSET_IN_CLAUSE (clause, bb->real_offset) && clause->flags == MONO_EXCEPTION_CLAUSE_NONE)
1377 set_metadata_flag (LLVMValueRef v, const char *flag_name)
1379 LLVMValueRef md_arg;
1382 md_kind = LLVMGetMDKindID (flag_name, strlen (flag_name));
1383 md_arg = LLVMMDString ("mono", 4);
1384 LLVMSetMetadata (v, md_kind, LLVMMDNode (&md_arg, 1));
1388 set_invariant_load_flag (LLVMValueRef v)
1390 LLVMValueRef md_arg;
1392 const char *flag_name;
1394 // FIXME: Cache this
1395 flag_name = "invariant.load";
1396 md_kind = LLVMGetMDKindID (flag_name, strlen (flag_name));
1397 md_arg = LLVMMDString ("<index>", strlen ("<index>"));
1398 LLVMSetMetadata (v, md_kind, LLVMMDNode (&md_arg, 1));
1404 * Emit an LLVM call or invoke instruction depending on whenever the call is inside
1408 emit_call (EmitContext *ctx, MonoBasicBlock *bb, LLVMBuilderRef *builder_ref, LLVMValueRef callee, LLVMValueRef *args, int pindex)
1410 MonoCompile *cfg = ctx->cfg;
1412 LLVMBuilderRef builder = *builder_ref;
1415 clause_index = get_handler_clause (cfg, bb);
1417 if (clause_index != -1) {
1418 MonoMethodHeader *header = cfg->header;
1419 MonoExceptionClause *ec = &header->clauses [clause_index];
1420 MonoBasicBlock *tblock;
1421 LLVMBasicBlockRef ex_bb, noex_bb;
1424 * Have to use an invoke instead of a call, branching to the
1425 * handler bblock of the clause containing this bblock.
1428 g_assert (ec->flags == MONO_EXCEPTION_CLAUSE_NONE || ec->flags == MONO_EXCEPTION_CLAUSE_FINALLY);
1430 tblock = cfg->cil_offset_to_bb [ec->handler_offset];
1433 ctx->bblocks [tblock->block_num].invoke_target = TRUE;
1435 ex_bb = get_bb (ctx, tblock);
1437 noex_bb = gen_bb (ctx, "NOEX_BB");
1440 lcall = LLVMBuildInvoke (builder, callee, args, pindex, noex_bb, ex_bb, "");
1442 builder = ctx->builder = create_builder (ctx);
1443 LLVMPositionBuilderAtEnd (ctx->builder, noex_bb);
1445 ctx->bblocks [bb->block_num].end_bblock = noex_bb;
1447 lcall = LLVMBuildCall (builder, callee, args, pindex, "");
1448 ctx->builder = builder;
1451 *builder_ref = ctx->builder;
1456 #if LLVM_API_VERSION >= 4
1457 #define EXTRA_MONO_LOAD_STORE_ARGS 1
1459 #define EXTRA_MONO_LOAD_STORE_ARGS 0
1463 emit_load_general (EmitContext *ctx, MonoBasicBlock *bb, LLVMBuilderRef *builder_ref, int size, LLVMValueRef addr, const char *name, gboolean is_faulting, BarrierKind barrier)
1465 const char *intrins_name;
1466 LLVMValueRef args [16], res;
1467 LLVMTypeRef addr_type;
1469 if (is_faulting && bb->region != -1) {
1470 #if LLVM_API_VERSION >= 4
1471 LLVMAtomicOrdering ordering;
1474 case LLVM_BARRIER_NONE:
1475 ordering = LLVMAtomicOrderingNotAtomic;
1477 case LLVM_BARRIER_ACQ:
1478 ordering = LLVMAtomicOrderingAcquire;
1480 case LLVM_BARRIER_SEQ:
1481 ordering = LLVMAtomicOrderingSequentiallyConsistent;
1484 g_assert_not_reached ();
1490 * We handle loads which can fault by calling a mono specific intrinsic
1491 * using an invoke, so they are handled properly inside try blocks.
1492 * We can't use this outside clauses, since LLVM optimizes intrinsics which
1493 * are marked with IntrReadArgMem.
1497 intrins_name = "llvm.mono.load.i8.p0i8";
1500 intrins_name = "llvm.mono.load.i16.p0i16";
1503 intrins_name = "llvm.mono.load.i32.p0i32";
1506 intrins_name = "llvm.mono.load.i64.p0i64";
1509 g_assert_not_reached ();
1512 addr_type = LLVMTypeOf (addr);
1513 if (addr_type == LLVMPointerType (LLVMDoubleType (), 0) || addr_type == LLVMPointerType (LLVMFloatType (), 0))
1514 addr = LLVMBuildBitCast (*builder_ref, addr, LLVMPointerType (LLVMIntType (size * 8), 0), "");
1517 args [1] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
1518 args [2] = LLVMConstInt (LLVMInt1Type (), TRUE, FALSE);
1519 #if LLVM_API_VERSION >= 4
1520 args [3] = LLVMConstInt (LLVMInt32Type (), ordering, FALSE);
1522 res = emit_call (ctx, bb, builder_ref, LLVMGetNamedFunction (ctx->module, intrins_name), args, 3 + EXTRA_MONO_LOAD_STORE_ARGS);
1524 if (addr_type == LLVMPointerType (LLVMDoubleType (), 0))
1525 res = LLVMBuildBitCast (*builder_ref, res, LLVMDoubleType (), "");
1526 else if (addr_type == LLVMPointerType (LLVMFloatType (), 0))
1527 res = LLVMBuildBitCast (*builder_ref, res, LLVMFloatType (), "");
1534 * We emit volatile loads for loads which can fault, because otherwise
1535 * LLVM will generate invalid code when encountering a load from a
1538 res = mono_llvm_build_load (*builder_ref, addr, name, is_faulting, barrier);
1540 /* Mark it with a custom metadata */
1543 set_metadata_flag (res, "mono.faulting.load");
1551 emit_load (EmitContext *ctx, MonoBasicBlock *bb, LLVMBuilderRef *builder_ref, int size, LLVMValueRef addr, const char *name, gboolean is_faulting)
1553 return emit_load_general (ctx, bb, builder_ref, size, addr, name, is_faulting, LLVM_BARRIER_NONE);
1557 emit_store_general (EmitContext *ctx, MonoBasicBlock *bb, LLVMBuilderRef *builder_ref, int size, LLVMValueRef value, LLVMValueRef addr, gboolean is_faulting, BarrierKind barrier)
1559 const char *intrins_name;
1560 LLVMValueRef args [16];
1562 if (is_faulting && bb->region != -1) {
1563 #if LLVM_API_VERSION >= 4
1564 LLVMAtomicOrdering ordering;
1567 case LLVM_BARRIER_NONE:
1568 ordering = LLVMAtomicOrderingNotAtomic;
1570 case LLVM_BARRIER_REL:
1571 ordering = LLVMAtomicOrderingRelease;
1573 case LLVM_BARRIER_SEQ:
1574 ordering = LLVMAtomicOrderingSequentiallyConsistent;
1577 g_assert_not_reached ();
1584 intrins_name = "llvm.mono.store.i8.p0i8";
1587 intrins_name = "llvm.mono.store.i16.p0i16";
1590 intrins_name = "llvm.mono.store.i32.p0i32";
1593 intrins_name = "llvm.mono.store.i64.p0i64";
1596 g_assert_not_reached ();
1599 if (LLVMTypeOf (value) == LLVMDoubleType () || LLVMTypeOf (value) == LLVMFloatType ()) {
1600 value = LLVMBuildBitCast (*builder_ref, value, LLVMIntType (size * 8), "");
1601 addr = LLVMBuildBitCast (*builder_ref, addr, LLVMPointerType (LLVMIntType (size * 8), 0), "");
1606 args [2] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
1607 args [3] = LLVMConstInt (LLVMInt1Type (), TRUE, FALSE);
1608 #if LLVM_API_VERSION >= 4
1609 args [4] = LLVMConstInt (LLVMInt32Type (), ordering, FALSE);
1611 emit_call (ctx, bb, builder_ref, LLVMGetNamedFunction (ctx->module, intrins_name), args, 4 + EXTRA_MONO_LOAD_STORE_ARGS);
1613 mono_llvm_build_store (*builder_ref, value, addr, is_faulting, barrier);
1618 emit_store (EmitContext *ctx, MonoBasicBlock *bb, LLVMBuilderRef *builder_ref, int size, LLVMValueRef value, LLVMValueRef addr, gboolean is_faulting)
1620 emit_store_general (ctx, bb, builder_ref, size, value, addr, is_faulting, LLVM_BARRIER_NONE);
1624 * emit_cond_system_exception:
1626 * Emit code to throw the exception EXC_TYPE if the condition CMP is false.
1627 * Might set the ctx exception.
1630 emit_cond_system_exception (EmitContext *ctx, MonoBasicBlock *bb, const char *exc_type, LLVMValueRef cmp)
1632 LLVMBasicBlockRef ex_bb, noex_bb;
1633 LLVMBuilderRef builder;
1634 MonoClass *exc_class;
1635 LLVMValueRef args [2];
1637 ex_bb = gen_bb (ctx, "EX_BB");
1638 noex_bb = gen_bb (ctx, "NOEX_BB");
1640 LLVMBuildCondBr (ctx->builder, cmp, ex_bb, noex_bb);
1642 exc_class = mono_class_from_name (mono_get_corlib (), "System", exc_type);
1643 g_assert (exc_class);
1645 /* Emit exception throwing code */
1646 builder = create_builder (ctx);
1647 LLVMPositionBuilderAtEnd (builder, ex_bb);
1649 if (!ctx->lmodule->throw_corlib_exception) {
1650 LLVMValueRef callee;
1652 const char *icall_name;
1654 MonoMethodSignature *throw_sig = mono_metadata_signature_alloc (mono_get_corlib (), 2);
1655 throw_sig->ret = &mono_get_void_class ()->byval_arg;
1656 throw_sig->params [0] = &mono_get_int32_class ()->byval_arg;
1657 icall_name = "llvm_throw_corlib_exception_abs_trampoline";
1658 /* This will become i8* */
1659 throw_sig->params [1] = &mono_get_byte_class ()->this_arg;
1660 sig = sig_to_llvm_sig (ctx, throw_sig);
1662 if (ctx->cfg->compile_aot) {
1663 callee = get_plt_entry (ctx, sig, MONO_PATCH_INFO_INTERNAL_METHOD, icall_name);
1665 callee = LLVMAddFunction (ctx->module, "llvm_throw_corlib_exception_trampoline", sig_to_llvm_sig (ctx, throw_sig));
1668 * Differences between the LLVM/non-LLVM throw corlib exception trampoline:
1669 * - On x86, LLVM generated code doesn't push the arguments
1670 * - The trampoline takes the throw address as an arguments, not a pc offset.
1672 LLVMAddGlobalMapping (ctx->lmodule->ee, callee, resolve_patch (ctx->cfg, MONO_PATCH_INFO_INTERNAL_METHOD, icall_name));
1675 mono_memory_barrier ();
1676 ctx->lmodule->throw_corlib_exception = callee;
1679 if (IS_TARGET_X86 || IS_TARGET_AMD64)
1680 args [0] = LLVMConstInt (LLVMInt32Type (), exc_class->type_token - MONO_TOKEN_TYPE_DEF, FALSE);
1682 args [0] = LLVMConstInt (LLVMInt32Type (), exc_class->type_token, FALSE);
1685 * The LLVM mono branch contains changes so a block address can be passed as an
1686 * argument to a call.
1688 args [1] = LLVMBlockAddress (ctx->lmethod, ex_bb);
1689 emit_call (ctx, bb, &builder, ctx->lmodule->throw_corlib_exception, args, 2);
1691 LLVMBuildUnreachable (builder);
1693 ctx->builder = create_builder (ctx);
1694 LLVMPositionBuilderAtEnd (ctx->builder, noex_bb);
1696 ctx->bblocks [bb->block_num].end_bblock = noex_bb;
1703 * emit_reg_to_vtype:
1705 * Emit code to store the vtype in the registers REGS to the address ADDRESS.
1708 emit_reg_to_vtype (EmitContext *ctx, LLVMBuilderRef builder, MonoType *t, LLVMValueRef address, LLVMArgInfo *ainfo, LLVMValueRef *regs)
1712 size = get_vtype_size (t);
1714 if (MONO_CLASS_IS_SIMD (ctx->cfg, mono_class_from_mono_type (t))) {
1715 address = LLVMBuildBitCast (ctx->builder, address, LLVMPointerType (LLVMInt8Type (), 0), "");
1718 for (j = 0; j < 2; ++j) {
1719 LLVMValueRef index [2], addr;
1720 int part_size = size > sizeof (gpointer) ? sizeof (gpointer) : size;
1721 LLVMTypeRef part_type;
1723 if (ainfo->pair_storage [j] == LLVMArgNone)
1726 part_type = LLVMIntType (part_size * 8);
1727 if (MONO_CLASS_IS_SIMD (ctx->cfg, mono_class_from_mono_type (t))) {
1728 index [0] = LLVMConstInt (LLVMInt32Type (), j * sizeof (gpointer), FALSE);
1729 addr = LLVMBuildGEP (builder, address, index, 1, "");
1731 index [0] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
1732 index [1] = LLVMConstInt (LLVMInt32Type (), j * sizeof (gpointer), FALSE);
1733 addr = LLVMBuildGEP (builder, address, index, 2, "");
1735 switch (ainfo->pair_storage [j]) {
1737 LLVMBuildStore (builder, convert (ctx, regs [j], part_type), LLVMBuildBitCast (ctx->builder, addr, LLVMPointerType (part_type, 0), ""));
1742 g_assert_not_reached ();
1745 size -= sizeof (gpointer);
1750 * emit_vtype_to_reg:
1752 * Emit code to load a vtype at address ADDRESS into registers. Store the registers
1753 * into REGS, and the number of registers into NREGS.
1756 emit_vtype_to_reg (EmitContext *ctx, LLVMBuilderRef builder, MonoType *t, LLVMValueRef address, LLVMArgInfo *ainfo, LLVMValueRef *regs, guint32 *nregs)
1761 size = get_vtype_size (t);
1763 if (MONO_CLASS_IS_SIMD (ctx->cfg, mono_class_from_mono_type (t))) {
1764 address = LLVMBuildBitCast (ctx->builder, address, LLVMPointerType (LLVMInt8Type (), 0), "");
1767 for (j = 0; j < 2; ++j) {
1768 LLVMValueRef index [2], addr;
1769 int partsize = size > sizeof (gpointer) ? sizeof (gpointer) : size;
1771 if (ainfo->pair_storage [j] == LLVMArgNone)
1774 if (MONO_CLASS_IS_SIMD (ctx->cfg, mono_class_from_mono_type (t))) {
1775 index [0] = LLVMConstInt (LLVMInt32Type (), j * sizeof (gpointer), FALSE);
1776 addr = LLVMBuildGEP (builder, address, index, 1, "");
1778 index [0] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
1779 index [1] = LLVMConstInt (LLVMInt32Type (), j * sizeof (gpointer), FALSE);
1780 addr = LLVMBuildGEP (builder, address, index, 2, "");
1782 switch (ainfo->pair_storage [j]) {
1784 regs [pindex ++] = convert (ctx, LLVMBuildLoad (builder, LLVMBuildBitCast (ctx->builder, addr, LLVMPointerType (LLVMIntType (partsize * 8), 0), ""), ""), IntPtrType ());
1789 g_assert_not_reached ();
1791 size -= sizeof (gpointer);
1798 build_alloca_llvm_type (EmitContext *ctx, LLVMTypeRef t, int align)
1801 * Have to place all alloca's at the end of the entry bb, since otherwise they would
1802 * get executed every time control reaches them.
1804 LLVMPositionBuilder (ctx->alloca_builder, get_bb (ctx, ctx->cfg->bb_entry), ctx->last_alloca);
1806 ctx->last_alloca = mono_llvm_build_alloca (ctx->alloca_builder, t, NULL, align, "");
1807 return ctx->last_alloca;
1811 build_alloca (EmitContext *ctx, MonoType *t)
1813 MonoClass *k = mono_class_from_mono_type (t);
1816 if (MONO_CLASS_IS_SIMD (ctx->cfg, k))
1819 align = mono_class_min_align (k);
1821 /* Sometimes align is not a power of 2 */
1822 while (mono_is_power_of_two (align) == -1)
1825 return build_alloca_llvm_type (ctx, type_to_llvm_type (ctx, t), align);
1829 * Put the global into the 'llvm.used' array to prevent it from being optimized away.
1832 mark_as_used (MonoLLVMModule *lmodule, LLVMValueRef global)
1835 lmodule->used = g_ptr_array_sized_new (16);
1836 g_ptr_array_add (lmodule->used, global);
1840 emit_llvm_used (MonoLLVMModule *lmodule)
1842 LLVMModuleRef module = lmodule->module;
1843 LLVMTypeRef used_type;
1844 LLVMValueRef used, *used_elem;
1850 used_type = LLVMArrayType (LLVMPointerType (LLVMInt8Type (), 0), lmodule->used->len);
1851 used = LLVMAddGlobal (module, used_type, "llvm.used");
1852 used_elem = g_new0 (LLVMValueRef, lmodule->used->len);
1853 for (i = 0; i < lmodule->used->len; ++i)
1854 used_elem [i] = LLVMConstBitCast (g_ptr_array_index (lmodule->used, i), LLVMPointerType (LLVMInt8Type (), 0));
1855 LLVMSetInitializer (used, LLVMConstArray (LLVMPointerType (LLVMInt8Type (), 0), used_elem, lmodule->used->len));
1856 LLVMSetLinkage (used, LLVMAppendingLinkage);
1857 LLVMSetSection (used, "llvm.metadata");
1863 * Emit code to load/convert arguments.
1866 emit_entry_bb (EmitContext *ctx, LLVMBuilderRef builder)
1869 MonoCompile *cfg = ctx->cfg;
1870 MonoMethodSignature *sig = ctx->sig;
1871 LLVMCallInfo *linfo = ctx->linfo;
1874 ctx->alloca_builder = create_builder (ctx);
1877 * Handle indirect/volatile variables by allocating memory for them
1878 * using 'alloca', and storing their address in a temporary.
1880 for (i = 0; i < cfg->num_varinfo; ++i) {
1881 MonoInst *var = cfg->varinfo [i];
1884 if (var->flags & (MONO_INST_VOLATILE|MONO_INST_INDIRECT) || mini_type_is_vtype (cfg, var->inst_vtype)) {
1885 vtype = type_to_llvm_type (ctx, var->inst_vtype);
1886 CHECK_FAILURE (ctx);
1887 /* Could be already created by an OP_VPHI */
1888 if (!ctx->addresses [var->dreg])
1889 ctx->addresses [var->dreg] = build_alloca (ctx, var->inst_vtype);
1890 ctx->vreg_cli_types [var->dreg] = var->inst_vtype;
1894 for (i = 0; i < sig->param_count; ++i) {
1895 LLVMArgInfo *ainfo = &linfo->args [i + sig->hasthis];
1896 int reg = cfg->args [i + sig->hasthis]->dreg;
1898 if (ainfo->storage == LLVMArgVtypeInReg) {
1899 LLVMValueRef regs [2];
1902 * Emit code to save the argument from the registers to
1903 * the real argument.
1905 pindex = ctx->pindexes [i];
1906 regs [0] = LLVMGetParam (ctx->lmethod, pindex);
1907 if (ainfo->pair_storage [1] != LLVMArgNone)
1908 regs [1] = LLVMGetParam (ctx->lmethod, pindex + 1);
1912 ctx->addresses [reg] = build_alloca (ctx, sig->params [i]);
1914 emit_reg_to_vtype (ctx, builder, sig->params [i], ctx->addresses [reg], ainfo, regs);
1916 if (MONO_CLASS_IS_SIMD (ctx->cfg, mono_class_from_mono_type (sig->params [i]))) {
1917 /* Treat these as normal values */
1918 ctx->values [reg] = LLVMBuildLoad (builder, ctx->addresses [reg], "");
1920 } else if (ainfo->storage == LLVMArgVtypeByVal) {
1921 ctx->addresses [reg] = LLVMGetParam (ctx->lmethod, ctx->pindexes [i]);
1923 if (MONO_CLASS_IS_SIMD (ctx->cfg, mono_class_from_mono_type (sig->params [i]))) {
1924 /* Treat these as normal values */
1925 ctx->values [reg] = LLVMBuildLoad (builder, ctx->addresses [reg], "");
1928 ctx->values [reg] = convert_full (ctx, ctx->values [reg], llvm_type_to_stack_type (type_to_llvm_type (ctx, sig->params [i])), type_is_unsigned (ctx, sig->params [i]));
1933 emit_volatile_store (ctx, cfg->vret_addr->dreg);
1935 emit_volatile_store (ctx, cfg->args [0]->dreg);
1936 for (i = 0; i < sig->param_count; ++i)
1937 if (!mini_type_is_vtype (cfg, sig->params [i]))
1938 emit_volatile_store (ctx, cfg->args [i + sig->hasthis]->dreg);
1940 if (sig->hasthis && !cfg->rgctx_var && cfg->generic_sharing_context) {
1941 LLVMValueRef this_alloc;
1944 * The exception handling code needs the location where the this argument was
1945 * stored for gshared methods. We create a separate alloca to hold it, and mark it
1946 * with the "mono.this" custom metadata to tell llvm that it needs to save its
1947 * location into the LSDA.
1949 this_alloc = mono_llvm_build_alloca (builder, ThisType (), LLVMConstInt (LLVMInt32Type (), 1, FALSE), 0, "");
1950 /* This volatile store will keep the alloca alive */
1951 mono_llvm_build_store (builder, ctx->values [cfg->args [0]->dreg], this_alloc, TRUE, LLVM_BARRIER_NONE);
1953 set_metadata_flag (this_alloc, "mono.this");
1956 if (cfg->rgctx_var) {
1957 LLVMValueRef rgctx_alloc, store;
1960 * We handle the rgctx arg similarly to the this pointer.
1962 g_assert (ctx->addresses [cfg->rgctx_var->dreg]);
1963 rgctx_alloc = ctx->addresses [cfg->rgctx_var->dreg];
1964 /* This volatile store will keep the alloca alive */
1965 store = mono_llvm_build_store (builder, convert (ctx, ctx->rgctx_arg, IntPtrType ()), rgctx_alloc, TRUE, LLVM_BARRIER_NONE);
1967 set_metadata_flag (rgctx_alloc, "mono.this");
1971 * For finally clauses, create an indicator variable telling OP_ENDFINALLY whenever
1972 * it needs to continue normally, or return back to the exception handling system.
1974 for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
1975 if (bb->region != -1 && (bb->flags & BB_EXCEPTION_HANDLER))
1976 g_hash_table_insert (ctx->region_to_handler, GUINT_TO_POINTER (mono_get_block_region_notry (cfg, bb->region)), bb);
1977 if (bb->region != -1 && (bb->flags & BB_EXCEPTION_HANDLER) && bb->in_scount == 0) {
1981 sprintf (name, "finally_ind_bb%d", bb->block_num);
1982 val = LLVMBuildAlloca (builder, LLVMInt32Type (), name);
1983 LLVMBuildStore (builder, LLVMConstInt (LLVMInt32Type (), 0, FALSE), val);
1985 ctx->bblocks [bb->block_num].finally_ind = val;
1988 * Create a new bblock which CALL_HANDLER can branch to, because branching to the
1989 * LLVM bblock containing the call to llvm.eh.selector causes problems for the
1990 * LLVM optimizer passes.
1992 sprintf (name, "BB_%d_CALL_HANDLER_TARGET", bb->block_num);
1993 ctx->bblocks [bb->block_num].call_handler_target_bb = LLVMAppendBasicBlock (ctx->lmethod, name);
2001 /* Have to export this for AOT */
2003 mono_personality (void);
2006 mono_personality (void)
2009 g_assert_not_reached ();
2013 process_call (EmitContext *ctx, MonoBasicBlock *bb, LLVMBuilderRef *builder_ref, MonoInst *ins)
2015 MonoCompile *cfg = ctx->cfg;
2016 LLVMModuleRef module = ctx->module;
2017 LLVMValueRef *values = ctx->values;
2018 LLVMValueRef *addresses = ctx->addresses;
2019 MonoCallInst *call = (MonoCallInst*)ins;
2020 MonoMethodSignature *sig = call->signature;
2021 LLVMValueRef callee = NULL, lcall;
2023 LLVMCallInfo *cinfo;
2027 LLVMTypeRef llvm_sig;
2029 gboolean virtual, calli;
2030 LLVMBuilderRef builder = *builder_ref;
2033 if (call->signature->call_convention != MONO_CALL_DEFAULT)
2034 LLVM_FAILURE (ctx, "non-default callconv");
2036 cinfo = call->cinfo;
2037 if (call->rgctx_arg_reg)
2038 cinfo->rgctx_arg = TRUE;
2039 if (call->imt_arg_reg)
2040 cinfo->imt_arg = TRUE;
2042 vretaddr = cinfo && cinfo->ret.storage == LLVMArgVtypeRetAddr;
2044 llvm_sig = sig_to_llvm_sig_full (ctx, sig, cinfo, &sinfo);
2045 CHECK_FAILURE (ctx);
2047 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);
2048 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);
2050 /* FIXME: Avoid creating duplicate methods */
2052 if (ins->flags & MONO_INST_HAS_METHOD) {
2056 if (cfg->compile_aot) {
2057 callee = get_plt_entry (ctx, llvm_sig, MONO_PATCH_INFO_METHOD, call->method);
2059 LLVM_FAILURE (ctx, "can't encode patch");
2061 callee = LLVMAddFunction (module, "", llvm_sig);
2064 mono_create_jit_trampoline_in_domain (mono_domain_get (),
2066 LLVMAddGlobalMapping (ctx->lmodule->ee, callee, target);
2070 if (call->method && strstr (call->method->klass->name, "AsyncVoidMethodBuilder"))
2071 /* LLVM miscompiles async methods */
2072 LLVM_FAILURE (ctx, "#13734");
2075 MonoJitICallInfo *info = mono_find_jit_icall_by_addr (call->fptr);
2081 memset (&ji, 0, sizeof (ji));
2082 ji.type = MONO_PATCH_INFO_JIT_ICALL_ADDR;
2083 ji.data.target = info->name;
2085 target = mono_resolve_patch_target (cfg->method, cfg->domain, NULL, &ji, FALSE);
2087 if (cfg->compile_aot) {
2088 callee = get_plt_entry (ctx, llvm_sig, MONO_PATCH_INFO_INTERNAL_METHOD, (char*)info->name);
2090 LLVM_FAILURE (ctx, "can't encode patch");
2092 callee = LLVMAddFunction (module, "", llvm_sig);
2093 target = (gpointer)mono_icall_get_wrapper (info);
2094 LLVMAddGlobalMapping (ctx->lmodule->ee, callee, target);
2097 if (cfg->compile_aot) {
2099 if (cfg->abs_patches) {
2100 MonoJumpInfo *abs_ji = g_hash_table_lookup (cfg->abs_patches, call->fptr);
2102 callee = get_plt_entry (ctx, llvm_sig, abs_ji->type, abs_ji->data.target);
2104 LLVM_FAILURE (ctx, "can't encode patch");
2108 LLVM_FAILURE (ctx, "aot");
2110 callee = LLVMAddFunction (module, "", llvm_sig);
2112 if (cfg->abs_patches) {
2113 MonoJumpInfo *abs_ji = g_hash_table_lookup (cfg->abs_patches, call->fptr);
2116 * FIXME: Some trampolines might have
2117 * their own calling convention on some platforms.
2119 #ifndef TARGET_AMD64
2120 if (abs_ji->type == MONO_PATCH_INFO_MONITOR_ENTER || abs_ji->type == MONO_PATCH_INFO_MONITOR_ENTER_V4 ||
2121 abs_ji->type == MONO_PATCH_INFO_MONITOR_EXIT || abs_ji->type == MONO_PATCH_INFO_GENERIC_CLASS_INIT)
2122 LLVM_FAILURE (ctx, "trampoline with own cconv");
2124 target = mono_resolve_patch_target (cfg->method, cfg->domain, NULL, abs_ji, FALSE);
2125 LLVMAddGlobalMapping (ctx->lmodule->ee, callee, target);
2129 LLVMAddGlobalMapping (ctx->lmodule->ee, callee, (gpointer)call->fptr);
2135 int size = sizeof (gpointer);
2138 g_assert (ins->inst_offset % size == 0);
2139 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset / size, FALSE);
2141 callee = convert (ctx, LLVMBuildLoad (builder, LLVMBuildGEP (builder, convert (ctx, values [ins->inst_basereg], LLVMPointerType (LLVMPointerType (IntPtrType (), 0), 0)), &index, 1, ""), ""), LLVMPointerType (llvm_sig, 0));
2143 callee = convert (ctx, values [ins->sreg1], LLVMPointerType (llvm_sig, 0));
2145 if (ins->flags & MONO_INST_HAS_METHOD) {
2150 * Collect and convert arguments
2152 nargs = (sig->param_count * 2) + sig->hasthis + vretaddr + call->rgctx_reg + call->imt_arg_reg;
2153 len = sizeof (LLVMValueRef) * nargs;
2154 args = alloca (len);
2155 memset (args, 0, len);
2156 l = call->out_ireg_args;
2158 if (call->rgctx_arg_reg) {
2159 g_assert (values [call->rgctx_arg_reg]);
2160 g_assert (sinfo.rgctx_arg_pindex < nargs);
2162 * On ARM, the imt/rgctx argument is passed in a caller save register, but some of our trampolines etc. clobber it, leading to
2163 * problems is LLVM moves the arg assignment earlier. To work around this, save the argument into a stack slot and load
2164 * it using a volatile load.
2167 if (!ctx->imt_rgctx_loc)
2168 ctx->imt_rgctx_loc = build_alloca_llvm_type (ctx, ctx->lmodule->ptr_type, sizeof (gpointer));
2169 LLVMBuildStore (builder, convert (ctx, ctx->values [call->rgctx_arg_reg], ctx->lmodule->ptr_type), ctx->imt_rgctx_loc);
2170 args [sinfo.rgctx_arg_pindex] = mono_llvm_build_load (builder, ctx->imt_rgctx_loc, "", TRUE, LLVM_BARRIER_NONE);
2172 args [sinfo.rgctx_arg_pindex] = convert (ctx, values [call->rgctx_arg_reg], ctx->lmodule->ptr_type);
2175 if (call->imt_arg_reg) {
2176 g_assert (values [call->imt_arg_reg]);
2177 g_assert (sinfo.imt_arg_pindex < nargs);
2179 if (!ctx->imt_rgctx_loc)
2180 ctx->imt_rgctx_loc = build_alloca_llvm_type (ctx, ctx->lmodule->ptr_type, sizeof (gpointer));
2181 LLVMBuildStore (builder, convert (ctx, ctx->values [call->imt_arg_reg], ctx->lmodule->ptr_type), ctx->imt_rgctx_loc);
2182 args [sinfo.imt_arg_pindex] = mono_llvm_build_load (builder, ctx->imt_rgctx_loc, "", TRUE, LLVM_BARRIER_NONE);
2184 args [sinfo.imt_arg_pindex] = convert (ctx, values [call->imt_arg_reg], ctx->lmodule->ptr_type);
2189 if (!addresses [call->inst.dreg])
2190 addresses [call->inst.dreg] = build_alloca (ctx, sig->ret);
2191 g_assert (sinfo.vret_arg_pindex < nargs);
2192 args [sinfo.vret_arg_pindex] = LLVMBuildPtrToInt (builder, addresses [call->inst.dreg], IntPtrType (), "");
2195 for (i = 0; i < sig->param_count + sig->hasthis; ++i) {
2198 LLVMArgInfo *ainfo = call->cinfo ? &call->cinfo->args [i] : NULL;
2202 pindex = sinfo.this_arg_pindex;
2204 pindex = sinfo.pindexes [i - 1];
2206 pindex = sinfo.pindexes [i];
2209 regpair = (guint32)(gssize)(l->data);
2210 reg = regpair & 0xffffff;
2211 args [pindex] = values [reg];
2212 if (ainfo->storage == LLVMArgVtypeInReg) {
2214 LLVMValueRef regs [2];
2219 g_assert (addresses [reg]);
2221 emit_vtype_to_reg (ctx, builder, sig->params [i - sig->hasthis], addresses [reg], ainfo, regs, &nregs);
2222 for (j = 0; j < nregs; ++j)
2223 args [pindex ++] = regs [j];
2226 // FIXME: Get rid of the VMOVE
2227 } else if (ainfo->storage == LLVMArgVtypeByVal) {
2228 g_assert (addresses [reg]);
2229 args [pindex] = addresses [reg];
2231 g_assert (args [pindex]);
2232 if (i == 0 && sig->hasthis)
2233 args [pindex] = convert (ctx, args [pindex], ThisType ());
2235 args [pindex] = convert (ctx, args [pindex], type_to_llvm_arg_type (ctx, sig->params [i - sig->hasthis]));
2241 // FIXME: Align call sites
2247 lcall = emit_call (ctx, bb, &builder, callee, args, LLVMCountParamTypes (llvm_sig));
2250 * Modify cconv and parameter attributes to pass rgctx/imt correctly.
2252 #if defined(MONO_ARCH_IMT_REG) && defined(MONO_ARCH_RGCTX_REG)
2253 g_assert (MONO_ARCH_IMT_REG == MONO_ARCH_RGCTX_REG);
2255 /* The two can't be used together, so use only one LLVM calling conv to pass them */
2256 g_assert (!(call->rgctx_arg_reg && call->imt_arg_reg));
2258 LLVMSetInstructionCallConv (lcall, LLVMMono1CallConv);
2260 if (call->rgctx_arg_reg)
2261 LLVMAddInstrAttribute (lcall, 1 + sinfo.rgctx_arg_pindex, LLVMInRegAttribute);
2262 if (call->imt_arg_reg)
2263 LLVMAddInstrAttribute (lcall, 1 + sinfo.imt_arg_pindex, LLVMInRegAttribute);
2265 /* Add byval attributes if needed */
2266 for (i = 0; i < sig->param_count; ++i) {
2267 LLVMArgInfo *ainfo = call->cinfo ? &call->cinfo->args [i + sig->hasthis] : NULL;
2269 if (ainfo && ainfo->storage == LLVMArgVtypeByVal) {
2270 LLVMAddInstrAttribute (lcall, 1 + sinfo.pindexes [i], LLVMByValAttribute);
2275 * Convert the result
2277 if (cinfo && cinfo->ret.storage == LLVMArgVtypeInReg) {
2278 LLVMValueRef regs [2];
2280 if (!addresses [ins->dreg])
2281 addresses [ins->dreg] = build_alloca (ctx, sig->ret);
2283 regs [0] = LLVMBuildExtractValue (builder, lcall, 0, "");
2284 if (cinfo->ret.pair_storage [1] != LLVMArgNone)
2285 regs [1] = LLVMBuildExtractValue (builder, lcall, 1, "");
2287 emit_reg_to_vtype (ctx, builder, sig->ret, addresses [ins->dreg], &cinfo->ret, regs);
2288 } else if (sig->ret->type != MONO_TYPE_VOID && !vretaddr) {
2289 /* If the method returns an unsigned value, need to zext it */
2291 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));
2294 *builder_ref = ctx->builder;
2296 g_free (sinfo.pindexes);
2304 process_bb (EmitContext *ctx, MonoBasicBlock *bb)
2306 MonoCompile *cfg = ctx->cfg;
2307 MonoMethodSignature *sig = ctx->sig;
2308 LLVMValueRef method = ctx->lmethod;
2309 LLVMValueRef *values = ctx->values;
2310 LLVMValueRef *addresses = ctx->addresses;
2312 LLVMCallInfo *linfo = ctx->linfo;
2313 LLVMModuleRef module = ctx->module;
2314 BBInfo *bblocks = ctx->bblocks;
2316 LLVMBasicBlockRef cbb;
2317 LLVMBuilderRef builder, starting_builder;
2318 gboolean has_terminator;
2320 LLVMValueRef lhs, rhs;
2323 cbb = get_bb (ctx, bb);
2324 builder = create_builder (ctx);
2325 ctx->builder = builder;
2326 LLVMPositionBuilderAtEnd (builder, cbb);
2328 if (bb == cfg->bb_entry)
2329 emit_entry_bb (ctx, builder);
2330 CHECK_FAILURE (ctx);
2332 if (bb->flags & BB_EXCEPTION_HANDLER) {
2334 LLVMValueRef personality;
2335 LLVMBasicBlockRef target_bb;
2337 static gint32 mapping_inited;
2338 static int ti_generator;
2341 LLVMValueRef type_info;
2344 if (!bblocks [bb->block_num].invoke_target) {
2346 * LLVM asserts if llvm.eh.selector is called from a bblock which
2347 * doesn't have an invoke pointing at it.
2348 * Update: LLVM no longer asserts, but some tests in exceptions.exe now fail.
2350 LLVM_FAILURE (ctx, "handler without invokes");
2353 // <resultval> = landingpad <somety> personality <type> <pers_fn> <clause>+
2355 if (cfg->compile_aot) {
2356 /* Use a dummy personality function */
2357 personality = LLVMGetNamedFunction (module, "mono_aot_personality");
2358 g_assert (personality);
2360 personality = LLVMGetNamedFunction (module, "mono_personality");
2361 if (InterlockedCompareExchange (&mapping_inited, 1, 0) == 0)
2362 LLVMAddGlobalMapping (ctx->lmodule->ee, personality, mono_personality);
2365 i8ptr = LLVMPointerType (LLVMInt8Type (), 0);
2367 clause_index = (mono_get_block_region_notry (cfg, bb->region) >> 8) - 1;
2370 * Create the type info
2372 sprintf (ti_name, "type_info_%d", ti_generator);
2375 if (cfg->compile_aot) {
2376 /* decode_eh_frame () in aot-runtime.c will decode this */
2377 type_info = LLVMAddGlobal (module, LLVMInt32Type (), ti_name);
2378 LLVMSetInitializer (type_info, LLVMConstInt (LLVMInt32Type (), clause_index, FALSE));
2381 * These symbols are not really used, the clause_index is embedded into the EH tables generated by DwarfMonoException in LLVM.
2383 LLVMSetLinkage (type_info, LLVMInternalLinkage);
2386 * Enabling this causes llc to crash:
2387 * http://llvm.org/bugs/show_bug.cgi?id=6102
2389 //LLVM_FAILURE (ctx, "aot+clauses");
2391 // test_0_invalid_unbox_arrays () fails
2392 LLVM_FAILURE (ctx, "aot+clauses");
2396 * After the cfg mempool is freed, the type info will point to stale memory,
2397 * but this is not a problem, since we decode it once in exception_cb during
2400 ti = mono_mempool_alloc (cfg->mempool, sizeof (gint32));
2401 *(gint32*)ti = clause_index;
2403 type_info = LLVMAddGlobal (module, i8ptr, ti_name);
2405 LLVMAddGlobalMapping (ctx->lmodule->ee, type_info, ti);
2409 LLVMTypeRef members [2], ret_type;
2410 LLVMValueRef landing_pad;
2412 members [0] = i8ptr;
2413 members [1] = LLVMInt32Type ();
2414 ret_type = LLVMStructType (members, 2, FALSE);
2416 landing_pad = LLVMBuildLandingPad (builder, ret_type, personality, 1, "");
2417 LLVMAddClause (landing_pad, type_info);
2419 /* Store the exception into the exvar */
2420 if (bb->in_scount == 1) {
2421 g_assert (bb->in_scount == 1);
2422 exvar = bb->in_stack [0];
2424 // FIXME: This is shared with filter clauses ?
2425 g_assert (!values [exvar->dreg]);
2427 values [exvar->dreg] = LLVMBuildExtractValue (builder, landing_pad, 0, "ex_obj");
2428 emit_volatile_store (ctx, exvar->dreg);
2432 /* Start a new bblock which CALL_HANDLER can branch to */
2433 target_bb = bblocks [bb->block_num].call_handler_target_bb;
2435 LLVMBuildBr (builder, target_bb);
2437 ctx->builder = builder = create_builder (ctx);
2438 LLVMPositionBuilderAtEnd (ctx->builder, target_bb);
2440 ctx->bblocks [bb->block_num].end_bblock = target_bb;
2444 has_terminator = FALSE;
2445 starting_builder = builder;
2446 for (ins = bb->code; ins; ins = ins->next) {
2447 const char *spec = LLVM_INS_INFO (ins->opcode);
2449 char dname_buf [128];
2451 emit_dbg_loc (ctx, builder, ins->cil_code);
2454 if (nins > 5000 && builder == starting_builder) {
2455 /* some steps in llc are non-linear in the size of basic blocks, see #5714 */
2456 LLVM_FAILURE (ctx, "basic block too long");
2460 /* There could be instructions after a terminator, skip them */
2463 if (spec [MONO_INST_DEST] != ' ' && !MONO_IS_STORE_MEMBASE (ins)) {
2464 sprintf (dname_buf, "t%d", ins->dreg);
2468 if (spec [MONO_INST_SRC1] != ' ' && spec [MONO_INST_SRC1] != 'v') {
2469 MonoInst *var = get_vreg_to_inst (cfg, ins->sreg1);
2471 if (var && var->flags & (MONO_INST_VOLATILE|MONO_INST_INDIRECT)) {
2472 lhs = emit_volatile_load (ctx, ins->sreg1);
2474 /* It is ok for SETRET to have an uninitialized argument */
2475 if (!values [ins->sreg1] && ins->opcode != OP_SETRET)
2476 LLVM_FAILURE (ctx, "sreg1");
2477 lhs = values [ins->sreg1];
2483 if (spec [MONO_INST_SRC2] != ' ' && spec [MONO_INST_SRC2] != ' ') {
2484 MonoInst *var = get_vreg_to_inst (cfg, ins->sreg2);
2485 if (var && var->flags & (MONO_INST_VOLATILE|MONO_INST_INDIRECT)) {
2486 rhs = emit_volatile_load (ctx, ins->sreg2);
2488 if (!values [ins->sreg2])
2489 LLVM_FAILURE (ctx, "sreg2");
2490 rhs = values [ins->sreg2];
2496 //mono_print_ins (ins);
2497 switch (ins->opcode) {
2500 case OP_LIVERANGE_START:
2501 case OP_LIVERANGE_END:
2504 values [ins->dreg] = LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE);
2507 #if SIZEOF_VOID_P == 4
2508 values [ins->dreg] = LLVMConstInt (LLVMInt64Type (), GET_LONG_IMM (ins), FALSE);
2510 values [ins->dreg] = LLVMConstInt (LLVMInt64Type (), (gint64)ins->inst_c0, FALSE);
2514 values [ins->dreg] = LLVMConstReal (LLVMDoubleType (), *(double*)ins->inst_p0);
2517 values [ins->dreg] = LLVMConstFPExt (LLVMConstReal (LLVMFloatType (), *(float*)ins->inst_p0), LLVMDoubleType ());
2519 case OP_DUMMY_ICONST:
2520 values [ins->dreg] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
2522 case OP_DUMMY_I8CONST:
2523 values [ins->dreg] = LLVMConstInt (LLVMInt64Type (), 0, FALSE);
2525 case OP_DUMMY_R8CONST:
2526 values [ins->dreg] = LLVMConstReal (LLVMDoubleType (), 0.0f);
2529 LLVMBuildBr (builder, get_bb (ctx, ins->inst_target_bb));
2530 has_terminator = TRUE;
2536 LLVMBasicBlockRef new_bb;
2537 LLVMBuilderRef new_builder;
2539 // The default branch is already handled
2540 // FIXME: Handle it here
2542 /* Start new bblock */
2543 sprintf (bb_name, "SWITCH_DEFAULT_BB%d", ctx->default_index ++);
2544 new_bb = LLVMAppendBasicBlock (ctx->lmethod, bb_name);
2546 lhs = convert (ctx, lhs, LLVMInt32Type ());
2547 v = LLVMBuildSwitch (builder, lhs, new_bb, GPOINTER_TO_UINT (ins->klass));
2548 for (i = 0; i < GPOINTER_TO_UINT (ins->klass); ++i) {
2549 MonoBasicBlock *target_bb = ins->inst_many_bb [i];
2551 LLVMAddCase (v, LLVMConstInt (LLVMInt32Type (), i, FALSE), get_bb (ctx, target_bb));
2554 new_builder = create_builder (ctx);
2555 LLVMPositionBuilderAtEnd (new_builder, new_bb);
2556 LLVMBuildUnreachable (new_builder);
2558 has_terminator = TRUE;
2559 g_assert (!ins->next);
2565 if (linfo->ret.storage == LLVMArgVtypeInReg) {
2566 LLVMTypeRef ret_type = LLVMGetReturnType (LLVMGetElementType (LLVMTypeOf (method)));
2567 LLVMValueRef part1, retval;
2570 size = get_vtype_size (sig->ret);
2572 g_assert (addresses [ins->sreg1]);
2574 g_assert (linfo->ret.pair_storage [0] == LLVMArgInIReg);
2575 g_assert (linfo->ret.pair_storage [1] == LLVMArgNone);
2577 part1 = convert (ctx, LLVMBuildLoad (builder, LLVMBuildBitCast (builder, addresses [ins->sreg1], LLVMPointerType (LLVMIntType (size * 8), 0), ""), ""), IntPtrType ());
2579 retval = LLVMBuildInsertValue (builder, LLVMGetUndef (ret_type), part1, 0, "");
2581 LLVMBuildRet (builder, retval);
2585 if (linfo->ret.storage == LLVMArgVtypeRetAddr) {
2586 LLVMBuildRetVoid (builder);
2590 if (!lhs || ctx->is_dead [ins->sreg1]) {
2592 * The method did not set its return value, probably because it
2593 * ends with a throw.
2596 LLVMBuildRetVoid (builder);
2598 LLVMBuildRet (builder, LLVMConstNull (type_to_llvm_type (ctx, sig->ret)));
2600 LLVMBuildRet (builder, convert (ctx, lhs, type_to_llvm_type (ctx, sig->ret)));
2602 has_terminator = TRUE;
2608 case OP_ICOMPARE_IMM:
2609 case OP_LCOMPARE_IMM:
2610 case OP_COMPARE_IMM: {
2614 if (ins->next->opcode == OP_NOP)
2617 if (ins->next->opcode == OP_BR)
2618 /* The comparison result is not needed */
2621 rel = mono_opcode_to_cond (ins->next->opcode);
2623 if (ins->opcode == OP_ICOMPARE_IMM) {
2624 lhs = convert (ctx, lhs, LLVMInt32Type ());
2625 rhs = LLVMConstInt (LLVMInt32Type (), ins->inst_imm, FALSE);
2627 if (ins->opcode == OP_LCOMPARE_IMM) {
2628 lhs = convert (ctx, lhs, LLVMInt64Type ());
2629 rhs = LLVMConstInt (LLVMInt64Type (), GET_LONG_IMM (ins), FALSE);
2631 if (ins->opcode == OP_LCOMPARE) {
2632 lhs = convert (ctx, lhs, LLVMInt64Type ());
2633 rhs = convert (ctx, rhs, LLVMInt64Type ());
2635 if (ins->opcode == OP_ICOMPARE) {
2636 lhs = convert (ctx, lhs, LLVMInt32Type ());
2637 rhs = convert (ctx, rhs, LLVMInt32Type ());
2641 if (LLVMGetTypeKind (LLVMTypeOf (lhs)) == LLVMPointerTypeKind)
2642 rhs = convert (ctx, rhs, LLVMTypeOf (lhs));
2643 else if (LLVMGetTypeKind (LLVMTypeOf (rhs)) == LLVMPointerTypeKind)
2644 lhs = convert (ctx, lhs, LLVMTypeOf (rhs));
2647 /* We use COMPARE+SETcc/Bcc, llvm uses SETcc+br cond */
2648 if (ins->opcode == OP_FCOMPARE)
2649 cmp = LLVMBuildFCmp (builder, fpcond_to_llvm_cond [rel], convert (ctx, lhs, LLVMDoubleType ()), convert (ctx, rhs, LLVMDoubleType ()), "");
2650 else if (ins->opcode == OP_COMPARE_IMM) {
2651 if (LLVMGetTypeKind (LLVMTypeOf (lhs)) == LLVMPointerTypeKind && ins->inst_imm == 0)
2652 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], lhs, LLVMConstNull (LLVMTypeOf (lhs)), "");
2654 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], convert (ctx, lhs, IntPtrType ()), LLVMConstInt (IntPtrType (), ins->inst_imm, FALSE), "");
2655 } else if (ins->opcode == OP_LCOMPARE_IMM) {
2656 if (SIZEOF_REGISTER == 4 && COMPILE_LLVM (cfg)) {
2657 /* The immediate is encoded in two fields */
2658 guint64 l = ((guint64)(guint32)ins->inst_offset << 32) | ((guint32)ins->inst_imm);
2659 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], convert (ctx, lhs, LLVMInt64Type ()), LLVMConstInt (LLVMInt64Type (), l, FALSE), "");
2661 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], convert (ctx, lhs, LLVMInt64Type ()), LLVMConstInt (LLVMInt64Type (), ins->inst_imm, FALSE), "");
2664 else if (ins->opcode == OP_COMPARE) {
2665 if (LLVMGetTypeKind (LLVMTypeOf (lhs)) == LLVMPointerTypeKind && LLVMTypeOf (lhs) == LLVMTypeOf (rhs))
2666 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], lhs, rhs, "");
2668 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], convert (ctx, lhs, IntPtrType ()), convert (ctx, rhs, IntPtrType ()), "");
2670 cmp = LLVMBuildICmp (builder, cond_to_llvm_cond [rel], lhs, rhs, "");
2672 if (MONO_IS_COND_BRANCH_OP (ins->next)) {
2673 if (ins->next->inst_true_bb == ins->next->inst_false_bb) {
2675 * If the target bb contains PHI instructions, LLVM requires
2676 * two PHI entries for this bblock, while we only generate one.
2677 * So convert this to an unconditional bblock. (bxc #171).
2679 LLVMBuildBr (builder, get_bb (ctx, ins->next->inst_true_bb));
2681 LLVMBuildCondBr (builder, cmp, get_bb (ctx, ins->next->inst_true_bb), get_bb (ctx, ins->next->inst_false_bb));
2683 has_terminator = TRUE;
2684 } else if (MONO_IS_SETCC (ins->next)) {
2685 sprintf (dname_buf, "t%d", ins->next->dreg);
2687 values [ins->next->dreg] = LLVMBuildZExt (builder, cmp, LLVMInt32Type (), dname);
2689 /* Add stores for volatile variables */
2690 emit_volatile_store (ctx, ins->next->dreg);
2691 } else if (MONO_IS_COND_EXC (ins->next)) {
2692 emit_cond_system_exception (ctx, bb, ins->next->inst_p1, cmp);
2693 CHECK_FAILURE (ctx);
2694 builder = ctx->builder;
2696 LLVM_FAILURE (ctx, "next");
2710 rel = mono_opcode_to_cond (ins->opcode);
2712 cmp = LLVMBuildFCmp (builder, fpcond_to_llvm_cond [rel], convert (ctx, lhs, LLVMDoubleType ()), convert (ctx, rhs, LLVMDoubleType ()), "");
2713 values [ins->dreg] = LLVMBuildZExt (builder, cmp, LLVMInt32Type (), dname);
2721 gboolean empty = TRUE;
2723 /* Check that all input bblocks really branch to us */
2724 for (i = 0; i < bb->in_count; ++i) {
2725 if (bb->in_bb [i]->last_ins && bb->in_bb [i]->last_ins->opcode == OP_NOT_REACHED)
2726 ins->inst_phi_args [i + 1] = -1;
2732 /* LLVM doesn't like phi instructions with zero operands */
2733 ctx->is_dead [ins->dreg] = TRUE;
2737 /* Created earlier, insert it now */
2738 LLVMInsertIntoBuilder (builder, values [ins->dreg]);
2740 for (i = 0; i < ins->inst_phi_args [0]; i++) {
2741 int sreg1 = ins->inst_phi_args [i + 1];
2745 * Count the number of times the incoming bblock branches to us,
2746 * since llvm requires a separate entry for each.
2748 if (bb->in_bb [i]->last_ins && bb->in_bb [i]->last_ins->opcode == OP_SWITCH) {
2749 MonoInst *switch_ins = bb->in_bb [i]->last_ins;
2752 for (j = 0; j < GPOINTER_TO_UINT (switch_ins->klass); ++j) {
2753 if (switch_ins->inst_many_bb [j] == bb)
2760 /* Remember for later */
2761 for (j = 0; j < count; ++j) {
2762 PhiNode *node = mono_mempool_alloc0 (ctx->mempool, sizeof (PhiNode));
2765 node->in_bb = bb->in_bb [i];
2767 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);
2777 values [ins->dreg] = lhs;
2780 MonoInst *var = get_vreg_to_inst (cfg, ins->dreg);
2783 values [ins->dreg] = lhs;
2785 if (var && var->klass->byval_arg.type == MONO_TYPE_R4) {
2787 * This is added by the spilling pass in case of the JIT,
2788 * but we have to do it ourselves.
2790 values [ins->dreg] = convert (ctx, values [ins->dreg], LLVMFloatType ());
2824 lhs = convert (ctx, lhs, regtype_to_llvm_type (spec [MONO_INST_DEST]));
2825 rhs = convert (ctx, rhs, regtype_to_llvm_type (spec [MONO_INST_DEST]));
2827 switch (ins->opcode) {
2830 values [ins->dreg] = LLVMBuildAdd (builder, lhs, rhs, dname);
2834 values [ins->dreg] = LLVMBuildSub (builder, lhs, rhs, dname);
2838 values [ins->dreg] = LLVMBuildMul (builder, lhs, rhs, dname);
2842 values [ins->dreg] = LLVMBuildSRem (builder, lhs, rhs, dname);
2846 values [ins->dreg] = LLVMBuildURem (builder, lhs, rhs, dname);
2850 values [ins->dreg] = LLVMBuildSDiv (builder, lhs, rhs, dname);
2854 values [ins->dreg] = LLVMBuildUDiv (builder, lhs, rhs, dname);
2857 values [ins->dreg] = LLVMBuildFDiv (builder, lhs, rhs, dname);
2861 values [ins->dreg] = LLVMBuildAnd (builder, lhs, rhs, dname);
2865 values [ins->dreg] = LLVMBuildOr (builder, lhs, rhs, dname);
2869 values [ins->dreg] = LLVMBuildXor (builder, lhs, rhs, dname);
2873 values [ins->dreg] = LLVMBuildShl (builder, lhs, rhs, dname);
2877 values [ins->dreg] = LLVMBuildAShr (builder, lhs, rhs, dname);
2881 values [ins->dreg] = LLVMBuildLShr (builder, lhs, rhs, dname);
2885 values [ins->dreg] = LLVMBuildFAdd (builder, lhs, rhs, dname);
2888 values [ins->dreg] = LLVMBuildFSub (builder, lhs, rhs, dname);
2891 values [ins->dreg] = LLVMBuildFMul (builder, lhs, rhs, dname);
2895 g_assert_not_reached ();
2902 case OP_IREM_UN_IMM:
2904 case OP_IDIV_UN_IMM:
2910 case OP_ISHR_UN_IMM:
2919 case OP_LSHR_UN_IMM:
2925 case OP_SHR_UN_IMM: {
2928 if (spec [MONO_INST_SRC1] == 'l') {
2929 imm = LLVMConstInt (LLVMInt64Type (), GET_LONG_IMM (ins), FALSE);
2931 imm = LLVMConstInt (LLVMInt32Type (), ins->inst_imm, FALSE);
2934 #if SIZEOF_VOID_P == 4
2935 if (ins->opcode == OP_LSHL_IMM || ins->opcode == OP_LSHR_IMM || ins->opcode == OP_LSHR_UN_IMM)
2936 imm = LLVMConstInt (LLVMInt32Type (), ins->inst_imm, FALSE);
2939 if (LLVMGetTypeKind (LLVMTypeOf (lhs)) == LLVMPointerTypeKind)
2940 lhs = convert (ctx, lhs, IntPtrType ());
2941 imm = convert (ctx, imm, LLVMTypeOf (lhs));
2942 switch (ins->opcode) {
2946 values [ins->dreg] = LLVMBuildAdd (builder, lhs, imm, dname);
2950 values [ins->dreg] = LLVMBuildSub (builder, lhs, imm, dname);
2954 values [ins->dreg] = LLVMBuildMul (builder, lhs, imm, dname);
2958 values [ins->dreg] = LLVMBuildSDiv (builder, lhs, imm, dname);
2960 case OP_IDIV_UN_IMM:
2961 case OP_LDIV_UN_IMM:
2962 values [ins->dreg] = LLVMBuildUDiv (builder, lhs, imm, dname);
2966 values [ins->dreg] = LLVMBuildSRem (builder, lhs, imm, dname);
2968 case OP_IREM_UN_IMM:
2969 values [ins->dreg] = LLVMBuildURem (builder, lhs, imm, dname);
2974 values [ins->dreg] = LLVMBuildAnd (builder, lhs, imm, dname);
2978 values [ins->dreg] = LLVMBuildOr (builder, lhs, imm, dname);
2982 values [ins->dreg] = LLVMBuildXor (builder, lhs, imm, dname);
2987 values [ins->dreg] = LLVMBuildShl (builder, lhs, imm, dname);
2992 values [ins->dreg] = LLVMBuildAShr (builder, lhs, imm, dname);
2994 case OP_ISHR_UN_IMM:
2995 /* This is used to implement conv.u4, so the lhs could be an i8 */
2996 lhs = convert (ctx, lhs, LLVMInt32Type ());
2997 imm = convert (ctx, imm, LLVMInt32Type ());
2998 values [ins->dreg] = LLVMBuildLShr (builder, lhs, imm, dname);
3000 case OP_LSHR_UN_IMM:
3002 values [ins->dreg] = LLVMBuildLShr (builder, lhs, imm, dname);
3005 g_assert_not_reached ();
3010 values [ins->dreg] = LLVMBuildSub (builder, LLVMConstInt (LLVMInt32Type (), 0, FALSE), convert (ctx, lhs, LLVMInt32Type ()), dname);
3013 values [ins->dreg] = LLVMBuildSub (builder, LLVMConstInt (LLVMInt64Type (), 0, FALSE), lhs, dname);
3016 lhs = convert (ctx, lhs, LLVMDoubleType ());
3017 values [ins->dreg] = LLVMBuildFSub (builder, LLVMConstReal (LLVMDoubleType (), 0.0), lhs, dname);
3020 guint32 v = 0xffffffff;
3021 values [ins->dreg] = LLVMBuildXor (builder, LLVMConstInt (LLVMInt32Type (), v, FALSE), convert (ctx, lhs, LLVMInt32Type ()), dname);
3025 guint64 v = 0xffffffffffffffffLL;
3026 values [ins->dreg] = LLVMBuildXor (builder, LLVMConstInt (LLVMInt64Type (), v, FALSE), lhs, dname);
3029 #if defined(TARGET_X86) || defined(TARGET_AMD64)
3031 LLVMValueRef v1, v2;
3033 v1 = LLVMBuildMul (builder, convert (ctx, rhs, IntPtrType ()), LLVMConstInt (IntPtrType (), (1 << ins->backend.shift_amount), FALSE), "");
3034 v2 = LLVMBuildAdd (builder, convert (ctx, lhs, IntPtrType ()), v1, "");
3035 values [ins->dreg] = LLVMBuildAdd (builder, v2, LLVMConstInt (IntPtrType (), ins->inst_imm, FALSE), dname);
3040 case OP_ICONV_TO_I1:
3041 case OP_ICONV_TO_I2:
3042 case OP_ICONV_TO_I4:
3043 case OP_ICONV_TO_U1:
3044 case OP_ICONV_TO_U2:
3045 case OP_ICONV_TO_U4:
3046 case OP_LCONV_TO_I1:
3047 case OP_LCONV_TO_I2:
3048 case OP_LCONV_TO_U1:
3049 case OP_LCONV_TO_U2:
3050 case OP_LCONV_TO_U4: {
3053 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);
3055 /* Have to do two casts since our vregs have type int */
3056 v = LLVMBuildTrunc (builder, lhs, op_to_llvm_type (ins->opcode), "");
3058 values [ins->dreg] = LLVMBuildSExt (builder, v, LLVMInt32Type (), dname);
3060 values [ins->dreg] = LLVMBuildZExt (builder, v, LLVMInt32Type (), dname);
3063 case OP_ICONV_TO_I8:
3064 values [ins->dreg] = LLVMBuildSExt (builder, lhs, LLVMInt64Type (), dname);
3066 case OP_ICONV_TO_U8:
3067 values [ins->dreg] = LLVMBuildZExt (builder, lhs, LLVMInt64Type (), dname);
3069 case OP_FCONV_TO_I4:
3070 values [ins->dreg] = LLVMBuildFPToSI (builder, lhs, LLVMInt32Type (), dname);
3072 case OP_FCONV_TO_I1:
3073 values [ins->dreg] = LLVMBuildSExt (builder, LLVMBuildFPToSI (builder, lhs, LLVMInt8Type (), dname), LLVMInt32Type (), "");
3075 case OP_FCONV_TO_U1:
3076 values [ins->dreg] = LLVMBuildZExt (builder, LLVMBuildFPToUI (builder, lhs, LLVMInt8Type (), dname), LLVMInt32Type (), "");
3078 case OP_FCONV_TO_I2:
3079 values [ins->dreg] = LLVMBuildSExt (builder, LLVMBuildFPToSI (builder, lhs, LLVMInt16Type (), dname), LLVMInt32Type (), "");
3081 case OP_FCONV_TO_U2:
3082 values [ins->dreg] = LLVMBuildZExt (builder, LLVMBuildFPToUI (builder, lhs, LLVMInt16Type (), dname), LLVMInt32Type (), "");
3084 case OP_FCONV_TO_I8:
3085 values [ins->dreg] = LLVMBuildFPToSI (builder, lhs, LLVMInt64Type (), dname);
3088 values [ins->dreg] = LLVMBuildFPToSI (builder, lhs, IntPtrType (), dname);
3090 case OP_ICONV_TO_R8:
3091 case OP_LCONV_TO_R8:
3092 values [ins->dreg] = LLVMBuildSIToFP (builder, lhs, LLVMDoubleType (), dname);
3094 case OP_LCONV_TO_R_UN:
3095 values [ins->dreg] = LLVMBuildUIToFP (builder, lhs, LLVMDoubleType (), dname);
3097 #if SIZEOF_VOID_P == 4
3100 case OP_LCONV_TO_I4:
3101 values [ins->dreg] = LLVMBuildTrunc (builder, lhs, LLVMInt32Type (), dname);
3103 case OP_ICONV_TO_R4:
3104 case OP_LCONV_TO_R4:
3105 v = LLVMBuildSIToFP (builder, lhs, LLVMFloatType (), "");
3106 values [ins->dreg] = LLVMBuildFPExt (builder, v, LLVMDoubleType (), dname);
3108 case OP_FCONV_TO_R4:
3109 v = LLVMBuildFPTrunc (builder, lhs, LLVMFloatType (), "");
3110 values [ins->dreg] = LLVMBuildFPExt (builder, v, LLVMDoubleType (), dname);
3113 values [ins->dreg] = LLVMBuildSExt (builder, convert (ctx, lhs, LLVMInt32Type ()), LLVMInt64Type (), dname);
3116 values [ins->dreg] = LLVMBuildZExt (builder, convert (ctx, lhs, LLVMInt32Type ()), LLVMInt64Type (), dname);
3119 values [ins->dreg] = LLVMBuildTrunc (builder, lhs, LLVMInt32Type (), dname);
3121 case OP_LOCALLOC_IMM: {
3124 guint32 size = ins->inst_imm;
3125 size = (size + (MONO_ARCH_FRAME_ALIGNMENT - 1)) & ~ (MONO_ARCH_FRAME_ALIGNMENT - 1);
3127 v = mono_llvm_build_alloca (builder, LLVMInt8Type (), LLVMConstInt (LLVMInt32Type (), size, FALSE), MONO_ARCH_FRAME_ALIGNMENT, "");
3129 if (ins->flags & MONO_INST_INIT) {
3130 LLVMValueRef args [5];
3133 args [1] = LLVMConstInt (LLVMInt8Type (), 0, FALSE);
3134 args [2] = LLVMConstInt (LLVMInt32Type (), size, FALSE);
3135 args [3] = LLVMConstInt (LLVMInt32Type (), MONO_ARCH_FRAME_ALIGNMENT, FALSE);
3136 args [4] = LLVMConstInt (LLVMInt1Type (), 0, FALSE);
3137 LLVMBuildCall (builder, LLVMGetNamedFunction (module, memset_func_name), args, memset_param_count, "");
3140 values [ins->dreg] = v;
3144 LLVMValueRef v, size;
3146 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), "");
3148 v = mono_llvm_build_alloca (builder, LLVMInt8Type (), size, MONO_ARCH_FRAME_ALIGNMENT, "");
3150 if (ins->flags & MONO_INST_INIT) {
3151 LLVMValueRef args [5];
3154 args [1] = LLVMConstInt (LLVMInt8Type (), 0, FALSE);
3156 args [3] = LLVMConstInt (LLVMInt32Type (), MONO_ARCH_FRAME_ALIGNMENT, FALSE);
3157 args [4] = LLVMConstInt (LLVMInt1Type (), 0, FALSE);
3158 LLVMBuildCall (builder, LLVMGetNamedFunction (module, memset_func_name), args, memset_param_count, "");
3160 values [ins->dreg] = v;
3164 case OP_LOADI1_MEMBASE:
3165 case OP_LOADU1_MEMBASE:
3166 case OP_LOADI2_MEMBASE:
3167 case OP_LOADU2_MEMBASE:
3168 case OP_LOADI4_MEMBASE:
3169 case OP_LOADU4_MEMBASE:
3170 case OP_LOADI8_MEMBASE:
3171 case OP_LOADR4_MEMBASE:
3172 case OP_LOADR8_MEMBASE:
3173 case OP_LOAD_MEMBASE:
3181 LLVMValueRef base, index, addr;
3183 gboolean sext = FALSE, zext = FALSE;
3184 gboolean is_volatile = (ins->flags & MONO_INST_FAULT);
3186 t = load_store_to_llvm_type (ins->opcode, &size, &sext, &zext);
3191 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)) {
3192 addr = LLVMConstInt (IntPtrType (), ins->inst_imm, FALSE);
3197 if (ins->inst_offset == 0) {
3199 } else if (ins->inst_offset % size != 0) {
3200 /* Unaligned load */
3201 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset, FALSE);
3202 addr = LLVMBuildGEP (builder, convert (ctx, base, LLVMPointerType (LLVMInt8Type (), 0)), &index, 1, "");
3204 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset / size, FALSE);
3205 addr = LLVMBuildGEP (builder, convert (ctx, base, LLVMPointerType (t, 0)), &index, 1, "");
3209 addr = convert (ctx, addr, LLVMPointerType (t, 0));
3211 values [ins->dreg] = emit_load (ctx, bb, &builder, size, addr, dname, is_volatile);
3213 if (!is_volatile && (ins->flags & MONO_INST_INVARIANT_LOAD)) {
3215 * These will signal LLVM that these loads do not alias any stores, and
3216 * they can't fail, allowing them to be hoisted out of loops.
3218 set_invariant_load_flag (values [ins->dreg]);
3219 set_metadata_flag (values [ins->dreg], "mono.nofail.load");
3223 values [ins->dreg] = LLVMBuildSExt (builder, values [ins->dreg], LLVMInt32Type (), dname);
3225 values [ins->dreg] = LLVMBuildZExt (builder, values [ins->dreg], LLVMInt32Type (), dname);
3226 else if (ins->opcode == OP_LOADR4_MEMBASE)
3227 values [ins->dreg] = LLVMBuildFPExt (builder, values [ins->dreg], LLVMDoubleType (), dname);
3231 case OP_STOREI1_MEMBASE_REG:
3232 case OP_STOREI2_MEMBASE_REG:
3233 case OP_STOREI4_MEMBASE_REG:
3234 case OP_STOREI8_MEMBASE_REG:
3235 case OP_STORER4_MEMBASE_REG:
3236 case OP_STORER8_MEMBASE_REG:
3237 case OP_STORE_MEMBASE_REG: {
3239 LLVMValueRef index, addr;
3241 gboolean sext = FALSE, zext = FALSE;
3242 gboolean is_volatile = (ins->flags & MONO_INST_FAULT);
3244 if (!values [ins->inst_destbasereg])
3245 LLVM_FAILURE (ctx, "inst_destbasereg");
3247 t = load_store_to_llvm_type (ins->opcode, &size, &sext, &zext);
3249 if (ins->inst_offset % size != 0) {
3250 /* Unaligned store */
3251 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset, FALSE);
3252 addr = LLVMBuildGEP (builder, convert (ctx, values [ins->inst_destbasereg], LLVMPointerType (LLVMInt8Type (), 0)), &index, 1, "");
3254 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset / size, FALSE);
3255 addr = LLVMBuildGEP (builder, convert (ctx, values [ins->inst_destbasereg], LLVMPointerType (t, 0)), &index, 1, "");
3257 emit_store (ctx, bb, &builder, size, convert (ctx, values [ins->sreg1], t), convert (ctx, addr, LLVMPointerType (t, 0)), is_volatile);
3261 case OP_STOREI1_MEMBASE_IMM:
3262 case OP_STOREI2_MEMBASE_IMM:
3263 case OP_STOREI4_MEMBASE_IMM:
3264 case OP_STOREI8_MEMBASE_IMM:
3265 case OP_STORE_MEMBASE_IMM: {
3267 LLVMValueRef index, addr;
3269 gboolean sext = FALSE, zext = FALSE;
3270 gboolean is_volatile = (ins->flags & MONO_INST_FAULT);
3272 t = load_store_to_llvm_type (ins->opcode, &size, &sext, &zext);
3274 if (ins->inst_offset % size != 0) {
3275 /* Unaligned store */
3276 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset, FALSE);
3277 addr = LLVMBuildGEP (builder, convert (ctx, values [ins->inst_destbasereg], LLVMPointerType (LLVMInt8Type (), 0)), &index, 1, "");
3279 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset / size, FALSE);
3280 addr = LLVMBuildGEP (builder, convert (ctx, values [ins->inst_destbasereg], LLVMPointerType (t, 0)), &index, 1, "");
3282 emit_store (ctx, bb, &builder, size, convert (ctx, LLVMConstInt (IntPtrType (), ins->inst_imm, FALSE), t), convert (ctx, addr, LLVMPointerType (t, 0)), is_volatile);
3287 emit_load (ctx, bb, &builder, sizeof (gpointer), convert (ctx, lhs, LLVMPointerType (IntPtrType (), 0)), "", TRUE);
3289 case OP_OUTARG_VTRETADDR:
3296 case OP_VOIDCALL_MEMBASE:
3297 case OP_CALL_MEMBASE:
3298 case OP_LCALL_MEMBASE:
3299 case OP_FCALL_MEMBASE:
3300 case OP_VCALL_MEMBASE:
3301 case OP_VOIDCALL_REG:
3305 case OP_VCALL_REG: {
3306 process_call (ctx, bb, &builder, ins);
3307 CHECK_FAILURE (ctx);
3312 LLVMValueRef indexes [2];
3314 LLVMValueRef got_entry_addr;
3317 * FIXME: Can't allocate from the cfg mempool since that is freed if
3318 * the LLVM compile fails.
3320 ji = g_new0 (MonoJumpInfo, 1);
3321 ji->type = (MonoJumpInfoType)ins->inst_i1;
3322 ji->data.target = ins->inst_p0;
3324 ji = mono_aot_patch_info_dup (ji);
3326 ji->next = cfg->patch_info;
3327 cfg->patch_info = ji;
3329 //mono_add_patch_info (cfg, 0, (MonoJumpInfoType)ins->inst_i1, ins->inst_p0);
3330 got_offset = mono_aot_get_got_offset (cfg->patch_info);
3331 ctx->lmodule->max_got_offset = MAX (ctx->lmodule->max_got_offset, got_offset);
3333 indexes [0] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
3334 indexes [1] = LLVMConstInt (LLVMInt32Type (), (gssize)got_offset, FALSE);
3335 got_entry_addr = LLVMBuildGEP (builder, ctx->lmodule->got_var, indexes, 2, "");
3337 values [ins->dreg] = LLVMBuildLoad (builder, got_entry_addr, dname);
3338 set_invariant_load_flag (values [ins->dreg]);
3341 case OP_NOT_REACHED:
3342 LLVMBuildUnreachable (builder);
3343 has_terminator = TRUE;
3344 g_assert (bb->block_num < cfg->max_block_num);
3345 ctx->unreachable [bb->block_num] = TRUE;
3346 /* Might have instructions after this */
3348 MonoInst *next = ins->next;
3350 * FIXME: If later code uses the regs defined by these instructions,
3351 * compilation will fail.
3353 MONO_DELETE_INS (bb, next);
3357 MonoInst *var = ins->inst_p0;
3359 values [ins->dreg] = addresses [var->dreg];
3363 LLVMValueRef args [1];
3365 args [0] = convert (ctx, lhs, LLVMDoubleType ());
3366 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, "llvm.sin.f64"), args, 1, dname);
3370 LLVMValueRef args [1];
3372 args [0] = convert (ctx, lhs, LLVMDoubleType ());
3373 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, "llvm.cos.f64"), args, 1, dname);
3377 LLVMValueRef args [1];
3380 /* This no longer seems to happen */
3382 * LLVM optimizes sqrt(nan) into undefined in
3383 * lib/Analysis/ConstantFolding.cpp
3384 * Also, sqrt(NegativeInfinity) is optimized into 0.
3386 LLVM_FAILURE (ctx, "sqrt");
3388 args [0] = convert (ctx, lhs, LLVMDoubleType ());
3389 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, "llvm.sqrt.f64"), args, 1, dname);
3393 LLVMValueRef args [1];
3395 args [0] = convert (ctx, lhs, LLVMDoubleType ());
3396 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, "fabs"), args, 1, dname);
3410 lhs = convert (ctx, lhs, regtype_to_llvm_type (spec [MONO_INST_DEST]));
3411 rhs = convert (ctx, rhs, regtype_to_llvm_type (spec [MONO_INST_DEST]));
3413 switch (ins->opcode) {
3416 v = LLVMBuildICmp (builder, LLVMIntSLE, lhs, rhs, "");
3420 v = LLVMBuildICmp (builder, LLVMIntSGE, lhs, rhs, "");
3424 v = LLVMBuildICmp (builder, LLVMIntULE, lhs, rhs, "");
3428 v = LLVMBuildICmp (builder, LLVMIntUGE, lhs, rhs, "");
3431 g_assert_not_reached ();
3434 values [ins->dreg] = LLVMBuildSelect (builder, v, lhs, rhs, dname);
3437 case OP_ATOMIC_EXCHANGE_I4:
3438 case OP_ATOMIC_EXCHANGE_I8: {
3439 LLVMValueRef args [2];
3442 if (ins->opcode == OP_ATOMIC_EXCHANGE_I4)
3443 t = LLVMInt32Type ();
3445 t = LLVMInt64Type ();
3447 g_assert (ins->inst_offset == 0);
3449 args [0] = convert (ctx, lhs, LLVMPointerType (t, 0));
3450 args [1] = convert (ctx, rhs, t);
3452 values [ins->dreg] = mono_llvm_build_atomic_rmw (builder, LLVM_ATOMICRMW_OP_XCHG, args [0], args [1]);
3455 case OP_ATOMIC_ADD_I4:
3456 case OP_ATOMIC_ADD_I8: {
3457 LLVMValueRef args [2];
3460 if (ins->opcode == OP_ATOMIC_ADD_I4)
3461 t = LLVMInt32Type ();
3463 t = LLVMInt64Type ();
3465 g_assert (ins->inst_offset == 0);
3467 args [0] = convert (ctx, lhs, LLVMPointerType (t, 0));
3468 args [1] = convert (ctx, rhs, t);
3469 values [ins->dreg] = LLVMBuildAdd (builder, mono_llvm_build_atomic_rmw (builder, LLVM_ATOMICRMW_OP_ADD, args [0], args [1]), args [1], dname);
3472 case OP_ATOMIC_CAS_I4:
3473 case OP_ATOMIC_CAS_I8: {
3474 LLVMValueRef args [3], val;
3477 if (ins->opcode == OP_ATOMIC_CAS_I4)
3478 t = LLVMInt32Type ();
3480 t = LLVMInt64Type ();
3482 args [0] = convert (ctx, lhs, LLVMPointerType (t, 0));
3484 args [1] = convert (ctx, values [ins->sreg3], t);
3486 args [2] = convert (ctx, values [ins->sreg2], t);
3487 val = mono_llvm_build_cmpxchg (builder, args [0], args [1], args [2]);
3488 #if LLVM_API_VERSION >= 1
3489 /* cmpxchg returns a pair */
3490 values [ins->dreg] = LLVMBuildExtractValue (builder, val, 0, "");
3492 values [ins->dreg] = val;
3496 case OP_MEMORY_BARRIER: {
3497 mono_llvm_build_fence (builder, (BarrierKind) ins->backend.memory_barrier_kind);
3500 case OP_ATOMIC_LOAD_I1:
3501 case OP_ATOMIC_LOAD_I2:
3502 case OP_ATOMIC_LOAD_I4:
3503 case OP_ATOMIC_LOAD_I8:
3504 case OP_ATOMIC_LOAD_U1:
3505 case OP_ATOMIC_LOAD_U2:
3506 case OP_ATOMIC_LOAD_U4:
3507 case OP_ATOMIC_LOAD_U8:
3508 case OP_ATOMIC_LOAD_R4:
3509 case OP_ATOMIC_LOAD_R8: {
3510 #if LLVM_API_VERSION >= 4
3512 gboolean sext, zext;
3514 gboolean is_volatile = (ins->flags & MONO_INST_FAULT);
3515 BarrierKind barrier = (BarrierKind) ins->backend.memory_barrier_kind;
3516 LLVMValueRef index, addr;
3518 t = load_store_to_llvm_type (ins->opcode, &size, &sext, &zext);
3523 if (ins->inst_offset != 0) {
3524 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset / size, FALSE);
3525 addr = LLVMBuildGEP (builder, convert (ctx, lhs, LLVMPointerType (t, 0)), &index, 1, "");
3530 addr = convert (ctx, addr, LLVMPointerType (t, 0));
3532 values [ins->dreg] = emit_load_general (ctx, bb, &builder, size, addr, dname, is_volatile, barrier);
3535 values [ins->dreg] = LLVMBuildSExt (builder, values [ins->dreg], LLVMInt32Type (), dname);
3537 values [ins->dreg] = LLVMBuildZExt (builder, values [ins->dreg], LLVMInt32Type (), dname);
3539 LLVM_FAILURE (ctx, "atomic mono.load intrinsic");
3543 case OP_ATOMIC_STORE_I1:
3544 case OP_ATOMIC_STORE_I2:
3545 case OP_ATOMIC_STORE_I4:
3546 case OP_ATOMIC_STORE_I8:
3547 case OP_ATOMIC_STORE_U1:
3548 case OP_ATOMIC_STORE_U2:
3549 case OP_ATOMIC_STORE_U4:
3550 case OP_ATOMIC_STORE_U8:
3551 case OP_ATOMIC_STORE_R4:
3552 case OP_ATOMIC_STORE_R8: {
3553 #if LLVM_API_VERSION >= 4
3555 gboolean sext, zext;
3557 gboolean is_volatile = (ins->flags & MONO_INST_FAULT);
3558 BarrierKind barrier = (BarrierKind) ins->backend.memory_barrier_kind;
3559 LLVMValueRef index, addr, value;
3561 if (!values [ins->inst_destbasereg])
3562 LLVM_FAILURE (ctx, "inst_destbasereg");
3564 t = load_store_to_llvm_type (ins->opcode, &size, &sext, &zext);
3566 index = LLVMConstInt (LLVMInt32Type (), ins->inst_offset / size, FALSE);
3567 addr = LLVMBuildGEP (builder, convert (ctx, values [ins->inst_destbasereg], LLVMPointerType (t, 0)), &index, 1, "");
3568 value = convert (ctx, values [ins->sreg1], t);
3570 emit_store_general (ctx, bb, &builder, size, value, addr, is_volatile, barrier);
3573 LLVM_FAILURE (ctx, "atomic mono.store intrinsic");
3577 case OP_RELAXED_NOP: {
3578 #if defined(TARGET_AMD64) || defined(TARGET_X86)
3579 emit_call (ctx, bb, &builder, LLVMGetNamedFunction (ctx->module, "llvm.x86.sse2.pause"), NULL, 0);
3586 #if (defined(TARGET_AMD64) || defined(TARGET_X86)) && defined(__linux__)
3588 // 257 == FS segment register
3589 LLVMTypeRef ptrtype = LLVMPointerType (IntPtrType (), 257);
3591 // 256 == GS segment register
3592 LLVMTypeRef ptrtype = LLVMPointerType (IntPtrType (), 256);
3595 values [ins->dreg] = LLVMBuildLoad (builder, LLVMBuildIntToPtr (builder, LLVMConstInt (IntPtrType (), ins->inst_offset, TRUE), ptrtype, ""), "");
3596 #elif defined(TARGET_AMD64) && defined(TARGET_OSX)
3597 /* See mono_amd64_emit_tls_get () */
3598 int offset = mono_amd64_get_tls_gs_offset () + (ins->inst_offset * 8);
3600 // 256 == GS segment register
3601 LLVMTypeRef ptrtype = LLVMPointerType (IntPtrType (), 256);
3602 values [ins->dreg] = LLVMBuildLoad (builder, LLVMBuildIntToPtr (builder, LLVMConstInt (IntPtrType (), offset, TRUE), ptrtype, ""), "");
3604 LLVM_FAILURE (ctx, "opcode tls-get");
3609 case OP_TLS_GET_REG: {
3610 #if defined(TARGET_AMD64) && defined(TARGET_OSX)
3611 /* See emit_tls_get_reg () */
3612 // 256 == GS segment register
3613 LLVMTypeRef ptrtype = LLVMPointerType (IntPtrType (), 256);
3614 values [ins->dreg] = LLVMBuildLoad (builder, LLVMBuildIntToPtr (builder, convert (ctx, lhs, LLVMInt32Type ()), ptrtype, ""), "");
3616 LLVM_FAILURE (ctx, "opcode tls-get");
3625 case OP_IADD_OVF_UN:
3627 case OP_ISUB_OVF_UN:
3629 case OP_IMUL_OVF_UN:
3630 #if SIZEOF_VOID_P == 8
3632 case OP_LADD_OVF_UN:
3634 case OP_LSUB_OVF_UN:
3636 case OP_LMUL_OVF_UN:
3639 LLVMValueRef args [2], val, ovf, func;
3641 args [0] = convert (ctx, lhs, op_to_llvm_type (ins->opcode));
3642 args [1] = convert (ctx, rhs, op_to_llvm_type (ins->opcode));
3643 func = LLVMGetNamedFunction (module, ovf_op_to_intrins (ins->opcode));
3645 val = LLVMBuildCall (builder, func, args, 2, "");
3646 values [ins->dreg] = LLVMBuildExtractValue (builder, val, 0, dname);
3647 ovf = LLVMBuildExtractValue (builder, val, 1, "");
3648 emit_cond_system_exception (ctx, bb, "OverflowException", ovf);
3649 CHECK_FAILURE (ctx);
3650 builder = ctx->builder;
3656 * We currently model them using arrays. Promotion to local vregs is
3657 * disabled for them in mono_handle_global_vregs () in the LLVM case,
3658 * so we always have an entry in cfg->varinfo for them.
3659 * FIXME: Is this needed ?
3662 MonoClass *klass = ins->klass;
3663 LLVMValueRef args [5];
3667 LLVM_FAILURE (ctx, "!klass");
3671 if (!addresses [ins->dreg])
3672 addresses [ins->dreg] = build_alloca (ctx, &klass->byval_arg);
3673 args [0] = LLVMBuildBitCast (builder, addresses [ins->dreg], LLVMPointerType (LLVMInt8Type (), 0), "");
3674 args [1] = LLVMConstInt (LLVMInt8Type (), 0, FALSE);
3675 args [2] = LLVMConstInt (LLVMInt32Type (), mono_class_value_size (klass, NULL), FALSE);
3677 args [3] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
3678 args [4] = LLVMConstInt (LLVMInt1Type (), 0, FALSE);
3679 LLVMBuildCall (builder, LLVMGetNamedFunction (module, memset_func_name), args, memset_param_count, "");
3682 case OP_DUMMY_VZERO:
3685 case OP_STOREV_MEMBASE:
3686 case OP_LOADV_MEMBASE:
3688 MonoClass *klass = ins->klass;
3689 LLVMValueRef src = NULL, dst, args [5];
3690 gboolean done = FALSE;
3694 LLVM_FAILURE (ctx, "!klass");
3698 if (mini_is_gsharedvt_klass (cfg, klass)) {
3700 LLVM_FAILURE (ctx, "gsharedvt");
3704 switch (ins->opcode) {
3705 case OP_STOREV_MEMBASE:
3706 if (cfg->gen_write_barriers && klass->has_references && ins->inst_destbasereg != cfg->frame_reg &&
3707 LLVMGetInstructionOpcode (values [ins->inst_destbasereg]) != LLVMAlloca) {
3708 /* Decomposed earlier */
3709 g_assert_not_reached ();
3712 if (!addresses [ins->sreg1]) {
3714 g_assert (values [ins->sreg1]);
3715 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));
3716 LLVMBuildStore (builder, values [ins->sreg1], dst);
3719 src = LLVMBuildBitCast (builder, addresses [ins->sreg1], LLVMPointerType (LLVMInt8Type (), 0), "");
3720 dst = convert (ctx, LLVMBuildAdd (builder, convert (ctx, values [ins->inst_destbasereg], IntPtrType ()), LLVMConstInt (IntPtrType (), ins->inst_offset, FALSE), ""), LLVMPointerType (LLVMInt8Type (), 0));
3723 case OP_LOADV_MEMBASE:
3724 if (!addresses [ins->dreg])
3725 addresses [ins->dreg] = build_alloca (ctx, &klass->byval_arg);
3726 src = convert (ctx, LLVMBuildAdd (builder, convert (ctx, values [ins->inst_basereg], IntPtrType ()), LLVMConstInt (IntPtrType (), ins->inst_offset, FALSE), ""), LLVMPointerType (LLVMInt8Type (), 0));
3727 dst = LLVMBuildBitCast (builder, addresses [ins->dreg], LLVMPointerType (LLVMInt8Type (), 0), "");
3730 if (!addresses [ins->sreg1])
3731 addresses [ins->sreg1] = build_alloca (ctx, &klass->byval_arg);
3732 if (!addresses [ins->dreg])
3733 addresses [ins->dreg] = build_alloca (ctx, &klass->byval_arg);
3734 src = LLVMBuildBitCast (builder, addresses [ins->sreg1], LLVMPointerType (LLVMInt8Type (), 0), "");
3735 dst = LLVMBuildBitCast (builder, addresses [ins->dreg], LLVMPointerType (LLVMInt8Type (), 0), "");
3738 g_assert_not_reached ();
3740 CHECK_FAILURE (ctx);
3747 args [2] = LLVMConstInt (LLVMInt32Type (), mono_class_value_size (klass, NULL), FALSE);
3748 args [3] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
3750 args [3] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
3751 args [4] = LLVMConstInt (LLVMInt1Type (), 0, FALSE);
3752 LLVMBuildCall (builder, LLVMGetNamedFunction (module, memcpy_func_name), args, memcpy_param_count, "");
3755 case OP_LLVM_OUTARG_VT:
3756 if (!addresses [ins->sreg1]) {
3757 addresses [ins->sreg1] = build_alloca (ctx, &ins->klass->byval_arg);
3758 g_assert (values [ins->sreg1]);
3759 LLVMBuildStore (builder, values [ins->sreg1], addresses [ins->sreg1]);
3761 addresses [ins->dreg] = addresses [ins->sreg1];
3767 #if defined(TARGET_X86) || defined(TARGET_AMD64)
3769 values [ins->dreg] = LLVMConstNull (type_to_llvm_type (ctx, &ins->klass->byval_arg));
3772 case OP_LOADX_MEMBASE: {
3773 LLVMTypeRef t = type_to_llvm_type (ctx, &ins->klass->byval_arg);
3776 src = convert (ctx, LLVMBuildAdd (builder, convert (ctx, values [ins->inst_basereg], IntPtrType ()), LLVMConstInt (IntPtrType (), ins->inst_offset, FALSE), ""), LLVMPointerType (t, 0));
3777 values [ins->dreg] = mono_llvm_build_aligned_load (builder, src, "", FALSE, 1);
3780 case OP_STOREX_MEMBASE: {
3781 LLVMTypeRef t = LLVMTypeOf (values [ins->sreg1]);
3784 dest = convert (ctx, LLVMBuildAdd (builder, convert (ctx, values [ins->inst_destbasereg], IntPtrType ()), LLVMConstInt (IntPtrType (), ins->inst_offset, FALSE), ""), LLVMPointerType (t, 0));
3785 mono_llvm_build_aligned_store (builder, values [ins->sreg1], dest, FALSE, 1);
3792 values [ins->dreg] = LLVMBuildAdd (builder, lhs, rhs, "");
3796 values [ins->dreg] = LLVMBuildFAdd (builder, lhs, rhs, "");
3802 values [ins->dreg] = LLVMBuildSub (builder, lhs, rhs, "");
3806 values [ins->dreg] = LLVMBuildFSub (builder, lhs, rhs, "");
3810 values [ins->dreg] = LLVMBuildFMul (builder, lhs, rhs, "");
3814 values [ins->dreg] = LLVMBuildFDiv (builder, lhs, rhs, "");
3817 values [ins->dreg] = LLVMBuildAnd (builder, lhs, rhs, "");
3820 values [ins->dreg] = LLVMBuildOr (builder, lhs, rhs, "");
3823 values [ins->dreg] = LLVMBuildXor (builder, lhs, rhs, "");
3827 values [ins->dreg] = LLVMBuildMul (builder, lhs, rhs, "");
3838 LLVMValueRef v = NULL;
3840 switch (ins->opcode) {
3845 t = LLVMVectorType (LLVMInt32Type (), 4);
3846 rt = LLVMVectorType (LLVMFloatType (), 4);
3852 t = LLVMVectorType (LLVMInt64Type (), 2);
3853 rt = LLVMVectorType (LLVMDoubleType (), 2);
3856 t = LLVMInt32Type ();
3857 rt = LLVMInt32Type ();
3858 g_assert_not_reached ();
3861 lhs = LLVMBuildBitCast (builder, lhs, t, "");
3862 rhs = LLVMBuildBitCast (builder, rhs, t, "");
3863 switch (ins->opcode) {
3866 v = LLVMBuildAnd (builder, lhs, rhs, "");
3870 v = LLVMBuildOr (builder, lhs, rhs, "");
3874 v = LLVMBuildXor (builder, lhs, rhs, "");
3878 v = LLVMBuildAnd (builder, rhs, LLVMBuildNot (builder, lhs, ""), "");
3881 values [ins->dreg] = LLVMBuildBitCast (builder, v, rt, "");
3905 case OP_PADDB_SAT_UN:
3906 case OP_PADDW_SAT_UN:
3907 case OP_PSUBB_SAT_UN:
3908 case OP_PSUBW_SAT_UN:
3916 case OP_PMULW_HIGH_UN: {
3917 LLVMValueRef args [2];
3922 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, simd_op_to_intrins (ins->opcode)), args, 2, dname);
3929 values [ins->dreg] = LLVMBuildSExt (builder, LLVMBuildICmp (builder, LLVMIntEQ, lhs, rhs, ""), LLVMTypeOf (lhs), "");
3933 values [ins->dreg] = LLVMBuildSExt (builder, LLVMBuildICmp (builder, LLVMIntSGT, lhs, rhs, ""), LLVMTypeOf (lhs), "");
3941 case OP_EXTRACTX_U2:
3943 case OP_EXTRACT_U1: {
3945 gboolean zext = FALSE;
3947 t = simd_op_to_llvm_type (ins->opcode);
3949 switch (ins->opcode) {
3957 case OP_EXTRACTX_U2:
3962 t = LLVMInt32Type ();
3963 g_assert_not_reached ();
3966 lhs = LLVMBuildBitCast (builder, lhs, t, "");
3967 values [ins->dreg] = LLVMBuildExtractElement (builder, lhs, LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), "");
3969 values [ins->dreg] = LLVMBuildZExt (builder, values [ins->dreg], LLVMInt32Type (), "");
3978 case OP_EXPAND_R8: {
3979 LLVMTypeRef t = simd_op_to_llvm_type (ins->opcode);
3980 LLVMValueRef mask [16], v;
3982 for (i = 0; i < 16; ++i)
3983 mask [i] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
3985 v = convert (ctx, values [ins->sreg1], LLVMGetElementType (t));
3987 values [ins->dreg] = LLVMBuildInsertElement (builder, LLVMConstNull (t), v, LLVMConstInt (LLVMInt32Type (), 0, FALSE), "");
3988 values [ins->dreg] = LLVMBuildShuffleVector (builder, values [ins->dreg], LLVMGetUndef (t), LLVMConstVector (mask, LLVMGetVectorSize (t)), "");
3993 values [ins->dreg] = LLVMBuildInsertElement (builder, values [ins->sreg1], convert (ctx, values [ins->sreg2], LLVMInt8Type ()), LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), dname);
3996 values [ins->dreg] = LLVMBuildInsertElement (builder, values [ins->sreg1], convert (ctx, values [ins->sreg2], LLVMInt16Type ()), LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), dname);
3999 values [ins->dreg] = LLVMBuildInsertElement (builder, values [ins->sreg1], convert (ctx, values [ins->sreg2], LLVMInt32Type ()), LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), dname);
4002 values [ins->dreg] = LLVMBuildInsertElement (builder, values [ins->sreg1], convert (ctx, values [ins->sreg2], LLVMInt64Type ()), LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), dname);
4005 values [ins->dreg] = LLVMBuildInsertElement (builder, values [ins->sreg1], convert (ctx, values [ins->sreg2], LLVMFloatType ()), LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), dname);
4008 values [ins->dreg] = LLVMBuildInsertElement (builder, values [ins->sreg1], convert (ctx, values [ins->sreg2], LLVMDoubleType ()), LLVMConstInt (LLVMInt32Type (), ins->inst_c0, FALSE), dname);
4019 case OP_EXTRACT_MASK:
4026 v = convert (ctx, values [ins->sreg1], simd_op_to_llvm_type (ins->opcode));
4028 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, simd_op_to_intrins (ins->opcode)), &v, 1, dname);
4032 case OP_ICONV_TO_R8_RAW:
4033 /* Same as OP_ICONV_TO_R8 */
4034 values [ins->dreg] = convert (ctx, LLVMBuildBitCast (builder, lhs, LLVMFloatType (), ""), LLVMDoubleType ());
4039 LLVMValueRef args [3];
4043 args [2] = LLVMConstInt (LLVMInt8Type (), ins->inst_c0, FALSE);
4045 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, simd_op_to_intrins (ins->opcode)), args, 3, dname);
4050 /* This is only used for implementing shifts by non-immediate */
4051 values [ins->dreg] = lhs;
4062 LLVMValueRef args [3];
4065 args [1] = LLVMConstInt (LLVMInt32Type (), ins->inst_imm, FALSE);
4067 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, simd_op_to_intrins (ins->opcode)), args, 2, dname);
4078 case OP_PSHLQ_REG: {
4079 LLVMValueRef args [3];
4082 args [1] = values [ins->sreg2];
4084 values [ins->dreg] = LLVMBuildCall (builder, LLVMGetNamedFunction (module, simd_op_to_intrins (ins->opcode)), args, 2, dname);
4091 case OP_PSHUFLEW_LOW:
4092 case OP_PSHUFLEW_HIGH: {
4094 LLVMValueRef v1 = NULL, v2 = NULL, mask_values [16];
4095 int i, mask_size = 0;
4096 int imask = ins->inst_c0;
4098 /* Convert the x86 shuffle mask to LLVM's */
4099 switch (ins->opcode) {
4102 mask [0] = ((imask >> 0) & 3);
4103 mask [1] = ((imask >> 2) & 3);
4104 mask [2] = ((imask >> 4) & 3) + 4;
4105 mask [3] = ((imask >> 6) & 3) + 4;
4106 v1 = values [ins->sreg1];
4107 v2 = values [ins->sreg2];
4111 mask [0] = ((imask >> 0) & 1);
4112 mask [1] = ((imask >> 1) & 1) + 2;
4113 v1 = values [ins->sreg1];
4114 v2 = values [ins->sreg2];
4116 case OP_PSHUFLEW_LOW:
4118 mask [0] = ((imask >> 0) & 3);
4119 mask [1] = ((imask >> 2) & 3);
4120 mask [2] = ((imask >> 4) & 3);
4121 mask [3] = ((imask >> 6) & 3);
4126 v1 = values [ins->sreg1];
4127 v2 = LLVMGetUndef (LLVMTypeOf (v1));
4129 case OP_PSHUFLEW_HIGH:
4135 mask [4] = 4 + ((imask >> 0) & 3);
4136 mask [5] = 4 + ((imask >> 2) & 3);
4137 mask [6] = 4 + ((imask >> 4) & 3);
4138 mask [7] = 4 + ((imask >> 6) & 3);
4139 v1 = values [ins->sreg1];
4140 v2 = LLVMGetUndef (LLVMTypeOf (v1));
4144 mask [0] = ((imask >> 0) & 3);
4145 mask [1] = ((imask >> 2) & 3);
4146 mask [2] = ((imask >> 4) & 3);
4147 mask [3] = ((imask >> 6) & 3);
4148 v1 = values [ins->sreg1];
4149 v2 = LLVMGetUndef (LLVMTypeOf (v1));
4152 g_assert_not_reached ();
4154 for (i = 0; i < mask_size; ++i)
4155 mask_values [i] = LLVMConstInt (LLVMInt32Type (), mask [i], FALSE);
4157 values [ins->dreg] =
4158 LLVMBuildShuffleVector (builder, v1, v2,
4159 LLVMConstVector (mask_values, mask_size), dname);
4163 case OP_UNPACK_LOWB:
4164 case OP_UNPACK_LOWW:
4165 case OP_UNPACK_LOWD:
4166 case OP_UNPACK_LOWQ:
4167 case OP_UNPACK_LOWPS:
4168 case OP_UNPACK_LOWPD:
4169 case OP_UNPACK_HIGHB:
4170 case OP_UNPACK_HIGHW:
4171 case OP_UNPACK_HIGHD:
4172 case OP_UNPACK_HIGHQ:
4173 case OP_UNPACK_HIGHPS:
4174 case OP_UNPACK_HIGHPD: {
4176 LLVMValueRef mask_values [16];
4177 int i, mask_size = 0;
4178 gboolean low = FALSE;
4180 switch (ins->opcode) {
4181 case OP_UNPACK_LOWB:
4185 case OP_UNPACK_LOWW:
4189 case OP_UNPACK_LOWD:
4190 case OP_UNPACK_LOWPS:
4194 case OP_UNPACK_LOWQ:
4195 case OP_UNPACK_LOWPD:
4199 case OP_UNPACK_HIGHB:
4202 case OP_UNPACK_HIGHW:
4205 case OP_UNPACK_HIGHD:
4206 case OP_UNPACK_HIGHPS:
4209 case OP_UNPACK_HIGHQ:
4210 case OP_UNPACK_HIGHPD:
4214 g_assert_not_reached ();
4218 for (i = 0; i < (mask_size / 2); ++i) {
4220 mask [(i * 2) + 1] = mask_size + i;
4223 for (i = 0; i < (mask_size / 2); ++i) {
4224 mask [(i * 2)] = (mask_size / 2) + i;
4225 mask [(i * 2) + 1] = mask_size + (mask_size / 2) + i;
4229 for (i = 0; i < mask_size; ++i)
4230 mask_values [i] = LLVMConstInt (LLVMInt32Type (), mask [i], FALSE);
4232 values [ins->dreg] =
4233 LLVMBuildShuffleVector (builder, values [ins->sreg1], values [ins->sreg2],
4234 LLVMConstVector (mask_values, mask_size), dname);
4239 LLVMTypeRef t = simd_op_to_llvm_type (ins->opcode);
4240 LLVMValueRef v, val;
4242 v = LLVMBuildExtractElement (builder, lhs, LLVMConstInt (LLVMInt32Type (), 0, FALSE), "");
4243 val = LLVMConstNull (t);
4244 val = LLVMBuildInsertElement (builder, val, v, LLVMConstInt (LLVMInt32Type (), 0, FALSE), "");
4245 val = LLVMBuildInsertElement (builder, val, v, LLVMConstInt (LLVMInt32Type (), 1, FALSE), dname);
4247 values [ins->dreg] = val;
4251 case OP_DUPPS_HIGH: {
4252 LLVMTypeRef t = simd_op_to_llvm_type (ins->opcode);
4253 LLVMValueRef v1, v2, val;
4256 if (ins->opcode == OP_DUPPS_LOW) {
4257 v1 = LLVMBuildExtractElement (builder, lhs, LLVMConstInt (LLVMInt32Type (), 0, FALSE), "");
4258 v2 = LLVMBuildExtractElement (builder, lhs, LLVMConstInt (LLVMInt32Type (), 2, FALSE), "");
4260 v1 = LLVMBuildExtractElement (builder, lhs, LLVMConstInt (LLVMInt32Type (), 1, FALSE), "");
4261 v2 = LLVMBuildExtractElement (builder, lhs, LLVMConstInt (LLVMInt32Type (), 3, FALSE), "");
4263 val = LLVMConstNull (t);
4264 val = LLVMBuildInsertElement (builder, val, v1, LLVMConstInt (LLVMInt32Type (), 0, FALSE), "");
4265 val = LLVMBuildInsertElement (builder, val, v1, LLVMConstInt (LLVMInt32Type (), 1, FALSE), "");
4266 val = LLVMBuildInsertElement (builder, val, v2, LLVMConstInt (LLVMInt32Type (), 2, FALSE), "");
4267 val = LLVMBuildInsertElement (builder, val, v2, LLVMConstInt (LLVMInt32Type (), 3, FALSE), "");
4269 values [ins->dreg] = val;
4279 * EXCEPTION HANDLING
4281 case OP_IMPLICIT_EXCEPTION:
4282 /* This marks a place where an implicit exception can happen */
4283 if (bb->region != -1)
4284 LLVM_FAILURE (ctx, "implicit-exception");
4288 MonoMethodSignature *throw_sig;
4289 LLVMValueRef callee, arg;
4290 gboolean rethrow = (ins->opcode == OP_RETHROW);
4291 const char *icall_name;
4293 callee = rethrow ? ctx->lmodule->rethrow : ctx->lmodule->throw;
4294 icall_name = rethrow ? "mono_arch_rethrow_exception" : "mono_arch_throw_exception";
4297 throw_sig = mono_metadata_signature_alloc (mono_get_corlib (), 1);
4298 throw_sig->ret = &mono_get_void_class ()->byval_arg;
4299 throw_sig->params [0] = &mono_get_object_class ()->byval_arg;
4300 if (cfg->compile_aot) {
4301 callee = get_plt_entry (ctx, sig_to_llvm_sig (ctx, throw_sig), MONO_PATCH_INFO_INTERNAL_METHOD, icall_name);
4303 callee = LLVMAddFunction (module, icall_name, sig_to_llvm_sig (ctx, throw_sig));
4307 * LLVM doesn't push the exception argument, so we need a different
4310 LLVMAddGlobalMapping (ctx->lmodule->ee, callee, resolve_patch (cfg, MONO_PATCH_INFO_INTERNAL_METHOD, rethrow ? "llvm_rethrow_exception_trampoline" : "llvm_throw_exception_trampoline"));
4312 LLVMAddGlobalMapping (ctx->lmodule->ee, callee, resolve_patch (cfg, MONO_PATCH_INFO_INTERNAL_METHOD, icall_name));
4316 mono_memory_barrier ();
4318 ctx->lmodule->rethrow = callee;
4320 ctx->lmodule->throw = callee;
4322 arg = convert (ctx, lhs, type_to_llvm_type (ctx, &mono_get_object_class ()->byval_arg));
4323 emit_call (ctx, bb, &builder, callee, &arg, 1);
4326 case OP_CALL_HANDLER: {
4328 * We don't 'call' handlers, but instead simply branch to them.
4329 * The code generated by ENDFINALLY will branch back to us.
4331 LLVMBasicBlockRef noex_bb;
4333 BBInfo *info = &bblocks [ins->inst_target_bb->block_num];
4335 bb_list = info->call_handler_return_bbs;
4338 * Set the indicator variable for the finally clause.
4340 lhs = info->finally_ind;
4342 LLVMBuildStore (builder, LLVMConstInt (LLVMInt32Type (), g_slist_length (bb_list) + 1, FALSE), lhs);
4344 /* Branch to the finally clause */
4345 LLVMBuildBr (builder, info->call_handler_target_bb);
4347 noex_bb = gen_bb (ctx, "CALL_HANDLER_CONT_BB");
4348 info->call_handler_return_bbs = g_slist_append_mempool (cfg->mempool, info->call_handler_return_bbs, noex_bb);
4350 builder = ctx->builder = create_builder (ctx);
4351 LLVMPositionBuilderAtEnd (ctx->builder, noex_bb);
4353 bblocks [bb->block_num].end_bblock = noex_bb;
4356 case OP_START_HANDLER: {
4359 case OP_ENDFINALLY: {
4360 LLVMBasicBlockRef resume_bb;
4361 MonoBasicBlock *handler_bb;
4362 LLVMValueRef val, switch_ins, callee;
4366 handler_bb = g_hash_table_lookup (ctx->region_to_handler, GUINT_TO_POINTER (mono_get_block_region_notry (cfg, bb->region)));
4367 g_assert (handler_bb);
4368 info = &bblocks [handler_bb->block_num];
4369 lhs = info->finally_ind;
4372 bb_list = info->call_handler_return_bbs;
4374 resume_bb = gen_bb (ctx, "ENDFINALLY_RESUME_BB");
4376 /* Load the finally variable */
4377 val = LLVMBuildLoad (builder, lhs, "");
4379 /* Reset the variable */
4380 LLVMBuildStore (builder, LLVMConstInt (LLVMInt32Type (), 0, FALSE), lhs);
4382 /* Branch to either resume_bb, or to the bblocks in bb_list */
4383 switch_ins = LLVMBuildSwitch (builder, val, resume_bb, g_slist_length (bb_list));
4385 * The other targets are added at the end to handle OP_CALL_HANDLER
4386 * opcodes processed later.
4388 info->endfinally_switch_ins_list = g_slist_append_mempool (cfg->mempool, info->endfinally_switch_ins_list, switch_ins);
4390 builder = ctx->builder = create_builder (ctx);
4391 LLVMPositionBuilderAtEnd (ctx->builder, resume_bb);
4393 if (ctx->cfg->compile_aot) {
4394 callee = get_plt_entry (ctx, LLVMFunctionType (LLVMVoidType (), NULL, 0, FALSE), MONO_PATCH_INFO_INTERNAL_METHOD, "llvm_resume_unwind_trampoline");
4396 callee = LLVMGetNamedFunction (module, "llvm_resume_unwind_trampoline");
4398 LLVMBuildCall (builder, callee, NULL, 0, "");
4400 LLVMBuildUnreachable (builder);
4401 has_terminator = TRUE;
4407 sprintf (reason, "opcode %s", mono_inst_name (ins->opcode));
4408 LLVM_FAILURE (ctx, reason);
4413 /* Convert the value to the type required by phi nodes */
4414 if (spec [MONO_INST_DEST] != ' ' && !MONO_IS_STORE_MEMBASE (ins) && ctx->vreg_types [ins->dreg]) {
4415 if (!values [ins->dreg])
4417 values [ins->dreg] = addresses [ins->dreg];
4419 values [ins->dreg] = convert (ctx, values [ins->dreg], ctx->vreg_types [ins->dreg]);
4422 /* Add stores for volatile variables */
4423 if (spec [MONO_INST_DEST] != ' ' && spec [MONO_INST_DEST] != 'v' && !MONO_IS_STORE_MEMBASE (ins))
4424 emit_volatile_store (ctx, ins->dreg);
4427 if (!has_terminator && bb->next_bb && (bb == cfg->bb_entry || bb->in_count > 0))
4428 LLVMBuildBr (builder, get_bb (ctx, bb->next_bb));
4430 if (bb == cfg->bb_exit && sig->ret->type == MONO_TYPE_VOID) {
4431 emit_dbg_loc (ctx, builder, cfg->header->code + cfg->header->code_size - 1);
4432 LLVMBuildRetVoid (builder);
4435 if (bb == cfg->bb_entry)
4436 ctx->last_alloca = LLVMGetLastInstruction (get_bb (ctx, cfg->bb_entry));
4445 * mono_llvm_check_method_supported:
4447 * Do some quick checks to decide whenever cfg->method can be compiled by LLVM, to avoid
4448 * compiling a method twice.
4451 mono_llvm_check_method_supported (MonoCompile *cfg)
4453 MonoMethodHeader *header = cfg->header;
4454 MonoExceptionClause *clause;
4457 if (cfg->method->save_lmf) {
4458 cfg->exception_message = g_strdup ("lmf");
4459 cfg->disable_llvm = TRUE;
4461 if (cfg->disable_llvm)
4465 for (i = 0; i < header->num_clauses; ++i) {
4466 clause = &header->clauses [i];
4468 if (i > 0 && clause->try_offset <= header->clauses [i - 1].handler_offset + header->clauses [i - 1].handler_len) {
4470 * FIXME: Some tests still fail with nested clauses.
4472 cfg->exception_message = g_strdup ("nested clauses");
4473 cfg->disable_llvm = TRUE;
4477 if (cfg->disable_llvm)
4482 if (cfg->method->dynamic) {
4483 cfg->exception_message = g_strdup ("dynamic.");
4484 cfg->disable_llvm = TRUE;
4486 if (cfg->disable_llvm)
4491 * mono_llvm_emit_method:
4493 * Emit LLVM IL from the mono IL, and compile it to native code using LLVM.
4496 mono_llvm_emit_method (MonoCompile *cfg)
4499 MonoMethodSignature *sig;
4501 LLVMTypeRef method_type;
4502 LLVMValueRef method = NULL;
4504 LLVMValueRef *values;
4505 int i, max_block_num, bb_index;
4506 gboolean last = FALSE;
4507 GPtrArray *phi_values;
4508 LLVMCallInfo *linfo;
4510 LLVMModuleRef module;
4512 GPtrArray *bblock_list;
4513 MonoMethodHeader *header;
4514 MonoExceptionClause *clause;
4518 /* The code below might acquire the loader lock, so use it for global locking */
4519 mono_loader_lock ();
4521 /* Used to communicate with the callbacks */
4522 mono_native_tls_set_value (current_cfg_tls_id, cfg);
4524 ctx = g_new0 (EmitContext, 1);
4526 ctx->mempool = cfg->mempool;
4529 * This maps vregs to the LLVM instruction defining them
4531 values = g_new0 (LLVMValueRef, cfg->next_vreg);
4533 * This maps vregs for volatile variables to the LLVM instruction defining their
4536 ctx->addresses = g_new0 (LLVMValueRef, cfg->next_vreg);
4537 ctx->vreg_types = g_new0 (LLVMTypeRef, cfg->next_vreg);
4538 ctx->vreg_cli_types = g_new0 (MonoType*, cfg->next_vreg);
4539 phi_values = g_ptr_array_sized_new (256);
4541 * This signals whenever the vreg was defined by a phi node with no input vars
4542 * (i.e. all its input bblocks end with NOT_REACHABLE).
4544 ctx->is_dead = g_new0 (gboolean, cfg->next_vreg);
4545 /* Whenever the bblock is unreachable */
4546 ctx->unreachable = g_new0 (gboolean, cfg->max_block_num);
4548 bblock_list = g_ptr_array_sized_new (256);
4550 ctx->values = values;
4551 ctx->region_to_handler = g_hash_table_new (NULL, NULL);
4553 if (cfg->compile_aot) {
4554 ctx->lmodule = &aot_module;
4555 method_name = mono_aot_get_method_name (cfg);
4556 cfg->llvm_method_name = g_strdup (method_name);
4558 init_jit_module (cfg->domain);
4559 ctx->lmodule = domain_jit_info (cfg->domain)->llvm_module;
4560 method_name = mono_method_full_name (cfg->method, TRUE);
4563 module = ctx->module = ctx->lmodule->module;
4566 LLVM_FAILURE (ctx, "gsharedvt");
4570 static int count = 0;
4573 if (g_getenv ("LLVM_COUNT")) {
4574 if (count == atoi (g_getenv ("LLVM_COUNT"))) {
4575 printf ("LAST: %s\n", mono_method_full_name (cfg->method, TRUE));
4579 if (count > atoi (g_getenv ("LLVM_COUNT")))
4580 LLVM_FAILURE (ctx, "");
4585 sig = mono_method_signature (cfg->method);
4588 linfo = mono_arch_get_llvm_call_info (cfg, sig);
4590 CHECK_FAILURE (ctx);
4593 linfo->rgctx_arg = TRUE;
4594 method_type = sig_to_llvm_sig_full (ctx, sig, linfo, &sinfo);
4595 CHECK_FAILURE (ctx);
4598 * This maps parameter indexes in the original signature to the indexes in
4599 * the LLVM signature.
4601 ctx->pindexes = sinfo.pindexes;
4603 method = LLVMAddFunction (module, method_name, method_type);
4604 ctx->lmethod = method;
4606 LLVMSetFunctionCallConv (method, LLVMMono1CallConv);
4607 LLVMSetLinkage (method, LLVMPrivateLinkage);
4609 LLVMAddFunctionAttr (method, LLVMUWTable);
4611 if (cfg->compile_aot) {
4612 LLVMSetLinkage (method, LLVMInternalLinkage);
4613 #if LLVM_API_VERSION == 0
4614 /* This causes an assertion in later LLVM versions */
4615 LLVMSetVisibility (method, LLVMHiddenVisibility);
4617 if (ctx->lmodule->external_symbols) {
4618 LLVMSetLinkage (method, LLVMExternalLinkage);
4619 LLVMSetVisibility (method, LLVMHiddenVisibility);
4622 LLVMSetLinkage (method, LLVMPrivateLinkage);
4625 if (cfg->method->save_lmf)
4626 LLVM_FAILURE (ctx, "lmf");
4628 if (sig->pinvoke && cfg->method->wrapper_type != MONO_WRAPPER_RUNTIME_INVOKE)
4629 LLVM_FAILURE (ctx, "pinvoke signature");
4631 header = cfg->header;
4632 for (i = 0; i < header->num_clauses; ++i) {
4633 clause = &header->clauses [i];
4634 if (clause->flags != MONO_EXCEPTION_CLAUSE_FINALLY && clause->flags != MONO_EXCEPTION_CLAUSE_NONE)
4635 LLVM_FAILURE (ctx, "non-finally/catch clause.");
4638 if (linfo->rgctx_arg) {
4639 ctx->rgctx_arg = LLVMGetParam (method, sinfo.rgctx_arg_pindex);
4641 * We mark the rgctx parameter with the inreg attribute, which is mapped to
4642 * MONO_ARCH_RGCTX_REG in the Mono calling convention in llvm, i.e.
4643 * CC_X86_64_Mono in X86CallingConv.td.
4645 LLVMAddAttribute (ctx->rgctx_arg, LLVMInRegAttribute);
4646 LLVMSetValueName (ctx->rgctx_arg, "rgctx");
4648 if (cfg->vret_addr) {
4649 values [cfg->vret_addr->dreg] = LLVMGetParam (method, sinfo.vret_arg_pindex);
4650 LLVMSetValueName (values [cfg->vret_addr->dreg], "vret");
4653 values [cfg->args [0]->dreg] = LLVMGetParam (method, sinfo.this_arg_pindex);
4654 LLVMSetValueName (values [cfg->args [0]->dreg], "this");
4657 names = g_new (char *, sig->param_count);
4658 mono_method_get_param_names (cfg->method, (const char **) names);
4660 for (i = 0; i < sig->param_count; ++i) {
4663 values [cfg->args [i + sig->hasthis]->dreg] = LLVMGetParam (method, sinfo.pindexes [i]);
4664 if (names [i] && names [i][0] != '\0')
4665 name = g_strdup_printf ("arg_%s", names [i]);
4667 name = g_strdup_printf ("arg_%d", i);
4668 LLVMSetValueName (values [cfg->args [i + sig->hasthis]->dreg], name);
4670 if (linfo->args [i + sig->hasthis].storage == LLVMArgVtypeByVal)
4671 LLVMAddAttribute (LLVMGetParam (method, sinfo.pindexes [i]), LLVMByValAttribute);
4675 if (ctx->lmodule->emit_dwarf && cfg->compile_aot && mono_debug_enabled ()) {
4676 ctx->minfo = mono_debug_lookup_method (cfg->method);
4677 ctx->dbg_md = emit_dbg_subprogram (ctx, cfg, method, method_name);
4681 for (bb = cfg->bb_entry; bb; bb = bb->next_bb)
4682 max_block_num = MAX (max_block_num, bb->block_num);
4683 ctx->bblocks = bblocks = g_new0 (BBInfo, max_block_num + 1);
4685 /* Add branches between non-consecutive bblocks */
4686 for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
4687 if (bb->last_ins && MONO_IS_COND_BRANCH_OP (bb->last_ins) &&
4688 bb->next_bb != bb->last_ins->inst_false_bb) {
4690 MonoInst *inst = mono_mempool_alloc0 (cfg->mempool, sizeof (MonoInst));
4691 inst->opcode = OP_BR;
4692 inst->inst_target_bb = bb->last_ins->inst_false_bb;
4693 mono_bblock_add_inst (bb, inst);
4698 * The INDIRECT flag added by OP_LDADDR inhibits optimizations, even if the LDADDR
4699 * was later optimized away, so clear these flags, and add them back for the still
4700 * present OP_LDADDR instructions.
4702 for (i = 0; i < cfg->next_vreg; ++i) {
4705 ins = get_vreg_to_inst (cfg, i);
4706 if (ins && ins != cfg->rgctx_var)
4707 ins->flags &= ~MONO_INST_INDIRECT;
4711 * Make a first pass over the code to precreate PHI nodes/set INDIRECT flags.
4713 for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
4715 LLVMBuilderRef builder;
4717 char dname_buf[128];
4719 builder = create_builder (ctx);
4721 for (ins = bb->code; ins; ins = ins->next) {
4722 switch (ins->opcode) {
4727 LLVMTypeRef phi_type = llvm_type_to_stack_type (type_to_llvm_type (ctx, &ins->klass->byval_arg));
4729 CHECK_FAILURE (ctx);
4731 if (ins->opcode == OP_VPHI) {
4732 /* Treat valuetype PHI nodes as operating on the address itself */
4733 g_assert (ins->klass);
4734 phi_type = LLVMPointerType (type_to_llvm_type (ctx, &ins->klass->byval_arg), 0);
4738 * Have to precreate these, as they can be referenced by
4739 * earlier instructions.
4741 sprintf (dname_buf, "t%d", ins->dreg);
4743 values [ins->dreg] = LLVMBuildPhi (builder, phi_type, dname);
4745 if (ins->opcode == OP_VPHI)
4746 ctx->addresses [ins->dreg] = values [ins->dreg];
4748 g_ptr_array_add (phi_values, values [ins->dreg]);
4751 * Set the expected type of the incoming arguments since these have
4752 * to have the same type.
4754 for (i = 0; i < ins->inst_phi_args [0]; i++) {
4755 int sreg1 = ins->inst_phi_args [i + 1];
4758 ctx->vreg_types [sreg1] = phi_type;
4763 ((MonoInst*)ins->inst_p0)->flags |= MONO_INST_INDIRECT;
4772 * Create an ordering for bblocks, use the depth first order first, then
4773 * put the exception handling bblocks last.
4775 for (bb_index = 0; bb_index < cfg->num_bblocks; ++bb_index) {
4776 bb = cfg->bblocks [bb_index];
4777 if (!(bb->region != -1 && !MONO_BBLOCK_IS_IN_REGION (bb, MONO_REGION_TRY))) {
4778 g_ptr_array_add (bblock_list, bb);
4779 bblocks [bb->block_num].added = TRUE;
4783 for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
4784 if (!bblocks [bb->block_num].added)
4785 g_ptr_array_add (bblock_list, bb);
4789 * Second pass: generate code.
4791 for (bb_index = 0; bb_index < bblock_list->len; ++bb_index) {
4792 bb = g_ptr_array_index (bblock_list, bb_index);
4794 if (!(bb == cfg->bb_entry || bb->in_count > 0))
4797 process_bb (ctx, bb);
4798 CHECK_FAILURE (ctx);
4801 /* Add incoming phi values */
4802 for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
4803 GSList *l, *ins_list;
4805 ins_list = bblocks [bb->block_num].phi_nodes;
4807 for (l = ins_list; l; l = l->next) {
4808 PhiNode *node = l->data;
4809 MonoInst *phi = node->phi;
4810 int sreg1 = node->sreg;
4811 LLVMBasicBlockRef in_bb;
4816 in_bb = get_end_bb (ctx, node->in_bb);
4818 if (ctx->unreachable [node->in_bb->block_num])
4821 if (!values [sreg1])
4822 /* Can happen with values in EH clauses */
4823 LLVM_FAILURE (ctx, "incoming phi sreg1");
4825 if (phi->opcode == OP_VPHI) {
4826 g_assert (LLVMTypeOf (ctx->addresses [sreg1]) == LLVMTypeOf (values [phi->dreg]));
4827 LLVMAddIncoming (values [phi->dreg], &ctx->addresses [sreg1], &in_bb, 1);
4829 if (LLVMTypeOf (values [sreg1]) != LLVMTypeOf (values [phi->dreg]))
4831 LLVM_FAILURE (ctx, "incoming phi arg type mismatch");
4832 g_assert (LLVMTypeOf (values [sreg1]) == LLVMTypeOf (values [phi->dreg]));
4833 LLVMAddIncoming (values [phi->dreg], &values [sreg1], &in_bb, 1);
4838 /* Create the SWITCH statements for ENDFINALLY instructions */
4839 for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
4840 BBInfo *info = &bblocks [bb->block_num];
4842 for (l = info->endfinally_switch_ins_list; l; l = l->next) {
4843 LLVMValueRef switch_ins = l->data;
4844 GSList *bb_list = info->call_handler_return_bbs;
4846 for (i = 0; i < g_slist_length (bb_list); ++i)
4847 LLVMAddCase (switch_ins, LLVMConstInt (LLVMInt32Type (), i + 1, FALSE), g_slist_nth (bb_list, i)->data);
4851 if (cfg->verbose_level > 1)
4852 mono_llvm_dump_value (method);
4854 if (cfg->compile_aot)
4855 mark_as_used (ctx->lmodule, method);
4857 if (cfg->compile_aot) {
4858 LLVMValueRef md_args [16];
4859 LLVMValueRef md_node;
4862 method_index = mono_aot_get_method_index (cfg->orig_method);
4863 md_args [0] = LLVMMDString (method_name, strlen (method_name));
4864 md_args [1] = LLVMConstInt (LLVMInt32Type (), method_index, FALSE);
4865 md_node = LLVMMDNode (md_args, 2);
4866 LLVMAddNamedMetadataOperand (module, "mono.function_indexes", md_node);
4867 //LLVMSetMetadata (method, md_kind, LLVMMDNode (&md_arg, 1));
4870 if (cfg->compile_aot) {
4871 /* Don't generate native code, keep the LLVM IR */
4872 if (cfg->compile_aot && cfg->verbose_level)
4873 printf ("%s emitted as %s\n", mono_method_full_name (cfg->method, TRUE), method_name);
4875 //LLVMVerifyFunction(method, 0);
4877 mono_llvm_optimize_method (ctx->lmodule->mono_ee, method);
4879 if (cfg->verbose_level > 1)
4880 mono_llvm_dump_value (method);
4882 cfg->native_code = LLVMGetPointerToGlobal (ctx->lmodule->ee, method);
4884 /* Set by emit_cb */
4885 g_assert (cfg->code_len);
4887 /* FIXME: Free the LLVM IL for the function */
4890 if (ctx->lmodule->method_to_lmethod)
4891 g_hash_table_insert (ctx->lmodule->method_to_lmethod, cfg->method, method);
4898 /* Need to add unused phi nodes as they can be referenced by other values */
4899 LLVMBasicBlockRef phi_bb = LLVMAppendBasicBlock (method, "PHI_BB");
4900 LLVMBuilderRef builder;
4902 builder = create_builder (ctx);
4903 LLVMPositionBuilderAtEnd (builder, phi_bb);
4905 for (i = 0; i < phi_values->len; ++i) {
4906 LLVMValueRef v = g_ptr_array_index (phi_values, i);
4907 if (LLVMGetInstructionParent (v) == NULL)
4908 LLVMInsertIntoBuilder (builder, v);
4911 LLVMDeleteFunction (method);
4916 g_free (ctx->addresses);
4917 g_free (ctx->vreg_types);
4918 g_free (ctx->vreg_cli_types);
4919 g_free (ctx->pindexes);
4920 g_free (ctx->is_dead);
4921 g_free (ctx->unreachable);
4922 g_ptr_array_free (phi_values, TRUE);
4923 g_free (ctx->bblocks);
4924 g_hash_table_destroy (ctx->region_to_handler);
4925 g_free (method_name);
4926 g_ptr_array_free (bblock_list, TRUE);
4928 for (l = ctx->builders; l; l = l->next) {
4929 LLVMBuilderRef builder = l->data;
4930 LLVMDisposeBuilder (builder);
4935 mono_native_tls_set_value (current_cfg_tls_id, NULL);
4937 mono_loader_unlock ();
4941 * mono_llvm_emit_call:
4943 * Same as mono_arch_emit_call () for LLVM.
4946 mono_llvm_emit_call (MonoCompile *cfg, MonoCallInst *call)
4949 MonoMethodSignature *sig;
4950 int i, n, stack_size;
4955 sig = call->signature;
4956 n = sig->param_count + sig->hasthis;
4958 call->cinfo = mono_arch_get_llvm_call_info (cfg, sig);
4960 if (cfg->disable_llvm)
4963 if (sig->call_convention == MONO_CALL_VARARG) {
4964 cfg->exception_message = g_strdup ("varargs");
4965 cfg->disable_llvm = TRUE;
4968 for (i = 0; i < n; ++i) {
4971 ainfo = call->cinfo->args + i;
4973 in = call->args [i];
4975 /* Simply remember the arguments */
4976 switch (ainfo->storage) {
4978 case LLVMArgInFPReg: {
4979 MonoType *t = (sig->hasthis && i == 0) ? &mono_get_intptr_class ()->byval_arg : sig->params [i - sig->hasthis];
4982 opcode = mono_type_to_regmove (cfg, t);
4983 if (opcode == OP_FMOVE) {
4984 MONO_INST_NEW (cfg, ins, OP_FMOVE);
4985 ins->dreg = mono_alloc_freg (cfg);
4986 } else if (opcode == OP_LMOVE) {
4987 MONO_INST_NEW (cfg, ins, OP_LMOVE);
4988 ins->dreg = mono_alloc_lreg (cfg);
4990 MONO_INST_NEW (cfg, ins, OP_MOVE);
4991 ins->dreg = mono_alloc_ireg (cfg);
4993 ins->sreg1 = in->dreg;
4996 case LLVMArgVtypeByVal:
4997 case LLVMArgVtypeInReg:
4998 MONO_INST_NEW (cfg, ins, OP_LLVM_OUTARG_VT);
4999 ins->dreg = mono_alloc_ireg (cfg);
5000 ins->sreg1 = in->dreg;
5001 ins->klass = mono_class_from_mono_type (sig->params [i - sig->hasthis]);
5004 call->cinfo = mono_arch_get_llvm_call_info (cfg, sig);
5005 cfg->exception_message = g_strdup ("ainfo->storage");
5006 cfg->disable_llvm = TRUE;
5010 if (!cfg->disable_llvm) {
5011 MONO_ADD_INS (cfg->cbb, ins);
5012 mono_call_inst_add_outarg_reg (cfg, call, ins->dreg, 0, FALSE);
5017 static unsigned char*
5018 alloc_cb (LLVMValueRef function, int size)
5022 cfg = mono_native_tls_get_value (current_cfg_tls_id);
5026 return mono_domain_code_reserve (cfg->domain, size);
5028 return mono_domain_code_reserve (mono_domain_get (), size);
5033 emitted_cb (LLVMValueRef function, void *start, void *end)
5037 cfg = mono_native_tls_get_value (current_cfg_tls_id);
5039 cfg->code_len = (guint8*)end - (guint8*)start;
5043 exception_cb (void *data)
5046 MonoJitExceptionInfo *ei;
5047 guint32 ei_len, i, j, nested_len, nindex;
5048 gpointer *type_info;
5049 int this_reg, this_offset;
5051 cfg = mono_native_tls_get_value (current_cfg_tls_id);
5055 * data points to a DWARF FDE structure, convert it to our unwind format and
5057 * An alternative would be to save it directly, and modify our unwinder to work
5060 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);
5061 if (cfg->verbose_level > 1)
5062 mono_print_unwind_info (cfg->encoded_unwind_ops, cfg->encoded_unwind_ops_len);
5064 /* Count nested clauses */
5066 for (i = 0; i < ei_len; ++i) {
5067 for (j = 0; j < ei_len; ++j) {
5068 gint32 cindex1 = *(gint32*)type_info [i];
5069 MonoExceptionClause *clause1 = &cfg->header->clauses [cindex1];
5070 gint32 cindex2 = *(gint32*)type_info [j];
5071 MonoExceptionClause *clause2 = &cfg->header->clauses [cindex2];
5073 if (cindex1 != cindex2 && clause1->try_offset >= clause2->try_offset && clause1->handler_offset <= clause2->handler_offset) {
5079 cfg->llvm_ex_info = mono_mempool_alloc0 (cfg->mempool, (ei_len + nested_len) * sizeof (MonoJitExceptionInfo));
5080 cfg->llvm_ex_info_len = ei_len + nested_len;
5081 memcpy (cfg->llvm_ex_info, ei, ei_len * sizeof (MonoJitExceptionInfo));
5082 /* Fill the rest of the information from the type info */
5083 for (i = 0; i < ei_len; ++i) {
5084 gint32 clause_index = *(gint32*)type_info [i];
5085 MonoExceptionClause *clause = &cfg->header->clauses [clause_index];
5087 cfg->llvm_ex_info [i].flags = clause->flags;
5088 cfg->llvm_ex_info [i].data.catch_class = clause->data.catch_class;
5092 * For nested clauses, the LLVM produced exception info associates the try interval with
5093 * the innermost handler, while mono expects it to be associated with all nesting clauses.
5095 /* FIXME: These should be order with the normal clauses */
5097 for (i = 0; i < ei_len; ++i) {
5098 for (j = 0; j < ei_len; ++j) {
5099 gint32 cindex1 = *(gint32*)type_info [i];
5100 MonoExceptionClause *clause1 = &cfg->header->clauses [cindex1];
5101 gint32 cindex2 = *(gint32*)type_info [j];
5102 MonoExceptionClause *clause2 = &cfg->header->clauses [cindex2];
5104 if (cindex1 != cindex2 && clause1->try_offset >= clause2->try_offset && clause1->handler_offset <= clause2->handler_offset) {
5106 * The try interval comes from the nested clause, everything else from the
5109 memcpy (&cfg->llvm_ex_info [nindex], &cfg->llvm_ex_info [j], sizeof (MonoJitExceptionInfo));
5110 cfg->llvm_ex_info [nindex].try_start = cfg->llvm_ex_info [i].try_start;
5111 cfg->llvm_ex_info [nindex].try_end = cfg->llvm_ex_info [i].try_end;
5116 g_assert (nindex == ei_len + nested_len);
5117 cfg->llvm_this_reg = this_reg;
5118 cfg->llvm_this_offset = this_offset;
5120 /* type_info [i] is cfg mempool allocated, no need to free it */
5127 dlsym_cb (const char *name, void **symbol)
5133 if (!strcmp (name, "__bzero")) {
5134 *symbol = (void*)bzero;
5136 current = mono_dl_open (NULL, 0, NULL);
5139 err = mono_dl_symbol (current, name, symbol);
5141 mono_dl_close (current);
5143 #ifdef MONO_ARCH_HAVE_CREATE_LLVM_NATIVE_THUNK
5144 *symbol = (char*)mono_arch_create_llvm_native_thunk (mono_domain_get (), (guint8*)(*symbol));
5150 AddFunc (LLVMModuleRef module, const char *name, LLVMTypeRef ret_type, LLVMTypeRef *param_types, int nparams)
5152 LLVMAddFunction (module, name, LLVMFunctionType (ret_type, param_types, nparams, FALSE));
5156 AddFunc2 (LLVMModuleRef module, const char *name, LLVMTypeRef ret_type, LLVMTypeRef param_type1, LLVMTypeRef param_type2)
5158 LLVMTypeRef param_types [4];
5160 param_types [0] = param_type1;
5161 param_types [1] = param_type2;
5163 AddFunc (module, name, ret_type, param_types, 2);
5167 add_intrinsics (LLVMModuleRef module)
5169 /* Emit declarations of instrinsics */
5171 * It would be nicer to emit only the intrinsics actually used, but LLVM's Module
5172 * type doesn't seem to do any locking.
5175 LLVMTypeRef memset_params [] = { LLVMPointerType (LLVMInt8Type (), 0), LLVMInt8Type (), LLVMInt32Type (), LLVMInt32Type (), LLVMInt1Type () };
5177 memset_param_count = 5;
5178 memset_func_name = "llvm.memset.p0i8.i32";
5180 LLVMAddFunction (module, memset_func_name, LLVMFunctionType (LLVMVoidType (), memset_params, memset_param_count, FALSE));
5184 LLVMTypeRef memcpy_params [] = { LLVMPointerType (LLVMInt8Type (), 0), LLVMPointerType (LLVMInt8Type (), 0), LLVMInt32Type (), LLVMInt32Type (), LLVMInt1Type () };
5186 memcpy_param_count = 5;
5187 memcpy_func_name = "llvm.memcpy.p0i8.p0i8.i32";
5189 LLVMAddFunction (module, memcpy_func_name, LLVMFunctionType (LLVMVoidType (), memcpy_params, memcpy_param_count, FALSE));
5193 LLVMTypeRef params [] = { LLVMDoubleType () };
5195 LLVMAddFunction (module, "llvm.sin.f64", LLVMFunctionType (LLVMDoubleType (), params, 1, FALSE));
5196 LLVMAddFunction (module, "llvm.cos.f64", LLVMFunctionType (LLVMDoubleType (), params, 1, FALSE));
5197 LLVMAddFunction (module, "llvm.sqrt.f64", LLVMFunctionType (LLVMDoubleType (), params, 1, FALSE));
5199 /* This isn't an intrinsic, instead llvm seems to special case it by name */
5200 LLVMAddFunction (module, "fabs", LLVMFunctionType (LLVMDoubleType (), params, 1, FALSE));
5204 LLVMTypeRef ovf_res_i32 [] = { LLVMInt32Type (), LLVMInt1Type () };
5205 LLVMTypeRef ovf_params_i32 [] = { LLVMInt32Type (), LLVMInt32Type () };
5207 LLVMAddFunction (module, "llvm.sadd.with.overflow.i32", LLVMFunctionType (LLVMStructType (ovf_res_i32, 2, FALSE), ovf_params_i32, 2, FALSE));
5208 LLVMAddFunction (module, "llvm.uadd.with.overflow.i32", LLVMFunctionType (LLVMStructType (ovf_res_i32, 2, FALSE), ovf_params_i32, 2, FALSE));
5209 LLVMAddFunction (module, "llvm.ssub.with.overflow.i32", LLVMFunctionType (LLVMStructType (ovf_res_i32, 2, FALSE), ovf_params_i32, 2, FALSE));
5210 LLVMAddFunction (module, "llvm.usub.with.overflow.i32", LLVMFunctionType (LLVMStructType (ovf_res_i32, 2, FALSE), ovf_params_i32, 2, FALSE));
5211 LLVMAddFunction (module, "llvm.smul.with.overflow.i32", LLVMFunctionType (LLVMStructType (ovf_res_i32, 2, FALSE), ovf_params_i32, 2, FALSE));
5212 LLVMAddFunction (module, "llvm.umul.with.overflow.i32", LLVMFunctionType (LLVMStructType (ovf_res_i32, 2, FALSE), ovf_params_i32, 2, FALSE));
5216 LLVMTypeRef ovf_res_i64 [] = { LLVMInt64Type (), LLVMInt1Type () };
5217 LLVMTypeRef ovf_params_i64 [] = { LLVMInt64Type (), LLVMInt64Type () };
5219 LLVMAddFunction (module, "llvm.sadd.with.overflow.i64", LLVMFunctionType (LLVMStructType (ovf_res_i64, 2, FALSE), ovf_params_i64, 2, FALSE));
5220 LLVMAddFunction (module, "llvm.uadd.with.overflow.i64", LLVMFunctionType (LLVMStructType (ovf_res_i64, 2, FALSE), ovf_params_i64, 2, FALSE));
5221 LLVMAddFunction (module, "llvm.ssub.with.overflow.i64", LLVMFunctionType (LLVMStructType (ovf_res_i64, 2, FALSE), ovf_params_i64, 2, FALSE));
5222 LLVMAddFunction (module, "llvm.usub.with.overflow.i64", LLVMFunctionType (LLVMStructType (ovf_res_i64, 2, FALSE), ovf_params_i64, 2, FALSE));
5223 LLVMAddFunction (module, "llvm.smul.with.overflow.i64", LLVMFunctionType (LLVMStructType (ovf_res_i64, 2, FALSE), ovf_params_i64, 2, FALSE));
5224 LLVMAddFunction (module, "llvm.umul.with.overflow.i64", LLVMFunctionType (LLVMStructType (ovf_res_i64, 2, FALSE), ovf_params_i64, 2, FALSE));
5229 LLVMTypeRef arg_types [2];
5230 LLVMTypeRef ret_type;
5232 arg_types [0] = LLVMPointerType (LLVMInt8Type (), 0);
5233 arg_types [1] = LLVMPointerType (LLVMInt8Type (), 0);
5234 ret_type = LLVMInt32Type ();
5236 LLVMAddFunction (module, "mono_personality", LLVMFunctionType (LLVMVoidType (), NULL, 0, FALSE));
5238 LLVMAddFunction (module, "llvm_resume_unwind_trampoline", LLVMFunctionType (LLVMVoidType (), NULL, 0, FALSE));
5241 /* SSE intrinsics */
5242 #if defined(TARGET_X86) || defined(TARGET_AMD64)
5244 LLVMTypeRef ret_type, arg_types [16];
5247 ret_type = type_to_simd_type (MONO_TYPE_I4);
5248 arg_types [0] = ret_type;
5249 arg_types [1] = ret_type;
5250 AddFunc (module, "llvm.x86.sse41.pminud", ret_type, arg_types, 2);
5251 AddFunc (module, "llvm.x86.sse41.pmaxud", ret_type, arg_types, 2);
5253 ret_type = type_to_simd_type (MONO_TYPE_I2);
5254 arg_types [0] = ret_type;
5255 arg_types [1] = ret_type;
5256 AddFunc (module, "llvm.x86.sse41.pminuw", ret_type, arg_types, 2);
5257 AddFunc (module, "llvm.x86.sse2.pmins.w", ret_type, arg_types, 2);
5258 AddFunc (module, "llvm.x86.sse41.pmaxuw", ret_type, arg_types, 2);
5259 AddFunc (module, "llvm.x86.sse2.padds.w", ret_type, arg_types, 2);
5260 AddFunc (module, "llvm.x86.sse2.psubs.w", ret_type, arg_types, 2);
5261 AddFunc (module, "llvm.x86.sse2.paddus.w", ret_type, arg_types, 2);
5262 AddFunc (module, "llvm.x86.sse2.psubus.w", ret_type, arg_types, 2);
5263 AddFunc (module, "llvm.x86.sse2.pavg.w", ret_type, arg_types, 2);
5264 AddFunc (module, "llvm.x86.sse2.pmulh.w", ret_type, arg_types, 2);
5265 AddFunc (module, "llvm.x86.sse2.pmulhu.w", ret_type, arg_types, 2);
5267 ret_type = type_to_simd_type (MONO_TYPE_I1);
5268 arg_types [0] = ret_type;
5269 arg_types [1] = ret_type;
5270 AddFunc (module, "llvm.x86.sse2.pminu.b", ret_type, arg_types, 2);
5271 AddFunc (module, "llvm.x86.sse2.pmaxu.b", ret_type, arg_types, 2);
5272 AddFunc (module, "llvm.x86.sse2.padds.b", ret_type, arg_types, 2);
5273 AddFunc (module, "llvm.x86.sse2.psubs.b", ret_type, arg_types, 2);
5274 AddFunc (module, "llvm.x86.sse2.paddus.b", ret_type, arg_types, 2);
5275 AddFunc (module, "llvm.x86.sse2.psubus.b", ret_type, arg_types, 2);
5276 AddFunc (module, "llvm.x86.sse2.pavg.b", ret_type, arg_types, 2);
5278 ret_type = type_to_simd_type (MONO_TYPE_R8);
5279 arg_types [0] = ret_type;
5280 arg_types [1] = ret_type;
5281 AddFunc (module, "llvm.x86.sse2.min.pd", ret_type, arg_types, 2);
5282 AddFunc (module, "llvm.x86.sse2.max.pd", ret_type, arg_types, 2);
5283 AddFunc (module, "llvm.x86.sse3.hadd.pd", ret_type, arg_types, 2);
5284 AddFunc (module, "llvm.x86.sse3.hsub.pd", ret_type, arg_types, 2);
5285 AddFunc (module, "llvm.x86.sse3.addsub.pd", ret_type, arg_types, 2);
5287 ret_type = type_to_simd_type (MONO_TYPE_R4);
5288 arg_types [0] = ret_type;
5289 arg_types [1] = ret_type;
5290 AddFunc (module, "llvm.x86.sse.min.ps", ret_type, arg_types, 2);
5291 AddFunc (module, "llvm.x86.sse.max.ps", ret_type, arg_types, 2);
5292 AddFunc (module, "llvm.x86.sse3.hadd.ps", ret_type, arg_types, 2);
5293 AddFunc (module, "llvm.x86.sse3.hsub.ps", ret_type, arg_types, 2);
5294 AddFunc (module, "llvm.x86.sse3.addsub.ps", ret_type, arg_types, 2);
5297 ret_type = type_to_simd_type (MONO_TYPE_I1);
5298 arg_types [0] = type_to_simd_type (MONO_TYPE_I2);
5299 arg_types [1] = type_to_simd_type (MONO_TYPE_I2);
5300 AddFunc (module, "llvm.x86.sse2.packsswb.128", ret_type, arg_types, 2);
5301 AddFunc (module, "llvm.x86.sse2.packuswb.128", ret_type, arg_types, 2);
5302 ret_type = type_to_simd_type (MONO_TYPE_I2);
5303 arg_types [0] = type_to_simd_type (MONO_TYPE_I4);
5304 arg_types [1] = type_to_simd_type (MONO_TYPE_I4);
5305 AddFunc (module, "llvm.x86.sse2.packssdw.128", ret_type, arg_types, 2);
5306 AddFunc (module, "llvm.x86.sse41.packusdw", ret_type, arg_types, 2);
5309 ret_type = type_to_simd_type (MONO_TYPE_R8);
5310 arg_types [0] = ret_type;
5311 arg_types [1] = ret_type;
5312 arg_types [2] = LLVMInt8Type ();
5313 AddFunc (module, "llvm.x86.sse2.cmp.pd", ret_type, arg_types, 3);
5314 ret_type = type_to_simd_type (MONO_TYPE_R4);
5315 arg_types [0] = ret_type;
5316 arg_types [1] = ret_type;
5317 arg_types [2] = LLVMInt8Type ();
5318 AddFunc (module, "llvm.x86.sse.cmp.ps", ret_type, arg_types, 3);
5320 /* Conversion ops */
5321 ret_type = type_to_simd_type (MONO_TYPE_R8);
5322 arg_types [0] = type_to_simd_type (MONO_TYPE_I4);
5323 AddFunc (module, "llvm.x86.sse2.cvtdq2pd", ret_type, arg_types, 1);
5324 ret_type = type_to_simd_type (MONO_TYPE_R4);
5325 arg_types [0] = type_to_simd_type (MONO_TYPE_I4);
5326 AddFunc (module, "llvm.x86.sse2.cvtdq2ps", ret_type, arg_types, 1);
5327 ret_type = type_to_simd_type (MONO_TYPE_I4);
5328 arg_types [0] = type_to_simd_type (MONO_TYPE_R8);
5329 AddFunc (module, "llvm.x86.sse2.cvtpd2dq", ret_type, arg_types, 1);
5330 ret_type = type_to_simd_type (MONO_TYPE_I4);
5331 arg_types [0] = type_to_simd_type (MONO_TYPE_R4);
5332 AddFunc (module, "llvm.x86.sse2.cvtps2dq", ret_type, arg_types, 1);
5333 ret_type = type_to_simd_type (MONO_TYPE_R4);
5334 arg_types [0] = type_to_simd_type (MONO_TYPE_R8);
5335 AddFunc (module, "llvm.x86.sse2.cvtpd2ps", ret_type, arg_types, 1);
5336 ret_type = type_to_simd_type (MONO_TYPE_R8);
5337 arg_types [0] = type_to_simd_type (MONO_TYPE_R4);
5338 AddFunc (module, "llvm.x86.sse2.cvtps2pd", ret_type, arg_types, 1);
5340 ret_type = type_to_simd_type (MONO_TYPE_I4);
5341 arg_types [0] = type_to_simd_type (MONO_TYPE_R8);
5342 AddFunc (module, "llvm.x86.sse2.cvttpd2dq", ret_type, arg_types, 1);
5343 ret_type = type_to_simd_type (MONO_TYPE_I4);
5344 arg_types [0] = type_to_simd_type (MONO_TYPE_R4);
5345 AddFunc (module, "llvm.x86.sse2.cvttps2dq", ret_type, arg_types, 1);
5348 ret_type = type_to_simd_type (MONO_TYPE_R8);
5349 arg_types [0] = ret_type;
5350 AddFunc (module, "llvm.x86.sse2.sqrt.pd", ret_type, arg_types, 1);
5351 ret_type = type_to_simd_type (MONO_TYPE_R4);
5352 arg_types [0] = ret_type;
5353 AddFunc (module, "llvm.x86.sse.sqrt.ps", ret_type, arg_types, 1);
5354 ret_type = type_to_simd_type (MONO_TYPE_R4);
5355 arg_types [0] = ret_type;
5356 AddFunc (module, "llvm.x86.sse.rsqrt.ps", ret_type, arg_types, 1);
5357 ret_type = type_to_simd_type (MONO_TYPE_R4);
5358 arg_types [0] = ret_type;
5359 AddFunc (module, "llvm.x86.sse.rcp.ps", ret_type, arg_types, 1);
5362 ret_type = type_to_simd_type (MONO_TYPE_I2);
5363 arg_types [0] = ret_type;
5364 arg_types [1] = LLVMInt32Type ();
5365 AddFunc (module, "llvm.x86.sse2.psrli.w", ret_type, arg_types, 2);
5366 AddFunc (module, "llvm.x86.sse2.psrai.w", ret_type, arg_types, 2);
5367 AddFunc (module, "llvm.x86.sse2.pslli.w", ret_type, arg_types, 2);
5368 ret_type = type_to_simd_type (MONO_TYPE_I4);
5369 arg_types [0] = ret_type;
5370 arg_types [1] = LLVMInt32Type ();
5371 AddFunc (module, "llvm.x86.sse2.psrli.d", ret_type, arg_types, 2);
5372 AddFunc (module, "llvm.x86.sse2.psrai.d", ret_type, arg_types, 2);
5373 AddFunc (module, "llvm.x86.sse2.pslli.d", ret_type, arg_types, 2);
5374 ret_type = type_to_simd_type (MONO_TYPE_I8);
5375 arg_types [0] = ret_type;
5376 arg_types [1] = LLVMInt32Type ();
5377 AddFunc (module, "llvm.x86.sse2.psrli.q", ret_type, arg_types, 2);
5378 AddFunc (module, "llvm.x86.sse2.pslli.q", ret_type, arg_types, 2);
5381 ret_type = LLVMInt32Type ();
5382 arg_types [0] = type_to_simd_type (MONO_TYPE_I1);
5383 AddFunc (module, "llvm.x86.sse2.pmovmskb.128", ret_type, arg_types, 1);
5386 AddFunc (module, "llvm.x86.sse2.pause", LLVMVoidType (), NULL, 0);
5389 /* Load/Store intrinsics */
5391 LLVMTypeRef arg_types [5];
5395 for (i = 1; i <= 8; i *= 2) {
5396 arg_types [0] = LLVMPointerType (LLVMIntType (i * 8), 0);
5397 arg_types [1] = LLVMInt32Type ();
5398 arg_types [2] = LLVMInt1Type ();
5399 #if LLVM_API_VERSION >= 4
5400 arg_types [3] = LLVMInt32Type ();
5402 sprintf (name, "llvm.mono.load.i%d.p0i%d", i * 8, i * 8);
5403 LLVMAddFunction (module, name, LLVMFunctionType (LLVMIntType (i * 8), arg_types, 3 + EXTRA_MONO_LOAD_STORE_ARGS, FALSE));
5405 arg_types [0] = LLVMIntType (i * 8);
5406 arg_types [1] = LLVMPointerType (LLVMIntType (i * 8), 0);
5407 arg_types [2] = LLVMInt32Type ();
5408 arg_types [3] = LLVMInt1Type ();
5409 #if LLVM_API_VERSION >= 4
5410 arg_types [4] = LLVMInt32Type ();
5412 sprintf (name, "llvm.mono.store.i%d.p0i%d", i * 8, i * 8);
5413 LLVMAddFunction (module, name, LLVMFunctionType (LLVMVoidType (), arg_types, 4 + EXTRA_MONO_LOAD_STORE_ARGS, FALSE));
5419 add_types (MonoLLVMModule *lmodule)
5421 lmodule->ptr_type = LLVMPointerType (sizeof (gpointer) == 8 ? LLVMInt64Type () : LLVMInt32Type (), 0);
5425 mono_llvm_init (void)
5427 mono_native_tls_alloc (¤t_cfg_tls_id, NULL);
5431 init_jit_module (MonoDomain *domain)
5433 MonoJitICallInfo *info;
5434 MonoJitDomainInfo *dinfo;
5435 MonoLLVMModule *module;
5438 dinfo = domain_jit_info (domain);
5439 if (dinfo->llvm_module)
5442 mono_loader_lock ();
5444 if (dinfo->llvm_module) {
5445 mono_loader_unlock ();
5449 module = g_new0 (MonoLLVMModule, 1);
5451 name = g_strdup_printf ("mono-%s", domain->friendly_name);
5452 module->module = LLVMModuleCreateWithName (name);
5454 module->mono_ee = mono_llvm_create_ee (LLVMCreateModuleProviderForExistingModule (module->module), alloc_cb, emitted_cb, exception_cb, dlsym_cb, &module->ee);
5456 add_intrinsics (module->module);
5459 module->llvm_types = g_hash_table_new (NULL, NULL);
5461 info = mono_find_jit_icall_by_name ("llvm_resume_unwind_trampoline");
5463 LLVMAddGlobalMapping (module->ee, LLVMGetNamedFunction (module->module, "llvm_resume_unwind_trampoline"), (void*)info->func);
5465 mono_memory_barrier ();
5467 dinfo->llvm_module = module;
5469 mono_loader_unlock ();
5473 mono_llvm_cleanup (void)
5475 if (aot_module.module)
5476 LLVMDisposeModule (aot_module.module);
5478 LLVMContextDispose (LLVMGetGlobalContext ());
5482 mono_llvm_free_domain_info (MonoDomain *domain)
5484 MonoJitDomainInfo *info = domain_jit_info (domain);
5485 MonoLLVMModule *module = info->llvm_module;
5491 if (module->llvm_types)
5492 g_hash_table_destroy (module->llvm_types);
5494 mono_llvm_dispose_ee (module->mono_ee);
5496 if (module->bb_names) {
5497 for (i = 0; i < module->bb_names_len; ++i)
5498 g_free (module->bb_names [i]);
5499 g_free (module->bb_names);
5501 //LLVMDisposeModule (module->module);
5505 info->llvm_module = NULL;
5509 mono_llvm_create_aot_module (const char *got_symbol, gboolean external_symbols, gboolean emit_dwarf)
5511 /* Delete previous module */
5512 if (aot_module.plt_entries)
5513 g_hash_table_destroy (aot_module.plt_entries);
5514 if (aot_module.module)
5515 LLVMDisposeModule (aot_module.module);
5517 memset (&aot_module, 0, sizeof (aot_module));
5519 aot_module.module = LLVMModuleCreateWithName ("aot");
5520 aot_module.got_symbol = got_symbol;
5521 aot_module.external_symbols = external_symbols;
5522 aot_module.emit_dwarf = emit_dwarf;
5523 /* The first few entries are reserved */
5524 aot_module.max_got_offset = 16;
5526 add_intrinsics (aot_module.module);
5527 add_types (&aot_module);
5531 * We couldn't compute the type of the LLVM global representing the got because
5532 * its size is only known after all the methods have been emitted. So create
5533 * a dummy variable, and replace all uses it with the real got variable when
5534 * its size is known in mono_llvm_emit_aot_module ().
5537 LLVMTypeRef got_type = LLVMArrayType (aot_module.ptr_type, 0);
5539 aot_module.got_var = LLVMAddGlobal (aot_module.module, got_type, "mono_dummy_got");
5540 LLVMSetInitializer (aot_module.got_var, LLVMConstNull (got_type));
5543 /* Add a dummy personality function */
5545 LLVMBasicBlockRef lbb;
5546 LLVMBuilderRef lbuilder;
5547 LLVMValueRef personality;
5549 personality = LLVMAddFunction (aot_module.module, "mono_aot_personality", LLVMFunctionType (LLVMVoidType (), NULL, 0, FALSE));
5550 LLVMSetLinkage (personality, LLVMInternalLinkage);
5551 lbb = LLVMAppendBasicBlock (personality, "BB0");
5552 lbuilder = LLVMCreateBuilder ();
5553 LLVMPositionBuilderAtEnd (lbuilder, lbb);
5554 LLVMBuildRetVoid (lbuilder);
5557 aot_module.llvm_types = g_hash_table_new (NULL, NULL);
5558 aot_module.plt_entries = g_hash_table_new (g_str_hash, g_str_equal);
5559 aot_module.plt_entries_ji = g_hash_table_new (NULL, NULL);
5560 aot_module.method_to_lmethod = g_hash_table_new (NULL, NULL);
5564 * Emit the aot module into the LLVM bitcode file FILENAME.
5567 mono_llvm_emit_aot_module (const char *filename, const char *cu_name)
5569 LLVMTypeRef got_type;
5570 LLVMValueRef real_got;
5571 MonoLLVMModule *module = &aot_module;
5574 * Create the real got variable and replace all uses of the dummy variable with
5577 got_type = LLVMArrayType (aot_module.ptr_type, module->max_got_offset + 1);
5578 real_got = LLVMAddGlobal (aot_module.module, got_type, aot_module.got_symbol);
5579 LLVMSetInitializer (real_got, LLVMConstNull (got_type));
5580 if (module->external_symbols) {
5581 LLVMSetLinkage (real_got, LLVMExternalLinkage);
5582 LLVMSetVisibility (real_got, LLVMHiddenVisibility);
5584 LLVMSetLinkage (real_got, LLVMInternalLinkage);
5586 mono_llvm_replace_uses_of (aot_module.got_var, real_got);
5588 mark_as_used (&aot_module, real_got);
5590 /* Delete the dummy got so it doesn't become a global */
5591 LLVMDeleteGlobal (aot_module.got_var);
5593 emit_llvm_used (&aot_module);
5594 emit_dbg_info (&aot_module, filename, cu_name);
5596 /* Replace PLT entries for directly callable methods with the methods themselves */
5598 GHashTableIter iter;
5600 LLVMValueRef callee;
5602 g_hash_table_iter_init (&iter, aot_module.plt_entries_ji);
5603 while (g_hash_table_iter_next (&iter, (void**)&ji, (void**)&callee)) {
5604 if (mono_aot_is_direct_callable (ji)) {
5605 LLVMValueRef lmethod;
5607 lmethod = g_hash_table_lookup (module->method_to_lmethod, ji->data.method);
5608 /* The types might not match because the caller might pass an rgctx */
5609 if (lmethod && LLVMTypeOf (callee) == LLVMTypeOf (lmethod)) {
5610 mono_llvm_replace_uses_of (callee, lmethod);
5611 mono_aot_mark_unused_llvm_plt_entry (ji);
5621 if (LLVMVerifyModule (aot_module.module, LLVMReturnStatusAction, &verifier_err)) {
5622 g_assert_not_reached ();
5627 LLVMWriteBitcodeToFile (aot_module.module, filename);
5632 md_string (const char *s)
5634 return LLVMMDString (s, strlen (s));
5637 /* Debugging support */
5640 emit_dbg_info (MonoLLVMModule *lmodule, const char *filename, const char *cu_name)
5642 LLVMModuleRef module = lmodule->module;
5643 LLVMValueRef args [16], cu_args [16], cu, ver;
5645 char *build_info, *s, *dir;
5648 * This can only be enabled when LLVM code is emitted into a separate object
5649 * file, since the AOT compiler also emits dwarf info,
5650 * and the abbrev indexes will not be correct since llvm has added its own
5653 if (!lmodule->emit_dwarf)
5657 * Emit dwarf info in the form of LLVM metadata. There is some
5658 * out-of-date documentation at:
5659 * http://llvm.org/docs/SourceLevelDebugging.html
5660 * but most of this was gathered from the llvm and
5665 cu_args [n_cuargs ++] = LLVMConstInt (LLVMInt32Type (), DW_TAG_compile_unit, FALSE);
5666 /* CU name/compilation dir */
5667 dir = g_path_get_dirname (filename);
5668 args [0] = LLVMMDString (cu_name, strlen (cu_name));
5669 args [1] = LLVMMDString (dir, strlen (dir));
5670 cu_args [n_cuargs ++] = LLVMMDNode (args, 2);
5673 cu_args [n_cuargs ++] = LLVMConstInt (LLVMInt32Type (), DW_LANG_C99, FALSE);
5675 build_info = mono_get_runtime_build_info ();
5676 s = g_strdup_printf ("Mono AOT Compiler %s (LLVM)", build_info);
5677 cu_args [n_cuargs ++] = LLVMMDString (s, strlen (s));
5678 g_free (build_info);
5680 cu_args [n_cuargs ++] = LLVMConstInt (LLVMInt32Type (), 1, FALSE);
5682 cu_args [n_cuargs ++] = LLVMMDString ("", strlen (""));
5683 /* Runtime version */
5684 cu_args [n_cuargs ++] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
5686 cu_args [n_cuargs ++] = LLVMMDNode (args, 0);
5687 cu_args [n_cuargs ++] = LLVMMDNode (args, 0);
5689 if (lmodule->subprogram_mds) {
5693 mds = g_new0 (LLVMValueRef, lmodule->subprogram_mds->len);
5694 for (i = 0; i < lmodule->subprogram_mds->len; ++i)
5695 mds [i] = g_ptr_array_index (lmodule->subprogram_mds, i);
5696 cu_args [n_cuargs ++] = LLVMMDNode (mds, lmodule->subprogram_mds->len);
5698 cu_args [n_cuargs ++] = LLVMMDNode (args, 0);
5701 cu_args [n_cuargs ++] = LLVMMDNode (args, 0);
5702 /* Imported modules */
5703 cu_args [n_cuargs ++] = LLVMMDNode (args, 0);
5705 cu_args [n_cuargs ++] = LLVMMDString ("", strlen (""));
5706 /* DebugEmissionKind = FullDebug */
5707 cu_args [n_cuargs ++] = LLVMConstInt (LLVMInt32Type (), 1, FALSE);
5708 cu = LLVMMDNode (cu_args, n_cuargs);
5709 LLVMAddNamedMetadataOperand (module, "llvm.dbg.cu", cu);
5711 args [0] = LLVMConstInt (LLVMInt32Type (), 1, FALSE);
5712 args [1] = LLVMMDString ("Dwarf Version", strlen ("Dwarf Version"));
5713 args [2] = LLVMConstInt (LLVMInt32Type (), 2, FALSE);
5714 ver = LLVMMDNode (args, 3);
5715 LLVMAddNamedMetadataOperand (module, "llvm.module.flags", ver);
5717 args [0] = LLVMConstInt (LLVMInt32Type (), 1, FALSE);
5718 args [1] = LLVMMDString ("Debug Info Version", strlen ("Debug Info Version"));
5719 args [2] = LLVMConstInt (LLVMInt32Type (), 1, FALSE);
5720 ver = LLVMMDNode (args, 3);
5721 LLVMAddNamedMetadataOperand (module, "llvm.module.flags", ver);
5725 emit_dbg_subprogram (EmitContext *ctx, MonoCompile *cfg, LLVMValueRef method, const char *name)
5727 MonoLLVMModule *module = ctx->lmodule;
5728 MonoDebugMethodInfo *minfo = ctx->minfo;
5729 char *source_file, *dir, *filename;
5730 LLVMValueRef md, args [16], ctx_args [16], md_args [64], type_args [16], ctx_md, type_md;
5738 mono_debug_symfile_get_line_numbers_full (minfo, &source_file, NULL, &n_il_offsets, &il_offsets, &line_numbers, NULL, NULL, NULL, NULL);
5740 source_file = g_strdup ("<unknown>");
5741 dir = g_path_get_dirname (source_file);
5742 filename = g_path_get_basename (source_file);
5744 ctx_args [0] = LLVMConstInt (LLVMInt32Type (), 0x29, FALSE);
5745 args [0] = md_string (filename);
5746 args [1] = md_string (dir);
5747 ctx_args [1] = LLVMMDNode (args, 2);
5748 ctx_md = LLVMMDNode (ctx_args, 2);
5750 type_args [0] = LLVMConstInt (LLVMInt32Type (), DW_TAG_subroutine_type, FALSE);
5751 type_args [1] = NULL;
5752 type_args [2] = NULL;
5753 type_args [3] = LLVMMDString ("", 0);
5754 type_args [4] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
5755 type_args [5] = LLVMConstInt (LLVMInt64Type (), 0, FALSE);
5756 type_args [6] = LLVMConstInt (LLVMInt64Type (), 0, FALSE);
5757 type_args [7] = LLVMConstInt (LLVMInt64Type (), 0, FALSE);
5758 type_args [8] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
5759 type_args [9] = NULL;
5760 type_args [10] = NULL;
5761 type_args [11] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
5762 type_args [12] = NULL;
5763 type_args [13] = NULL;
5764 type_args [14] = NULL;
5765 type_md = LLVMMDNode (type_args, 14);
5767 /* http://llvm.org/docs/SourceLevelDebugging.html#subprogram-descriptors */
5768 md_args [0] = LLVMConstInt (LLVMInt32Type (), DW_TAG_subprogram, FALSE);
5769 /* Source directory + file pair */
5770 args [0] = md_string (filename);
5771 args [1] = md_string (dir);
5772 md_args [1] = LLVMMDNode (args ,2);
5773 md_args [2] = ctx_md;
5774 md_args [3] = md_string (cfg->method->name);
5775 md_args [4] = md_string (name);
5776 md_args [5] = md_string (name);
5779 md_args [6] = LLVMConstInt (LLVMInt32Type (), line_numbers [0], FALSE);
5781 md_args [6] = LLVMConstInt (LLVMInt32Type (), 1, FALSE);
5783 md_args [7] = type_md;
5785 md_args [8] = LLVMConstInt (LLVMInt1Type (), 0, FALSE);
5787 md_args [9] = LLVMConstInt (LLVMInt1Type (), 1, FALSE);
5789 md_args [10] = LLVMConstInt (LLVMInt32Type (), 0, FALSE);
5790 /* Index into a virtual function */
5791 md_args [11] = NULL;
5792 md_args [12] = NULL;
5794 md_args [13] = LLVMConstInt (LLVMInt1Type (), 0, FALSE);
5796 md_args [14] = LLVMConstInt (LLVMInt1Type (), 1, FALSE);
5797 /* Pointer to LLVM function */
5798 md_args [15] = method;
5799 /* Function template parameter */
5800 md_args [16] = NULL;
5801 /* Function declaration descriptor */
5802 md_args [17] = NULL;
5803 /* List of function variables */
5804 md_args [18] = LLVMMDNode (args, 0);
5806 md_args [19] = LLVMConstInt (LLVMInt32Type (), 1, FALSE);
5807 md = LLVMMDNode (md_args, 20);
5809 if (!module->subprogram_mds)
5810 module->subprogram_mds = g_ptr_array_new ();
5811 g_ptr_array_add (module->subprogram_mds, md);
5815 g_free (source_file);
5816 g_free (il_offsets);
5817 g_free (line_numbers);
5823 emit_dbg_loc (EmitContext *ctx, LLVMBuilderRef builder, const unsigned char *cil_code)
5825 MonoCompile *cfg = ctx->cfg;
5827 if (ctx->minfo && cil_code && cil_code >= cfg->header->code && cil_code < cfg->header->code + cfg->header->code_size) {
5828 MonoDebugSourceLocation *loc;
5829 LLVMValueRef loc_md, md_args [16];
5832 loc = mono_debug_symfile_lookup_location (ctx->minfo, cil_code - cfg->header->code);
5836 md_args [nmd_args ++] = LLVMConstInt (LLVMInt32Type (), loc->row, FALSE);
5837 md_args [nmd_args ++] = LLVMConstInt (LLVMInt32Type (), loc->column, FALSE);
5838 md_args [nmd_args ++] = ctx->dbg_md;
5839 md_args [nmd_args ++] = NULL;
5840 loc_md = LLVMMDNode (md_args, nmd_args);
5841 LLVMSetCurrentDebugLocation (builder, loc_md);
5842 mono_debug_symfile_free_location (loc);
5849 - Emit LLVM IR from the mono IR using the LLVM C API.
5850 - The original arch specific code remains, so we can fall back to it if we run
5851 into something we can't handle.
5855 A partial list of issues:
5856 - Handling of opcodes which can throw exceptions.
5858 In the mono JIT, these are implemented using code like this:
5865 push throw_pos - method
5866 call <exception trampoline>
5868 The problematic part is push throw_pos - method, which cannot be represented
5869 in the LLVM IR, since it does not support label values.
5870 -> this can be implemented in AOT mode using inline asm + labels, but cannot
5871 be implemented in JIT mode ?
5872 -> a possible but slower implementation would use the normal exception
5873 throwing code but it would need to control the placement of the throw code
5874 (it needs to be exactly after the compare+branch).
5875 -> perhaps add a PC offset intrinsics ?
5877 - efficient implementation of .ovf opcodes.
5879 These are currently implemented as:
5880 <ins which sets the condition codes>
5883 Some overflow opcodes are now supported by LLVM SVN.
5885 - exception handling, unwinding.
5886 - SSA is disabled for methods with exception handlers
5887 - How to obtain unwind info for LLVM compiled methods ?
5888 -> this is now solved by converting the unwind info generated by LLVM
5890 - LLVM uses the c++ exception handling framework, while we use our home grown
5891 code, and couldn't use the c++ one:
5892 - its not supported under VC++, other exotic platforms.
5893 - it might be impossible to support filter clauses with it.
5897 The trampolines need a predictable call sequence, since they need to disasm
5898 the calling code to obtain register numbers / offsets.
5900 LLVM currently generates this code in non-JIT mode:
5901 mov -0x98(%rax),%eax
5903 Here, the vtable pointer is lost.
5904 -> solution: use one vtable trampoline per class.
5906 - passing/receiving the IMT pointer/RGCTX.
5907 -> solution: pass them as normal arguments ?
5911 LLVM does not allow the specification of argument registers etc. This means
5912 that all calls are made according to the platform ABI.
5914 - passing/receiving vtypes.
5916 Vtypes passed/received in registers are handled by the front end by using
5917 a signature with scalar arguments, and loading the parts of the vtype into those
5920 Vtypes passed on the stack are handled using the 'byval' attribute.
5924 Supported though alloca, we need to emit the load/store code.
5928 The mono JIT uses pointer sized iregs/double fregs, while LLVM uses precisely
5929 typed registers, so we have to keep track of the precise LLVM type of each vreg.
5930 This is made easier because the IR is already in SSA form.
5931 An additional problem is that our IR is not consistent with types, i.e. i32/ia64
5932 types are frequently used incorrectly.
5937 Emit LLVM bytecode into a .bc file, compile it using llc into a .s file, then
5938 append the AOT data structures to that file. For methods which cannot be
5939 handled by LLVM, the normal JIT compiled versions are used.
5942 /* FIXME: Normalize some aspects of the mono IR to allow easier translation, like:
5943 * - each bblock should end with a branch
5944 * - setting the return value, making cfg->ret non-volatile
5945 * - avoid some transformations in the JIT which make it harder for us to generate
5947 * - use pointer types to help optimizations.