Skip to content

Commit 5e0d3c9

Browse files
committed
fix compilation error in JIT and potentially load nullptr
1 parent 9a71956 commit 5e0d3c9

File tree

2 files changed

+71
-31
lines changed

2 files changed

+71
-31
lines changed

core/iwasm/compilation/aot_emit_memory.c

Lines changed: 28 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -145,6 +145,7 @@ ffs(int n)
145145
static LLVMValueRef
146146
get_memory_curr_page_count(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx);
147147

148+
#if WASM_ENABLE_SHARED_HEAP != 0
148149
uint32
149150
get_module_inst_extra_offset(AOTCompContext *comp_ctx);
150151

@@ -192,8 +193,7 @@ get_module_inst_extra_offset(AOTCompContext *comp_ctx);
192193
BUILD_LOAD_PTR(field_p, data_type, res); \
193194
} while (0)
194195

195-
/* Only update last used shared heap info(alloc ptr) in function ctx,
196-
* let runtime API update module inst shared heap info
196+
/* Update last used shared heap info(alloc ptr) in function ctx:
197197
* 1. shared_heap_start_off 2. shared_heap_end_off 3. shared_heap_base_addr_adj
198198
*/
199199
bool
@@ -224,7 +224,6 @@ aot_check_shared_heap_chain(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
224224

225225
/* Call function */
226226
param_values[0] = func_ctx->aot_inst;
227-
/* TODO: all use alloca to optimize the func call to single basic block? */
228227
param_values[1] = start_offset;
229228
param_values[2] = bytes;
230229
/* pass alloc ptr */
@@ -299,26 +298,12 @@ aot_check_shared_heap_memory_overflow_common(
299298
else
300299
LLVMMoveBasicBlockAfter(block_maddr_phi, check_succ);
301300

302-
// BUILD_LOAD_PTR(func_ctx->shared_heap_start_off, offset_type,
303-
// shared_heap_start_off);
304-
// BUILD_ICMP(LLVMIntUGE, start_offset, shared_heap_start_off,
305-
// is_in_shared_heap, "shared_heap_lb_cmp");
306-
BUILD_ICMP(LLVMIntUGE, start_offset, func_ctx->shared_heap_head_start_off,
301+
/* Use >= here for func_ctx->shared_heap_head_start_off =
302+
* shared_heap_head->start - 1 and use UINT32_MAX/UINT64_MAX value to
303+
* indicate invalid value. The shared heap chain oob will be detected in
304+
* app_addr_in_shared_heap block or aot_check_shared_heap_chain function */
305+
BUILD_ICMP(LLVMIntUGT, start_offset, func_ctx->shared_heap_head_start_off,
307306
is_in_shared_heap, "shared_heap_lb_cmp");
308-
/* For bulk memory previously already check whether start_offset + bytes
309-
* overflows, can safely omit the upper boundary check */
310-
if (!bulk_memory) {
311-
shared_heap_check_bound =
312-
is_memory64
313-
? I64_CONST(UINT64_MAX - bytes_u32 + 1)
314-
: (is_target_64bit ? I64_CONST(UINT32_MAX - bytes_u32 + 1)
315-
: I32_CONST(UINT32_MAX - bytes_u32 + 1));
316-
CHECK_LLVM_CONST(shared_heap_check_bound);
317-
BUILD_ICMP(LLVMIntULE, start_offset, shared_heap_check_bound, cmp,
318-
"shared_heap_ub_cmp");
319-
BUILD_OP(And, is_in_shared_heap, cmp, is_in_shared_heap,
320-
"is_in_shared_heap");
321-
}
322307
BUILD_COND_BR(is_in_shared_heap, app_addr_in_shared_heap_chain,
323308
app_addr_in_linear_mem);
324309

@@ -435,6 +420,7 @@ aot_check_bulk_memory_shared_heap_memory_overflow(
435420
start_offset, max_addr, NULL, bytes, 0, is_memory64, is_target_64bit,
436421
true, false);
437422
}
423+
#endif
438424

439425
LLVMValueRef
440426
aot_check_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
@@ -443,10 +429,10 @@ aot_check_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
443429
{
444430
LLVMValueRef offset_const =
445431
MEMORY64_COND_VALUE(I64_CONST(offset), I32_CONST(offset));
446-
LLVMValueRef addr, maddr, maddr_phi = NULL, offset1, cmp1, cmp;
432+
LLVMValueRef addr, maddr, offset1, cmp1, cmp;
447433
LLVMValueRef mem_base_addr, mem_check_bound;
448434
LLVMBasicBlockRef block_curr = LLVMGetInsertBlock(comp_ctx->builder);
449-
LLVMBasicBlockRef check_succ, block_maddr_phi = NULL;
435+
LLVMBasicBlockRef check_succ;
450436
AOTValue *aot_value_top;
451437
uint32 local_idx_of_aot_value = 0;
452438
uint64 const_value;
@@ -461,6 +447,10 @@ aot_check_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
461447
#else
462448
bool is_memory64 = IS_MEMORY64;
463449
#endif
450+
#if WASM_ENABLE_SHARED_HEAP != 0
451+
LLVMValueRef maddr_phi = NULL;
452+
LLVMBasicBlockRef block_maddr_phi = NULL;
453+
#endif
464454

465455
is_target_64bit = (comp_ctx->pointer_size == sizeof(uint64)) ? true : false;
466456

@@ -626,6 +616,7 @@ aot_check_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
626616
block_curr = check_integer_overflow_end;
627617
}
628618

619+
#if WASM_ENABLE_SHARED_HEAP != 0
629620
if (comp_ctx->enable_shared_heap /* TODO: && mem_idx == 0 */) {
630621
ADD_BASIC_BLOCK(block_maddr_phi, "maddr_phi");
631622
SET_BUILD_POS(block_maddr_phi);
@@ -645,6 +636,7 @@ aot_check_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
645636
goto fail;
646637
}
647638
}
639+
#endif
648640

649641
if (comp_ctx->enable_bound_check
650642
&& !(is_local_of_aot_value
@@ -723,6 +715,7 @@ aot_check_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
723715
}
724716
}
725717

718+
#if WASM_ENABLE_SHARED_HEAP != 0
726719
if (comp_ctx->enable_shared_heap /* TODO: && mem_idx == 0 */) {
727720
block_curr = LLVMGetInsertBlock(comp_ctx->builder);
728721
LLVMAddIncoming(maddr_phi, &maddr, &block_curr, 1);
@@ -734,6 +727,7 @@ aot_check_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
734727
return maddr_phi;
735728
}
736729
else
730+
#endif
737731
return maddr;
738732
fail:
739733
return NULL;
@@ -1356,16 +1350,20 @@ check_bulk_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
13561350
LLVMValueRef offset, LLVMValueRef bytes)
13571351
{
13581352
LLVMValueRef maddr, max_addr, cmp, cmp1;
1359-
LLVMValueRef mem_base_addr, maddr_phi = NULL;
1353+
LLVMValueRef mem_base_addr;
13601354
LLVMBasicBlockRef block_curr = LLVMGetInsertBlock(comp_ctx->builder);
1361-
LLVMBasicBlockRef check_succ, block_maddr_phi = NULL;
1355+
LLVMBasicBlockRef check_succ;
13621356
LLVMValueRef mem_size;
13631357
bool is_target_64bit;
13641358
#if WASM_ENABLE_MEMORY64 == 0
13651359
bool is_memory64 = false;
13661360
#else
13671361
bool is_memory64 = IS_MEMORY64;
13681362
#endif
1363+
#if WASM_ENABLE_SHARED_HEAP != 0
1364+
LLVMValueRef maddr_phi = NULL;
1365+
LLVMBasicBlockRef block_maddr_phi = NULL;
1366+
#endif
13691367

13701368
is_target_64bit = (comp_ctx->pointer_size == sizeof(uint64)) ? true : false;
13711369

@@ -1466,6 +1464,7 @@ check_bulk_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
14661464
block_curr = check_integer_overflow_end;
14671465
}
14681466

