diff --git a/integration_tests/test_list_03.py b/integration_tests/test_list_03.py index ee7c33b86a..40f74cc7e3 100644 --- a/integration_tests/test_list_03.py +++ b/integration_tests/test_list_03.py @@ -24,6 +24,23 @@ def test_list_insert_02(x: list[i32], n: i32) -> list[i32]: return x +def test_list_insert_03(): + l1:list[str] = ["a", "b", "c", "d"] + l2:list[str] = [] + l1.insert(5,"e") + s:str = "a" + i:i32 = 0 + for i in range(len(l1)): + assert l1[i] == chr(ord(s)+i) + +def test_list_insert_04(): + l:list[i32] = [1, 2, 3, 4, 5] + i:i32 + l.insert(6,6) + l.insert(100,7) + for i in range(1,8): + assert l[i-1] == i + def test_list_02(n: i32) -> i32: x: list[i32] = [50, 1] acc: i32 = 0 @@ -60,5 +77,7 @@ def verify(): assert test_list_01(11) == 55 assert test_list_02(50) == 3628 test_list_02_string() + test_list_insert_03() + test_list_insert_04() verify() diff --git a/src/libasr/codegen/llvm_utils.cpp b/src/libasr/codegen/llvm_utils.cpp index bc790d5974..381c13e153 100644 --- a/src/libasr/codegen/llvm_utils.cpp +++ b/src/libasr/codegen/llvm_utils.cpp @@ -2344,7 +2344,17 @@ namespace LCompilers { llvm::Type* el_type = std::get<2>(typecode2listtype[type_code]); resize_if_needed(list, current_end_point, current_capacity, type_size, el_type, module); - + llvm::Value* adjusted_pos = builder->CreateSelect( + builder->CreateICmpSGT(pos, current_end_point), + current_end_point, + pos + ); + adjusted_pos = builder->CreateSelect( + builder->CreateICmpSGE(adjusted_pos, llvm::ConstantInt::get(context, llvm::APInt(32, 0))), + adjusted_pos, + llvm::ConstantInt::get(context, llvm::APInt(32, 0)) + ); + /* While loop equivalent in C++: * end_point // nth index of list * pos // ith index to insert the element @@ -2366,7 +2376,7 @@ namespace LCompilers { // LLVMList should treat them as data members and create them // only if they are NULL llvm::AllocaInst *tmp_ptr = builder->CreateAlloca(el_type, nullptr); - LLVM::CreateStore(*builder, read_item(list, pos, false, *module, false), tmp_ptr); + LLVM::CreateStore(*builder, read_item(list, adjusted_pos, false, *module, false), tmp_ptr); llvm::Value* tmp = nullptr; // TODO: Should be created outside the user loop and not here. @@ -2409,7 +2419,7 @@ namespace LCompilers { // end llvm_utils->start_new_block(loopend); - write_item(list, pos, item, asr_type, false, module, name2memidx); + write_item(list, adjusted_pos, item, asr_type, false, module, name2memidx); shift_end_point_by_one(list); }