Hello!
I have a question about dereferencing raw pointers in Rust, as it relates to LLVM-IR instructions. As I understand it, when a pointer is dereferenced, this is represented as a load instruction in the LLVM-IR language. However, I have noticed that in some cases, I do not see a load instruction, but instead see a store instruction.
For example, the following code creates a raw pointer and then dereferences it, with the corresponding LLVM-IR code appearing as follows:
[Source Code]
let value = 42;
let ptr: *const i32 = &value as *const i32;
unsafe {
println!("{:?}" , *ptr);
}
[LLVM-IR]
start:
%ptr.dbg.spill = alloca i32*, align 8
%b.dbg.spill = alloca i32, align 4
%a.dbg.spill = alloca i32, align 4
%_14 = alloca [1 x { i8*, i64* }], align 8
%_7 = alloca %"core::fmt::Arguments", align 8
%value = alloca i32, align 4
store i32 %a, i32* %a.dbg.spill, align 4
call void @llvm.dbg.declare(metadata i32* %a.dbg.spill, metadata !388, metadata !DIExpression()), !dbg !395
store i32 %b, i32* %b.dbg.spill, align 4
call void @llvm.dbg.declare(metadata i32* %b.dbg.spill, metadata !389, metadata !DIExpression()), !dbg !396
call void @llvm.dbg.declare(metadata i32* %value, metadata !390, metadata !DIExpression()), !dbg !397
store i32 42, i32* %value, align 4, !dbg !398
store i32* %value, i32** %ptr.dbg.spill, align 8, !dbg !399
call void @llvm.dbg.declare(metadata i32** %ptr.dbg.spill, metadata !392, metadata !DIExpression()), !dbg !400
; call core::fmt::ArgumentV1::new_debug
%1 = call { i8*, i64* } @_ZN4core3fmt10ArgumentV19new_debug17he33cadefc4e0dc85E(i32* align 4 %value), !dbg !401
%_15.0 = extractvalue { i8*, i64* } %1, 0, !dbg !401
%_15.1 = extractvalue { i8*, i64* } %1, 1, !dbg !401
br label %bb1, !dbg !401
(I expected to see a load instruction, but instead, a store instruction was present.)
Is there a rule or method for handling such exceptions in Rust? Could you explain why this might be the case?
Have a nice day!!