1467+
#if WASM_ENABLE_SHARED_HEAP != 0
14691468
if (comp_ctx->enable_shared_heap /* TODO: && mem_idx == 0 */) {
14701469
ADD_BASIC_BLOCK(block_maddr_phi, "maddr_phi");
14711470
SET_BUILD_POS(block_maddr_phi);
@@ -1483,6 +1482,7 @@ check_bulk_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
14831482
goto fail;
14841483
}
14851484
}
1485+
#endif
14861486

14871487
/* mem_size is always 64-bit, extend max_addr on 32 bits platform */
14881488
if (!is_target_64bit
@@ -1506,6 +1506,7 @@ check_bulk_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
15061506
goto fail;
15071507
}
15081508

1509+
#if WASM_ENABLE_SHARED_HEAP != 0
15091510
if (comp_ctx->enable_shared_heap /* TODO: && mem_idx == 0 */) {
15101511
block_curr = LLVMGetInsertBlock(comp_ctx->builder);
15111512
LLVMAddIncoming(maddr_phi, &maddr, &block_curr, 1);
@@ -1517,6 +1518,7 @@ check_bulk_memory_overflow(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
15171518
return maddr_phi;
15181519
}
15191520
else
1521+
#endif
15201522
return maddr;
15211523
fail:
15221524
return NULL;

core/iwasm/compilation/aot_llvm.c

Lines changed: 43 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1518,6 +1518,14 @@ create_memory_info(const AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
15181518
return true;
15191519
}
15201520

1521+
#define BUILD_IS_NOT_NULL(value, res, name) \
1522+
do { \
1523+
if (!(res = LLVMBuildIsNotNull(comp_ctx->builder, value, name))) { \
1524+
aot_set_last_error("llvm build is not null failed."); \
1525+
goto fail; \
1526+
} \
1527+
} while (0)
1528+
15211529
#define LOAD_MODULE_EXTRA_FIELD_AND_ALLOCA(field, type) \
15221530
do { \
15231531
get_module_extra_field_offset(field); \
@@ -1548,8 +1556,10 @@ create_memory_info(const AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
15481556
static bool
15491557
create_shared_heap_info(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx)
15501558
{
1559+
#if WASM_ENABLE_SHARED_HEAP != 0
15511560
LLVMValueRef offset, field_p, load_val, shared_heap_head_p,
1552-
shared_heap_head;
1561+
shared_heap_head, cmp, field_p_or_default, shared_heap_head_start_off,
1562+
shared_heap_head_start_off_minus_one;
15531563
LLVMTypeRef shared_heap_offset_type;
15541564
uint32 offset_u32;
15551565
#if WASM_ENABLE_MEMORY64 == 0
@@ -1587,6 +1597,7 @@ create_shared_heap_info(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx)
15871597
aot_set_last_error("llvm build load failed");
15881598
goto fail;
15891599
}
1600+
BUILD_IS_NOT_NULL(shared_heap_head, cmp, "has_shared_heap");
15901601

15911602
if (is_memory64) {
15921603
offset_u32 = offsetof(WASMSharedHeap, start_off_mem64);
@@ -1602,16 +1613,43 @@ create_shared_heap_info(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx)
16021613
aot_set_last_error("llvm build inbounds gep failed");
16031614
goto fail;
16041615
}
1605-
if (!(func_ctx->shared_heap_head_start_off =
1606-
LLVMBuildLoad2(comp_ctx->builder, shared_heap_offset_type,
1607-
field_p, "shared_heap_head_start_off"))) {
1616+
1617+
/* Select shared heap head ptr or safe alloca
1618+
* shared_heap_start_off(UINT32_MAX/UINT64_MAX) based on the condition */
1619+
if (!(field_p_or_default = LLVMBuildSelect(comp_ctx->builder, cmp, field_p,
1620+
func_ctx->shared_heap_start_off,
1621+
"ptr_or_default"))) {
1622+
aot_set_last_error("llvm build select failed");
1623+
goto fail;
1624+
}
1625+
1626+
if (!(shared_heap_head_start_off = LLVMBuildLoad2(
1627+
comp_ctx->builder, shared_heap_offset_type, field_p_or_default,
1628+
"shared_heap_head_start_off"))) {
1629+
aot_set_last_error("llvm build load failed");
1630+
goto fail;
1631+
}
1632+
if (!(shared_heap_head_start_off_minus_one = LLVMBuildAdd(
1633+
comp_ctx->builder, shared_heap_head_start_off,
1634+
comp_ctx->pointer_size == sizeof(uint64) ? I64_NEG_ONE
1635+
: I32_NEG_ONE,
1636+
"head_start_off_minus_one"))) {
16081637
aot_set_last_error("llvm build load failed");
16091638
goto fail;
16101639
}
16111640

1641+
if (!(func_ctx->shared_heap_head_start_off = LLVMBuildSelect(
1642+
comp_ctx->builder, cmp, shared_heap_head_start_off_minus_one,
1643+
shared_heap_head_start_off, "head_start_off"))) {
1644+
aot_set_last_error("llvm build select failed");
1645+
goto fail;
1646+
}
16121647
return true;
16131648
fail:
16141649
return false;
1650+
#else
1651+
return true;
1652+
#endif
16151653
}
16161654

16171655
static bool
@@ -2466,7 +2504,7 @@ jit_stack_size_callback(void *user_data, const char *name, size_t namelen,
24662504
stack_consumption_to_call_wrapped_func =
24672505
musttail ? 0
24682506
: aot_estimate_stack_usage_for_function_call(
2469-
comp_ctx, func_ctx->aot_func->func_type);
2507+
comp_ctx, func_ctx->aot_func->func_type);
24702508
LOG_VERBOSE("func %.*s stack %u + %zu + %u", (int)namelen, name,
24712509
stack_consumption_to_call_wrapped_func, stack_size, call_size);
24722510

0 commit comments

Comments
 (0)