* Casting i128 into f64 in UEFI Rust pagefaults @ 2022-07-25 17:33 Ayush Singh 2022-07-25 17:51 ` [edk2-devel] " Andrew Fish [not found] ` <170523E2507C1293.4676@groups.io> 0 siblings, 2 replies; 11+ messages in thread From: Ayush Singh @ 2022-07-25 17:33 UTC (permalink / raw) To: devel@edk2.groups.io Cc: Kinney, Michael D, mikuback@linux.microsoft.com, Gaibusab, Jabeena B, Yao, Jiewen Hello everyone.While running Rust tests in UEFI environment, I have come across a numeric test that causes a pagefault. A simple reproducible example for this is given below: ```rust fn main() { use std::hint::black_box as b; let z: i128 = b(1); assert!((-z as f64) < 0.0); } ``` The exception output is as follows: ``` !!!! X64 Exception Type - 0E(#PF - Page-Fault) CPU Apic ID - 00000000 !!!! ExceptionData - 0000000000000000 I:0 R:0 U:0 W:0 P:0 PK:0 SS:0 SGX:0 RIP - 000000000603DB60, CS - 0000000000000038, RFLAGS - 0000000000000246 RAX - 0000000000000000, RCX - FFFFFFFFFFFFFFFF, RDX - FFFFFFFFFFFFFFFF RBX - 0000000000000000, RSP - 0000000007EDF1D0, RBP - 0000000007EDF4C0 RSI - 0000000007EDF360, RDI - 0000000007EDF3C0 R8 - 0000000000000000, R9 - 0000000000000038, R10 - 0000000000000000 R11 - 0000000000000000, R12 - 00000000060C6018, R13 - 0000000007EDF520 R14 - 0000000007EDF6A8, R15 - 0000000005FA9490 DS - 0000000000000030, ES - 0000000000000030, FS - 0000000000000030 GS - 0000000000000030, SS - 0000000000000030 CR0 - 0000000080010033, CR2 - FFFFFFFFFFFFFFFF, CR3 - 0000000007C01000 CR4 - 0000000000000668, CR8 - 0000000000000000 DR0 - 0000000000000000, DR1 - 0000000000000000, DR2 - 0000000000000000 DR3 - 0000000000000000, DR6 - 00000000FFFF0FF0, DR7 - 0000000000000400 GDTR - 00000000079DE000 0000000000000047, LDTR - 0000000000000000 IDTR - 0000000007418018 0000000000000FFF, TR - 0000000000000000 FXSAVE_STATE - 0000000007EDEE30 !!!! Find image based on IP(0x603DB60) /var/home/ayush/Documents/Programming/Rust/uefi/hello_world_std/target/x86_64-unknown-uefi/debug/deps/hello_world_std-338028f9369e2d42.pdb (ImageBase=000000000603C000, EntryPoint=000000000603D8C0) !!!! ``` From my testing, the exception only occurs when a few conditions are met. 1. The binary is compiled in Debug mode. No error in Release mode. 2. `i128` is in a black_box [1]. Does not occur if `black_box` is not present. 3. It has to be `i128`. `i64` or something else work fine. 4. The cast has to be done on `-z`. Doing the same with `+z` is fine. I have also been discussing this in the Rust zulipchat [2], so feel free to chime in there. Additionally, here are links for more information about this program: 1. Assembly: https://rust-lang.zulipchat.com/user_uploads/4715/od51Y9Dkfjahcg9HHcOud8Fm/hello_world_std-338028f9369e2d42.s 2. EFI Binary: https://rust-lang.zulipchat.com/user_uploads/4715/CknqtXLR8SaJZmyOnXctQkpL/hello_world_std.efi 3. PDB file: https://rust-lang.zulipchat.com/user_uploads/4715/zV4i6DsjgQXotp_gS1naEsU0/hello_world_std-338028f9369e2d42.pdb Yours Sincerely, Ayush Singh [1]: https://doc.rust-lang.org/std/hint/fn.black_box.html [2]: https://rust-lang.zulipchat.com/#narrow/stream/182449-t-compiler.2Fhelp/topic/Casting.20i128.20to.20f64.20in.20black_box.20causes.20exception.20in.20UEFI ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [edk2-devel] Casting i128 into f64 in UEFI Rust pagefaults 2022-07-25 17:33 Casting i128 into f64 in UEFI Rust pagefaults Ayush Singh @ 2022-07-25 17:51 ` Andrew Fish [not found] ` <170523E2507C1293.4676@groups.io> 1 sibling, 0 replies; 11+ messages in thread From: Andrew Fish @ 2022-07-25 17:51 UTC (permalink / raw) To: devel, ayushdevel1325 Cc: Mike Kinney, mikuback@linux.microsoft.com, Gaibusab, Jabeena B, Yao, Jiewen [-- Attachment #1: Type: text/plain, Size: 3863 bytes --] Ayush, CR2 is the fault address so 0xFFFFFFFFFFFFFFFF. Given for EFI Virt == Physical the fault address looks like a bad pointer. Sorry I’ve not used VC++ in a long time so I don’t know how to debug with VC++, but If I was using clang/lldb I’d look at the source and assembly for the fault address. The image base is: 0x000000000603C000 The fault PC/RIP is: 000000000603DB60 So the faulting code is at 0x1B60 in the image. Given the images are linked at zero you should be able to load the build product into the debugger and look at what code is at offset 0x1B60. The same should work for any tools that dump the binary. Thanks, Andrew Fish > On Jul 25, 2022, at 10:33 AM, Ayush Singh <ayushdevel1325@gmail.com> wrote: > > Hello everyone.While running Rust tests in UEFI environment, I have come across a numeric test that causes a pagefault. A simple reproducible example for this is given below: > > ```rust > > fn main() { > use std::hint::black_box as b; > > let z: i128 = b(1); > assert!((-z as f64) < 0.0); > } > > ``` > > > The exception output is as follows: > > ``` > > !!!! X64 Exception Type - 0E(#PF - Page-Fault) CPU Apic ID - 00000000 !!!! > ExceptionData - 0000000000000000 I:0 R:0 U:0 W:0 P:0 PK:0 SS:0 SGX:0 > RIP - 000000000603DB60, CS - 0000000000000038, RFLAGS - 0000000000000246 > RAX - 0000000000000000, RCX - FFFFFFFFFFFFFFFF, RDX - FFFFFFFFFFFFFFFF > RBX - 0000000000000000, RSP - 0000000007EDF1D0, RBP - 0000000007EDF4C0 > RSI - 0000000007EDF360, RDI - 0000000007EDF3C0 > R8 - 0000000000000000, R9 - 0000000000000038, R10 - 0000000000000000 > R11 - 0000000000000000, R12 - 00000000060C6018, R13 - 0000000007EDF520 > R14 - 0000000007EDF6A8, R15 - 0000000005FA9490 > DS - 0000000000000030, ES - 0000000000000030, FS - 0000000000000030 > GS - 0000000000000030, SS - 0000000000000030 > CR0 - 0000000080010033, CR2 - FFFFFFFFFFFFFFFF, CR3 - 0000000007C01000 > CR4 - 0000000000000668, CR8 - 0000000000000000 > DR0 - 0000000000000000, DR1 - 0000000000000000, DR2 - 0000000000000000 > DR3 - 0000000000000000, DR6 - 00000000FFFF0FF0, DR7 - 0000000000000400 > GDTR - 00000000079DE000 0000000000000047, LDTR - 0000000000000000 > IDTR - 0000000007418018 0000000000000FFF, TR - 0000000000000000 > FXSAVE_STATE - 0000000007EDEE30 > !!!! Find image based on IP(0x603DB60) /var/home/ayush/Documents/Programming/Rust/uefi/hello_world_std/target/x86_64-unknown-uefi/debug/deps/hello_world_std-338028f9369e2d42.pdb (ImageBase=000000000603C000, EntryPoint=000000000603D8C0) !!!! > > ``` > > > From my testing, the exception only occurs when a few conditions are met. > > 1. The binary is compiled in Debug mode. No error in Release mode. > > 2. `i128` is in a black_box [1]. Does not occur if `black_box` is not present. > > 3. It has to be `i128`. `i64` or something else work fine. > > 4. The cast has to be done on `-z`. Doing the same with `+z` is fine. > > > I have also been discussing this in the Rust zulipchat [2], so feel free to chime in there. > > > Additionally, here are links for more information about this program: > > 1. Assembly: https://rust-lang.zulipchat.com/user_uploads/4715/od51Y9Dkfjahcg9HHcOud8Fm/hello_world_std-338028f9369e2d42.s > > 2. EFI Binary: https://rust-lang.zulipchat.com/user_uploads/4715/CknqtXLR8SaJZmyOnXctQkpL/hello_world_std.efi > > 3. PDB file: https://rust-lang.zulipchat.com/user_uploads/4715/zV4i6DsjgQXotp_gS1naEsU0/hello_world_std-338028f9369e2d42.pdb > > > Yours Sincerely, > > Ayush Singh > > > [1]: https://doc.rust-lang.org/std/hint/fn.black_box.html > > [2]: https://rust-lang.zulipchat.com/#narrow/stream/182449-t-compiler.2Fhelp/topic/Casting.20i128.20to.20f64.20in.20black_box.20causes.20exception.20in.20UEFI > > > > [-- Attachment #2: Type: text/html, Size: 47716 bytes --] ^ permalink raw reply [flat|nested] 11+ messages in thread
[parent not found: <170523E2507C1293.4676@groups.io>]
* Re: [edk2-devel] Casting i128 into f64 in UEFI Rust pagefaults [not found] ` <170523E2507C1293.4676@groups.io> @ 2022-07-25 18:45 ` Andrew Fish 2022-07-25 18:54 ` Andrew Fish 0 siblings, 1 reply; 11+ messages in thread From: Andrew Fish @ 2022-07-25 18:45 UTC (permalink / raw) To: edk2-devel-groups-io, Andrew Fish Cc: ayushdevel1325, Mike Kinney, mikuback@linux.microsoft.com, Gaibusab, Jabeena B, Yao, Jiewen [-- Attachment #1: Type: text/plain, Size: 5290 bytes --] Ops… Looks like your PE/COFF is linked at 0x0000000140000000, so 0x140001b60 is the interesting bit. (lldb) dis -s 0x0000000140001B60 -b hello_world_std.efi[0x140001b60]: 48 8b 09 movq (%rcx), %rcx hello_world_std.efi[0x140001b63]: 48 01 c1 addq %rax, %rcx hello_world_std.efi[0x140001b66]: 4c 89 c2 movq %r8, %rdx hello_world_std.efi[0x140001b69]: 48 11 c2 adcq %rax, %rdx hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq %rax, %rcx hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq %rax, %rdx hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq %r8, %rsi RCX - FFFFFFFFFFFFFFFF So yea that looks like the fault. I don’t see that pattern in your .s file…. Can you figure out what function is @ 0x140001b60 in the PE/COFF image. Do you have a map file from the linker? Thanks, Andrew Fish PS Again sorry I don’t have anything installed to crack PDB files. Thanks, Andrew Fish > On Jul 25, 2022, at 10:51 AM, Andrew Fish via groups.io <afish=apple.com@groups.io> wrote: > > Ayush, > > CR2 is the fault address so 0xFFFFFFFFFFFFFFFF. Given for EFI Virt == Physical the fault address looks like a bad pointer. > > Sorry I’ve not used VC++ in a long time so I don’t know how to debug with VC++, but If I was using clang/lldb I’d look at the source and assembly for the fault address. > > The image base is: 0x000000000603C000 > The fault PC/RIP is: 000000000603DB60 > > So the faulting code is at 0x1B60 in the image. Given the images are linked at zero you should be able to load the build product into the debugger and look at what code is at offset 0x1B60. The same should work for any tools that dump the binary. > > Thanks, > > Andrew Fish > >> On Jul 25, 2022, at 10:33 AM, Ayush Singh <ayushdevel1325@gmail.com> wrote: >> >> Hello everyone.While running Rust tests in UEFI environment, I have come across a numeric test that causes a pagefault. A simple reproducible example for this is given below: >> >> ```rust >> >> fn main() { >> use std::hint::black_box as b; >> >> let z: i128 = b(1); >> assert!((-z as f64) < 0.0); >> } >> >> ``` >> >> >> The exception output is as follows: >> >> ``` >> >> !!!! X64 Exception Type - 0E(#PF - Page-Fault) CPU Apic ID - 00000000 !!!! >> ExceptionData - 0000000000000000 I:0 R:0 U:0 W:0 P:0 PK:0 SS:0 SGX:0 >> RIP - 000000000603DB60, CS - 0000000000000038, RFLAGS - 0000000000000246 >> RAX - 0000000000000000, RCX - FFFFFFFFFFFFFFFF, RDX - FFFFFFFFFFFFFFFF >> RBX - 0000000000000000, RSP - 0000000007EDF1D0, RBP - 0000000007EDF4C0 >> RSI - 0000000007EDF360, RDI - 0000000007EDF3C0 >> R8 - 0000000000000000, R9 - 0000000000000038, R10 - 0000000000000000 >> R11 - 0000000000000000, R12 - 00000000060C6018, R13 - 0000000007EDF520 >> R14 - 0000000007EDF6A8, R15 - 0000000005FA9490 >> DS - 0000000000000030, ES - 0000000000000030, FS - 0000000000000030 >> GS - 0000000000000030, SS - 0000000000000030 >> CR0 - 0000000080010033, CR2 - FFFFFFFFFFFFFFFF, CR3 - 0000000007C01000 >> CR4 - 0000000000000668, CR8 - 0000000000000000 >> DR0 - 0000000000000000, DR1 - 0000000000000000, DR2 - 0000000000000000 >> DR3 - 0000000000000000, DR6 - 00000000FFFF0FF0, DR7 - 0000000000000400 >> GDTR - 00000000079DE000 0000000000000047, LDTR - 0000000000000000 >> IDTR - 0000000007418018 0000000000000FFF, TR - 0000000000000000 >> FXSAVE_STATE - 0000000007EDEE30 >> !!!! Find image based on IP(0x603DB60) /var/home/ayush/Documents/Programming/Rust/uefi/hello_world_std/target/x86_64-unknown-uefi/debug/deps/hello_world_std-338028f9369e2d42.pdb (ImageBase=000000000603C000, EntryPoint=000000000603D8C0) !!!! >> >> ``` >> >> >> From my testing, the exception only occurs when a few conditions are met. >> >> 1. The binary is compiled in Debug mode. No error in Release mode. >> >> 2. `i128` is in a black_box [1]. Does not occur if `black_box` is not present. >> >> 3. It has to be `i128`. `i64` or something else work fine. >> >> 4. The cast has to be done on `-z`. Doing the same with `+z` is fine. >> >> >> I have also been discussing this in the Rust zulipchat [2], so feel free to chime in there. >> >> >> Additionally, here are links for more information about this program: >> >> 1. Assembly: https://rust-lang.zulipchat.com/user_uploads/4715/od51Y9Dkfjahcg9HHcOud8Fm/hello_world_std-338028f9369e2d42.s >> >> 2. EFI Binary: https://rust-lang.zulipchat.com/user_uploads/4715/CknqtXLR8SaJZmyOnXctQkpL/hello_world_std.efi >> >> 3. PDB file: https://rust-lang.zulipchat.com/user_uploads/4715/zV4i6DsjgQXotp_gS1naEsU0/hello_world_std-338028f9369e2d42.pdb >> >> >> Yours Sincerely, >> >> Ayush Singh >> >> >> [1]: https://doc.rust-lang.org/std/hint/fn.black_box.html >> >> [2]: https://rust-lang.zulipchat.com/#narrow/stream/182449-t-compiler.2Fhelp/topic/Casting.20i128.20to.20f64.20in.20black_box.20causes.20exception.20in.20UEFI >> >> >> > > [-- Attachment #2: Type: text/html, Size: 56892 bytes --] ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [edk2-devel] Casting i128 into f64 in UEFI Rust pagefaults 2022-07-25 18:45 ` Andrew Fish @ 2022-07-25 18:54 ` Andrew Fish 2022-07-26 5:43 ` Ayush Singh 0 siblings, 1 reply; 11+ messages in thread From: Andrew Fish @ 2022-07-25 18:54 UTC (permalink / raw) To: edk2-devel-groups-io, Andrew Fish Cc: ayushdevel1325, Mike Kinney, mikuback@linux.microsoft.com, Gaibusab, Jabeena B, Yao, Jiewen [-- Attachment #1: Type: text/plain, Size: 9007 bytes --] I guess I could at least dump to the end (req)…. Going backwards is a bit painful in x86. (lldb) dis -s 0x0000000140001B60 -b -c 30 hello_world_std.efi[0x140001b60]: 48 8b 09 movq (%rcx), %rcx hello_world_std.efi[0x140001b63]: 48 01 c1 addq %rax, %rcx hello_world_std.efi[0x140001b66]: 4c 89 c2 movq %r8, %rdx hello_world_std.efi[0x140001b69]: 48 11 c2 adcq %rax, %rdx hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq %rax, %rcx hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq %rax, %rdx hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq %r8, %rsi hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 callq 0x1400070e0 hello_world_std.efi[0x140001b84]: 48 09 f0 orq %rsi, %rax hello_world_std.efi[0x140001b87]: 48 83 c4 20 addq $0x20, %rsp hello_world_std.efi[0x140001b8b]: 5e popq %rsi hello_world_std.efi[0x140001b8c]: c3 retq hello_world_std.efi[0x140001b8d]: cc int3 hello_world_std.efi[0x140001b8e]: cc int3 hello_world_std.efi[0x140001b8f]: cc int3 hello_world_std.efi[0x140001b90]: e9 db 55 00 00 jmp 0x140007170 hello_world_std.efi[0x140001b95]: cc int3 … Then we can guess based on how functions get aligned to find the start…. hello_world_std.efi[0x140001b50]: 56 pushq %rsi hello_world_std.efi[0x140001b51]: 48 83 ec 20 subq $0x20, %rsp hello_world_std.efi[0x140001b55]: 4c 8b 41 08 movq 0x8(%rcx), %r8 hello_world_std.efi[0x140001b59]: 4c 89 c0 movq %r8, %rax hello_world_std.efi[0x140001b5c]: 48 c1 f8 3f sarq $0x3f, %rax hello_world_std.efi[0x140001b60]: 48 8b 09 movq (%rcx), %rcx hello_world_std.efi[0x140001b63]: 48 01 c1 addq %rax, %rcx hello_world_std.efi[0x140001b66]: 4c 89 c2 movq %r8, %rdx hello_world_std.efi[0x140001b69]: 48 11 c2 adcq %rax, %rdx hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq %rax, %rcx hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq %rax, %rdx hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq %r8, %rsi hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 callq 0x1400070e0 hello_world_std.efi[0x140001b84]: 48 09 f0 orq %rsi, %rax hello_world_std.efi[0x140001b87]: 48 83 c4 20 addq $0x20, %rsp hello_world_std.efi[0x140001b8b]: 5e popq %rsi hello_world_std.efi[0x140001b8c]: c3 retq So the faulting function is getting passed a bad pointer as its 1st arg. Thanks, Andrew Fish > On Jul 25, 2022, at 11:45 AM, Andrew Fish <afish@apple.com> wrote: > > Ops… Looks like your PE/COFF is linked at 0x0000000140000000, so 0x140001b60 is the interesting bit. > > (lldb) dis -s 0x0000000140001B60 -b > hello_world_std.efi[0x140001b60]: 48 8b 09 movq (%rcx), %rcx > hello_world_std.efi[0x140001b63]: 48 01 c1 addq %rax, %rcx > hello_world_std.efi[0x140001b66]: 4c 89 c2 movq %r8, %rdx > hello_world_std.efi[0x140001b69]: 48 11 c2 adcq %rax, %rdx > hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq %rax, %rcx > hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq %rax, %rdx > hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 > hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq %r8, %rsi > > RCX - FFFFFFFFFFFFFFFF > > So yea that looks like the fault. > > I don’t see that pattern in your .s file…. > > Can you figure out what function is @ 0x140001b60 in the PE/COFF image. Do you have a map file from the linker? > > Thanks, > > Andrew Fish > > PS Again sorry I don’t have anything installed to crack PDB files. > > Thanks, > > Andrew Fish > >> On Jul 25, 2022, at 10:51 AM, Andrew Fish via groups.io <afish=apple.com@groups.io> wrote: >> >> Ayush, >> >> CR2 is the fault address so 0xFFFFFFFFFFFFFFFF. Given for EFI Virt == Physical the fault address looks like a bad pointer. >> >> Sorry I’ve not used VC++ in a long time so I don’t know how to debug with VC++, but If I was using clang/lldb I’d look at the source and assembly for the fault address. >> >> The image base is: 0x000000000603C000 >> The fault PC/RIP is: 000000000603DB60 >> >> So the faulting code is at 0x1B60 in the image. Given the images are linked at zero you should be able to load the build product into the debugger and look at what code is at offset 0x1B60. The same should work for any tools that dump the binary. >> >> Thanks, >> >> Andrew Fish >> >>> On Jul 25, 2022, at 10:33 AM, Ayush Singh <ayushdevel1325@gmail.com> wrote: >>> >>> Hello everyone.While running Rust tests in UEFI environment, I have come across a numeric test that causes a pagefault. A simple reproducible example for this is given below: >>> >>> ```rust >>> >>> fn main() { >>> use std::hint::black_box as b; >>> >>> let z: i128 = b(1); >>> assert!((-z as f64) < 0.0); >>> } >>> >>> ``` >>> >>> >>> The exception output is as follows: >>> >>> ``` >>> >>> !!!! X64 Exception Type - 0E(#PF - Page-Fault) CPU Apic ID - 00000000 !!!! >>> ExceptionData - 0000000000000000 I:0 R:0 U:0 W:0 P:0 PK:0 SS:0 SGX:0 >>> RIP - 000000000603DB60, CS - 0000000000000038, RFLAGS - 0000000000000246 >>> RAX - 0000000000000000, RCX - FFFFFFFFFFFFFFFF, RDX - FFFFFFFFFFFFFFFF >>> RBX - 0000000000000000, RSP - 0000000007EDF1D0, RBP - 0000000007EDF4C0 >>> RSI - 0000000007EDF360, RDI - 0000000007EDF3C0 >>> R8 - 0000000000000000, R9 - 0000000000000038, R10 - 0000000000000000 >>> R11 - 0000000000000000, R12 - 00000000060C6018, R13 - 0000000007EDF520 >>> R14 - 0000000007EDF6A8, R15 - 0000000005FA9490 >>> DS - 0000000000000030, ES - 0000000000000030, FS - 0000000000000030 >>> GS - 0000000000000030, SS - 0000000000000030 >>> CR0 - 0000000080010033, CR2 - FFFFFFFFFFFFFFFF, CR3 - 0000000007C01000 >>> CR4 - 0000000000000668, CR8 - 0000000000000000 >>> DR0 - 0000000000000000, DR1 - 0000000000000000, DR2 - 0000000000000000 >>> DR3 - 0000000000000000, DR6 - 00000000FFFF0FF0, DR7 - 0000000000000400 >>> GDTR - 00000000079DE000 0000000000000047, LDTR - 0000000000000000 >>> IDTR - 0000000007418018 0000000000000FFF, TR - 0000000000000000 >>> FXSAVE_STATE - 0000000007EDEE30 >>> !!!! Find image based on IP(0x603DB60) /var/home/ayush/Documents/Programming/Rust/uefi/hello_world_std/target/x86_64-unknown-uefi/debug/deps/hello_world_std-338028f9369e2d42.pdb (ImageBase=000000000603C000, EntryPoint=000000000603D8C0) !!!! >>> >>> ``` >>> >>> >>> From my testing, the exception only occurs when a few conditions are met. >>> >>> 1. The binary is compiled in Debug mode. No error in Release mode. >>> >>> 2. `i128` is in a black_box [1]. Does not occur if `black_box` is not present. >>> >>> 3. It has to be `i128`. `i64` or something else work fine. >>> >>> 4. The cast has to be done on `-z`. Doing the same with `+z` is fine. >>> >>> >>> I have also been discussing this in the Rust zulipchat [2], so feel free to chime in there. >>> >>> >>> Additionally, here are links for more information about this program: >>> >>> 1. Assembly: https://rust-lang.zulipchat.com/user_uploads/4715/od51Y9Dkfjahcg9HHcOud8Fm/hello_world_std-338028f9369e2d42.s >>> >>> 2. EFI Binary: https://rust-lang.zulipchat.com/user_uploads/4715/CknqtXLR8SaJZmyOnXctQkpL/hello_world_std.efi >>> >>> 3. PDB file: https://rust-lang.zulipchat.com/user_uploads/4715/zV4i6DsjgQXotp_gS1naEsU0/hello_world_std-338028f9369e2d42.pdb >>> >>> >>> Yours Sincerely, >>> >>> Ayush Singh >>> >>> >>> [1]: https://doc.rust-lang.org/std/hint/fn.black_box.html >>> >>> [2]: https://rust-lang.zulipchat.com/#narrow/stream/182449-t-compiler.2Fhelp/topic/Casting.20i128.20to.20f64.20in.20black_box.20causes.20exception.20in.20UEFI >>> >>> >>> >> >> > [-- Attachment #2: Type: text/html, Size: 70553 bytes --] ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [edk2-devel] Casting i128 into f64 in UEFI Rust pagefaults 2022-07-25 18:54 ` Andrew Fish @ 2022-07-26 5:43 ` Ayush Singh 2022-07-26 17:50 ` Andrew Fish 2022-07-26 19:12 ` Pedro Falcato 0 siblings, 2 replies; 11+ messages in thread From: Ayush Singh @ 2022-07-26 5:43 UTC (permalink / raw) To: Andrew Fish, edk2-devel-groups-io Cc: Mike Kinney, mikuback@linux.microsoft.com, Gaibusab, Jabeena B, Yao, Jiewen [-- Attachment #1: Type: text/plain, Size: 10229 bytes --] Hi Andrew. Thanks for all your work. The more I look at this, the more it feels like it might be a problem on the LLVM side instead of Rust. I also found some more tests (all related to numbers btw) which can cause different types of exceptions, so I think I will try filing bugs upstream. Yours Sincerely, Ayush Singh On 7/26/22 00:24, Andrew Fish wrote: > I guess I could at least dump to the end (req)…. Going backwards is a > bit painful in x86. > > (lldb) dis -s 0x0000000140001B60 -b -c 30 > > hello_world_std.efi[0x140001b60]: 48 8b 09 movq > (%rcx), %rcx > > hello_world_std.efi[0x140001b63]: 48 01 c1 addq > %rax, %rcx > > hello_world_std.efi[0x140001b66]: 4c 89 c2 movq > %r8, %rdx > > hello_world_std.efi[0x140001b69]: 48 11 c2 adcq > %rax, %rdx > > hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq > %rax, %rcx > > hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq > %rax, %rdx > > hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 > movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 > > hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq > %r8, %rsi > > hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 > callq 0x1400070e0 > > hello_world_std.efi[0x140001b84]: 48 09 f0 orq > %rsi, %rax > > hello_world_std.efi[0x140001b87]: 48 83 c4 20 addq > $0x20, %rsp > > hello_world_std.efi[0x140001b8b]: 5e popq > %rsi > > hello_world_std.efi[0x140001b8c]: c3 retq > > hello_world_std.efi[0x140001b8d]: cc int3 > > hello_world_std.efi[0x140001b8e]: cc int3 > > hello_world_std.efi[0x140001b8f]: cc int3 > > hello_world_std.efi[0x140001b90]: e9 db 55 00 00 jmp > 0x140007170 > > hello_world_std.efi[0x140001b95]: cc int3 > > … > > Then we can guess based on how functions get aligned to find the start…. > > hello_world_std.efi[0x140001b50]: 56 > pushq %rsi > > hello_world_std.efi[0x140001b51]: 48 83 ec 20 > subq $0x20, %rsp > > hello_world_std.efi[0x140001b55]: 4c 8b 41 08 > movq 0x8(%rcx), %r8 > > hello_world_std.efi[0x140001b59]: 4c 89 c0 > movq %r8, %rax > > hello_world_std.efi[0x140001b5c]: 48 c1 f8 3f > sarq $0x3f, %rax > > hello_world_std.efi[0x140001b60]: 48 8b 09 > movq (%rcx), %rcx > > hello_world_std.efi[0x140001b63]: 48 01 c1 > addq %rax, %rcx > > hello_world_std.efi[0x140001b66]: 4c 89 c2 > movq %r8, %rdx > > hello_world_std.efi[0x140001b69]: 48 11 c2 > adcq %rax, %rdx > > hello_world_std.efi[0x140001b6c]: 48 31 c1 > xorq %rax, %rcx > > hello_world_std.efi[0x140001b6f]: 48 31 c2 > xorq %rax, %rdx > > hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 > movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 > > hello_world_std.efi[0x140001b7c]: 4c 21 c6 > andq %r8, %rsi > > hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 > callq 0x1400070e0 > > hello_world_std.efi[0x140001b84]: 48 09 f0 > orq %rsi, %rax > > hello_world_std.efi[0x140001b87]: 48 83 c4 20 > addq $0x20, %rsp > > hello_world_std.efi[0x140001b8b]: 5e > popq %rsi > > hello_world_std.efi[0x140001b8c]: c3 > retq > > > So the faulting function is getting passed a bad pointer as its 1st arg. > > Thanks, > > Andrew Fish > >> On Jul 25, 2022, at 11:45 AM, Andrew Fish <afish@apple.com> wrote: >> >> Ops… Looks like your PE/COFF is linked at 0x0000000140000000, >> so 0x140001b60 is the interesting bit. >> >> (lldb) dis -s 0x0000000140001B60 -b >> hello_world_std.efi[0x140001b60]: 48 8b 09 movq >> (%rcx), %rcx >> hello_world_std.efi[0x140001b63]: 48 01 c1 addq >> %rax, %rcx >> hello_world_std.efi[0x140001b66]: 4c 89 c2 movq >> %r8, %rdx >> hello_world_std.efi[0x140001b69]: 48 11 c2 adcq >> %rax, %rdx >> hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq >> %rax, %rcx >> hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq >> %rax, %rdx >> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 >> movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >> hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq >> %r8, %rsi >> >> RCX - FFFFFFFFFFFFFFFF >> >> So yea that looks like the fault. >> >> I don’t see that pattern in your .s file…. >> >> Can you figure out what function is @ 0x140001b60 in the PE/COFF >> image. Do you have a map file from the linker? >> >> Thanks, >> >> Andrew Fish >> >> PS Again sorry I don’t have anything installed to crack PDB files. >> >> Thanks, >> >> Andrew Fish >> >>> On Jul 25, 2022, at 10:51 AM, Andrew Fish via groups.io >>> <afish=apple.com@groups.io> wrote: >>> >>> Ayush, >>> >>> CR2 is the fault address so 0xFFFFFFFFFFFFFFFF. Given for EFI Virt >>> == Physical the fault address looks like a bad pointer. >>> >>> Sorry I’ve not used VC++ in a long time so I don’t know how to debug >>> with VC++, but If I was using clang/lldb I’d look at the source and >>> assembly for the fault address. >>> >>> The image base is: 0x000000000603C000 >>> The fault PC/RIP is: 000000000603DB60 >>> >>> So the faulting code is at 0x1B60 in the image. Given the images are >>> linked at zero you should be able to load the build product into the >>> debugger and look at what code is at offset 0x1B60. The same should >>> work for any tools that dump the binary. >>> >>> Thanks, >>> >>> Andrew Fish >>> >>>> On Jul 25, 2022, at 10:33 AM, Ayush Singh >>>> <ayushdevel1325@gmail.com> wrote: >>>> >>>> Hello everyone.While running Rust tests in UEFI environment, I have >>>> come across a numeric test that causes a pagefault. A simple >>>> reproducible example for this is given below: >>>> >>>> ```rust >>>> >>>> fn main() { >>>> use std::hint::black_box as b; >>>> >>>> let z: i128 = b(1); >>>> assert!((-z as f64) < 0.0); >>>> } >>>> >>>> ``` >>>> >>>> >>>> The exception output is as follows: >>>> >>>> ``` >>>> >>>> !!!! X64 Exception Type - 0E(#PF - Page-Fault) CPU Apic ID - >>>> 00000000 !!!! >>>> ExceptionData - 0000000000000000 I:0 R:0 U:0 W:0 P:0 PK:0 SS:0 SGX:0 >>>> RIP - 000000000603DB60, CS - 0000000000000038, RFLAGS - >>>> 0000000000000246 >>>> RAX - 0000000000000000, RCX - FFFFFFFFFFFFFFFF, RDX - FFFFFFFFFFFFFFFF >>>> RBX - 0000000000000000, RSP - 0000000007EDF1D0, RBP - 0000000007EDF4C0 >>>> RSI - 0000000007EDF360, RDI - 0000000007EDF3C0 >>>> R8 - 0000000000000000, R9 - 0000000000000038, R10 - 0000000000000000 >>>> R11 - 0000000000000000, R12 - 00000000060C6018, R13 - 0000000007EDF520 >>>> R14 - 0000000007EDF6A8, R15 - 0000000005FA9490 >>>> DS - 0000000000000030, ES - 0000000000000030, FS - 0000000000000030 >>>> GS - 0000000000000030, SS - 0000000000000030 >>>> CR0 - 0000000080010033, CR2 - FFFFFFFFFFFFFFFF, CR3 - 0000000007C01000 >>>> CR4 - 0000000000000668, CR8 - 0000000000000000 >>>> DR0 - 0000000000000000, DR1 - 0000000000000000, DR2 - 0000000000000000 >>>> DR3 - 0000000000000000, DR6 - 00000000FFFF0FF0, DR7 - 0000000000000400 >>>> GDTR - 00000000079DE000 0000000000000047, LDTR - 0000000000000000 >>>> IDTR - 0000000007418018 0000000000000FFF, TR - 0000000000000000 >>>> FXSAVE_STATE - 0000000007EDEE30 >>>> !!!! Find image based on IP(0x603DB60) >>>> /var/home/ayush/Documents/Programming/Rust/uefi/hello_world_std/target/x86_64-unknown-uefi/debug/deps/hello_world_std-338028f9369e2d42.pdb >>>> (ImageBase=000000000603C000, EntryPoint=000000000603D8C0) !!!! >>>> >>>> ``` >>>> >>>> >>>> From my testing, the exception only occurs when a few conditions >>>> are met. >>>> >>>> 1. The binary is compiled in Debug mode. No error in Release mode. >>>> >>>> 2. `i128` is in a black_box [1]. Does not occur if `black_box` is >>>> not present. >>>> >>>> 3. It has to be `i128`. `i64` or something else work fine. >>>> >>>> 4. The cast has to be done on `-z`. Doing the same with `+z` is fine. >>>> >>>> >>>> I have also been discussing this in the Rust zulipchat [2], so feel >>>> free to chime in there. >>>> >>>> >>>> Additionally, here are links for more information about this program: >>>> >>>> 1. >>>> Assembly:https://rust-lang.zulipchat.com/user_uploads/4715/od51Y9Dkfjahcg9HHcOud8Fm/hello_world_std-338028f9369e2d42.s >>>> >>>> 2. EFI >>>> Binary:https://rust-lang.zulipchat.com/user_uploads/4715/CknqtXLR8SaJZmyOnXctQkpL/hello_world_std.efi >>>> >>>> 3. PDB >>>> file:https://rust-lang.zulipchat.com/user_uploads/4715/zV4i6DsjgQXotp_gS1naEsU0/hello_world_std-338028f9369e2d42.pdb >>>> >>>> >>>> Yours Sincerely, >>>> >>>> Ayush Singh >>>> >>>> >>>> [1]:https://doc.rust-lang.org/std/hint/fn.black_box.html >>>> >>>> [2]:https://rust-lang.zulipchat.com/#narrow/stream/182449-t-compiler.2Fhelp/topic/Casting.20i128.20to.20f64.20in.20black_box.20causes.20exception.20in.20UEFI >>>> >>>> >>>> >>> >>> >> > [-- Attachment #2: Type: text/html, Size: 129098 bytes --] ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [edk2-devel] Casting i128 into f64 in UEFI Rust pagefaults 2022-07-26 5:43 ` Ayush Singh @ 2022-07-26 17:50 ` Andrew Fish 2022-07-26 19:15 ` Ayush Singh 2022-07-26 19:12 ` Pedro Falcato 1 sibling, 1 reply; 11+ messages in thread From: Andrew Fish @ 2022-07-26 17:50 UTC (permalink / raw) To: Ayush Singh Cc: edk2-devel-groups-io, Mike Kinney, mikuback@linux.microsoft.com, Gaibusab, Jabeena B, Yao, Jiewen [-- Attachment #1: Type: text/plain, Size: 11555 bytes --] > On Jul 25, 2022, at 10:43 PM, Ayush Singh <ayushdevel1325@gmail.com> wrote: > > Hi Andrew. Thanks for all your work. The more I look at this, the more it feels like it might be a problem on the LLVM side instead of Rust. I also found some more tests (all related to numbers btw) which can cause different types of exceptions, so I think I will try filing bugs upstream. Ayush, In general If we want to move to Rust we are going to need a way to debug issues like this down to the root cause. I think figuring out how to debug will make it easier to move forward with the Rust port in general. It will time well spent. The best way to get LLVM fixed, if it is even broken, is to provide a simple test case that reproduces the behavior. I don’t think at this point we know what is going on. It is very unlikely that some random LLVM developer is going to invest the time in trying to setup some UEFI environment to try and root cause this bug. I general find I have to create a simple at desk example and then I get stuff fixed quickly. Basically a test case the LLVM developer can compile at their desk and see the error in assembler, or at least run it at desk and have bogus output. I’m not 100% sure what toolchain you are using. Can you `objdump -d hello_world_std.efi`and get some symbols with the disassembly? For VC++ I think it would be `DUMPBIN /DISASM`. What are you planning on using for source level debugging Rust? I wrote some gdb[1] and lldb[2] debugging commands in Python. I’m guessing loading Rust symbols from PE/COFF images should be similar, as long as the debugger knows about rust. I’m happy to help you figure out stuff related to debugging Rust. [1] https://github.com/tianocore/edk2/blob/master/BaseTools/Scripts/efi_gdb.py [2] https://github.com/tianocore/edk2/blob/master/BaseTools/Scripts/efi_lldb.py Thanks, Andrew Fish > Yours Sincerely, > > Ayush Singh > > > > On 7/26/22 00:24, Andrew Fish wrote: >> I guess I could at least dump to the end (req)…. Going backwards is a bit painful in x86. >> >> (lldb) dis -s 0x0000000140001B60 -b -c 30 >> hello_world_std.efi[0x140001b60]: 48 8b 09 movq (%rcx), %rcx >> hello_world_std.efi[0x140001b63]: 48 01 c1 addq %rax, %rcx >> hello_world_std.efi[0x140001b66]: 4c 89 c2 movq %r8, %rdx >> hello_world_std.efi[0x140001b69]: 48 11 c2 adcq %rax, %rdx >> hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq %rax, %rcx >> hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq %rax, %rdx >> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >> hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq %r8, %rsi >> hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 callq 0x1400070e0 >> hello_world_std.efi[0x140001b84]: 48 09 f0 orq %rsi, %rax >> hello_world_std.efi[0x140001b87]: 48 83 c4 20 addq $0x20, %rsp >> hello_world_std.efi[0x140001b8b]: 5e popq %rsi >> hello_world_std.efi[0x140001b8c]: c3 retq >> hello_world_std.efi[0x140001b8d]: cc int3 >> hello_world_std.efi[0x140001b8e]: cc int3 >> hello_world_std.efi[0x140001b8f]: cc int3 >> hello_world_std.efi[0x140001b90]: e9 db 55 00 00 jmp 0x140007170 >> hello_world_std.efi[0x140001b95]: cc int3 >> … >> >> Then we can guess based on how functions get aligned to find the start…. >> >> hello_world_std.efi[0x140001b50]: 56 pushq %rsi >> hello_world_std.efi[0x140001b51]: 48 83 ec 20 subq $0x20, %rsp >> hello_world_std.efi[0x140001b55]: 4c 8b 41 08 movq 0x8(%rcx), %r8 >> hello_world_std.efi[0x140001b59]: 4c 89 c0 movq %r8, %rax >> hello_world_std.efi[0x140001b5c]: 48 c1 f8 3f sarq $0x3f, %rax >> hello_world_std.efi[0x140001b60]: 48 8b 09 movq (%rcx), %rcx >> hello_world_std.efi[0x140001b63]: 48 01 c1 addq %rax, %rcx >> hello_world_std.efi[0x140001b66]: 4c 89 c2 movq %r8, %rdx >> hello_world_std.efi[0x140001b69]: 48 11 c2 adcq %rax, %rdx >> hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq %rax, %rcx >> hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq %rax, %rdx >> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >> hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq %r8, %rsi >> hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 callq 0x1400070e0 >> hello_world_std.efi[0x140001b84]: 48 09 f0 orq %rsi, %rax >> hello_world_std.efi[0x140001b87]: 48 83 c4 20 addq $0x20, %rsp >> hello_world_std.efi[0x140001b8b]: 5e popq %rsi >> hello_world_std.efi[0x140001b8c]: c3 retq >> >> So the faulting function is getting passed a bad pointer as its 1st arg. >> >> Thanks, >> >> Andrew Fish >> >>> On Jul 25, 2022, at 11:45 AM, Andrew Fish <afish@apple.com> <mailto:afish@apple.com> wrote: >>> >>> Ops… Looks like your PE/COFF is linked at 0x0000000140000000, so 0x140001b60 is the interesting bit. >>> >>> (lldb) dis -s 0x0000000140001B60 -b >>> hello_world_std.efi[0x140001b60]: 48 8b 09 movq (%rcx), %rcx >>> hello_world_std.efi[0x140001b63]: 48 01 c1 addq %rax, %rcx >>> hello_world_std.efi[0x140001b66]: 4c 89 c2 movq %r8, %rdx >>> hello_world_std.efi[0x140001b69]: 48 11 c2 adcq %rax, %rdx >>> hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq %rax, %rcx >>> hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq %rax, %rdx >>> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >>> hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq %r8, %rsi >>> >>> RCX - FFFFFFFFFFFFFFFF >>> >>> So yea that looks like the fault. >>> >>> I don’t see that pattern in your .s file…. >>> >>> Can you figure out what function is @ 0x140001b60 in the PE/COFF image. Do you have a map file from the linker? >>> >>> Thanks, >>> >>> Andrew Fish >>> >>> PS Again sorry I don’t have anything installed to crack PDB files. >>> >>> Thanks, >>> >>> Andrew Fish >>> >>>> On Jul 25, 2022, at 10:51 AM, Andrew Fish via groups.io <afish=apple.com@groups.io> <mailto:afish=apple.com@groups.io> wrote: >>>> >>>> Ayush, >>>> >>>> CR2 is the fault address so 0xFFFFFFFFFFFFFFFF. Given for EFI Virt == Physical the fault address looks like a bad pointer. >>>> >>>> Sorry I’ve not used VC++ in a long time so I don’t know how to debug with VC++, but If I was using clang/lldb I’d look at the source and assembly for the fault address. >>>> >>>> The image base is: 0x000000000603C000 >>>> The fault PC/RIP is: 000000000603DB60 >>>> >>>> So the faulting code is at 0x1B60 in the image. Given the images are linked at zero you should be able to load the build product into the debugger and look at what code is at offset 0x1B60. The same should work for any tools that dump the binary. >>>> >>>> Thanks, >>>> >>>> Andrew Fish >>>> >>>>> On Jul 25, 2022, at 10:33 AM, Ayush Singh <ayushdevel1325@gmail.com> <mailto:ayushdevel1325@gmail.com> wrote: >>>>> >>>>> Hello everyone.While running Rust tests in UEFI environment, I have come across a numeric test that causes a pagefault. A simple reproducible example for this is given below: >>>>> >>>>> ```rust >>>>> >>>>> fn main() { >>>>> use std::hint::black_box as b; >>>>> >>>>> let z: i128 = b(1); >>>>> assert!((-z as f64) < 0.0); >>>>> } >>>>> >>>>> ``` >>>>> >>>>> >>>>> The exception output is as follows: >>>>> >>>>> ``` >>>>> >>>>> !!!! X64 Exception Type - 0E(#PF - Page-Fault) CPU Apic ID - 00000000 !!!! >>>>> ExceptionData - 0000000000000000 I:0 <i:0> R:0 <r:0> U:0 <u:0> W:0 <w:0> P:0 <p:0> PK:0 <pk:0> SS:0 <ss:0> SGX:0 <sgx:0> >>>>> RIP - 000000000603DB60, CS - 0000000000000038, RFLAGS - 0000000000000246 >>>>> RAX - 0000000000000000, RCX - FFFFFFFFFFFFFFFF, RDX - FFFFFFFFFFFFFFFF >>>>> RBX - 0000000000000000, RSP - 0000000007EDF1D0, RBP - 0000000007EDF4C0 >>>>> RSI - 0000000007EDF360, RDI - 0000000007EDF3C0 >>>>> R8 - 0000000000000000, R9 - 0000000000000038, R10 - 0000000000000000 >>>>> R11 - 0000000000000000, R12 - 00000000060C6018, R13 - 0000000007EDF520 >>>>> R14 - 0000000007EDF6A8, R15 - 0000000005FA9490 >>>>> DS - 0000000000000030, ES - 0000000000000030, FS - 0000000000000030 >>>>> GS - 0000000000000030, SS - 0000000000000030 >>>>> CR0 - 0000000080010033, CR2 - FFFFFFFFFFFFFFFF, CR3 - 0000000007C01000 >>>>> CR4 - 0000000000000668, CR8 - 0000000000000000 >>>>> DR0 - 0000000000000000, DR1 - 0000000000000000, DR2 - 0000000000000000 >>>>> DR3 - 0000000000000000, DR6 - 00000000FFFF0FF0, DR7 - 0000000000000400 >>>>> GDTR - 00000000079DE000 0000000000000047, LDTR - 0000000000000000 >>>>> IDTR - 0000000007418018 0000000000000FFF, TR - 0000000000000000 >>>>> FXSAVE_STATE - 0000000007EDEE30 >>>>> !!!! Find image based on IP(0x603DB60) /var/home/ayush/Documents/Programming/Rust/uefi/hello_world_std/target/x86_64-unknown-uefi/debug/deps/hello_world_std-338028f9369e2d42.pdb (ImageBase=000000000603C000, EntryPoint=000000000603D8C0) !!!! >>>>> >>>>> ``` >>>>> >>>>> >>>>> From my testing, the exception only occurs when a few conditions are met. >>>>> >>>>> 1. The binary is compiled in Debug mode. No error in Release mode. >>>>> >>>>> 2. `i128` is in a black_box [1]. Does not occur if `black_box` is not present. >>>>> >>>>> 3. It has to be `i128`. `i64` or something else work fine. >>>>> >>>>> 4. The cast has to be done on `-z`. Doing the same with `+z` is fine. >>>>> >>>>> >>>>> I have also been discussing this in the Rust zulipchat [2], so feel free to chime in there. >>>>> >>>>> >>>>> Additionally, here are links for more information about this program: >>>>> >>>>> 1. Assembly: https://rust-lang.zulipchat.com/user_uploads/4715/od51Y9Dkfjahcg9HHcOud8Fm/hello_world_std-338028f9369e2d42.s >>>>> >>>>> 2. EFI Binary: https://rust-lang.zulipchat.com/user_uploads/4715/CknqtXLR8SaJZmyOnXctQkpL/hello_world_std.efi >>>>> >>>>> 3. PDB file: https://rust-lang.zulipchat.com/user_uploads/4715/zV4i6DsjgQXotp_gS1naEsU0/hello_world_std-338028f9369e2d42.pdb >>>>> >>>>> >>>>> Yours Sincerely, >>>>> >>>>> Ayush Singh >>>>> >>>>> >>>>> [1]: https://doc.rust-lang.org/std/hint/fn.black_box.html >>>>> >>>>> [2]: https://rust-lang.zulipchat.com/#narrow/stream/182449-t-compiler.2Fhelp/topic/Casting.20i128.20to.20f64.20in.20black_box.20causes.20exception.20in.20UEFI >>>>> >>>>> >>>>> >>>> >>>> >>> >> [-- Attachment #2: Type: text/html, Size: 132416 bytes --] ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [edk2-devel] Casting i128 into f64 in UEFI Rust pagefaults 2022-07-26 17:50 ` Andrew Fish @ 2022-07-26 19:15 ` Ayush Singh 2022-07-26 21:38 ` Andrew Fish 0 siblings, 1 reply; 11+ messages in thread From: Ayush Singh @ 2022-07-26 19:15 UTC (permalink / raw) To: Andrew Fish Cc: edk2-devel-groups-io, Mike Kinney, mikuback@linux.microsoft.com, Gaibusab, Jabeena B, Yao, Jiewen [-- Attachment #1: Type: text/plain, Size: 14225 bytes --] Hi Andrew. I do agree with having better debugging support for Rust-UEFI. However, I am not much experienced with even the C side of UEFI debugging, so it has been difficult for me to do much on the Rust side either. It isn't like Rust UEFI debugging is not possible. There are some examples ([1]), but as you might guess, they are quite few. Additionally, most of them seem to be concentrated around Windows. Finally, there is actually quite good debugging support in uefi-rs [2], but well, that's licensed under MPL-2.0, so I have stayed clear of it. Another reason I have gone so long without using any actual debugger is because, well, Rust makes it quite explicit where wired errors can occur. Most functions, even inside the std, don't use pointers but rather use `NonNull`, `MaybeUninint` or some other safe abstraction. Even on the worst failure, the program will abort instead of crash. On aborting, Rust also gives a nice message on stderr stating exactly where the error occurred along with all the details of the error. Basically, it was always so clear what caused the error and where it occurred that I simply didn't feel the need to attach a debugger, till now. There is some work going on to actually document using Rust for UEFI in the rustc docs, sponsored by Red Hat [3], so the situation should improve soon. What I do know is that the `.pdb` files generated by Rust (which are always generated) should contain all the symbols for debugging. I can work on debugging once I finish up with solving all other errors which are due to my implementation of std rather than the ones that have been caused by the rust intrinsic. Ayush Singh [1]: https://xitan.me/posts/rust-uefi-runtime-driver/ [2]: https://github.com/rust-osdev/uefi-rs [3]: https://github.com/rust-lang/rust/pull/99760 On 7/26/22 23:20, Andrew Fish wrote: >> On Jul 25, 2022, at 10:43 PM, Ayush Singh <ayushdevel1325@gmail.com> >> wrote: >> >> Hi Andrew. Thanks for all your work. The more I look at this, the >> more it feels like it might be a problem on the LLVM side instead of >> Rust. I also found some more tests (all related to numbers btw) which >> can cause different types of exceptions, so I think I will try filing >> bugs upstream. >> > > Ayush, > > In general If we want to move to Rust we are going to need a way to > debug issues like this down to the root cause. I think figuring out > how to debug will make it easier to move forward with the Rust port in > general. It will time well spent. > > The best way to get LLVM fixed, if it is even broken, is to provide a > simple test case that reproduces the behavior. I don’t think at this > point we know what is going on. It is very unlikely that some random > LLVM developer is going to invest the time in trying to setup some > UEFI environment to try and root cause this bug. I general find I have > to create a simple at desk example and then I get stuff fixed quickly. > Basically a test case the LLVM developer can compile at their desk and > see the error in assembler, or at least run it at desk and have bogus > output. > > I’m not 100% sure what toolchain you are using. Can you `objdump > -d hello_world_std.efi`and get some symbols with the disassembly? For > VC++ I think it would be `DUMPBIN /DISASM`. > > What are you planning on using for source level debugging Rust? I > wrote some gdb[1] and lldb[2] debugging commands in Python. I’m > guessing loading Rust symbols from PE/COFF images should be similar, > as long as the debugger knows about rust. > > I’m happy to help you figure out stuff related to debugging Rust. > > [1] > https://github.com/tianocore/edk2/blob/master/BaseTools/Scripts/efi_gdb.py > [2] > https://github.com/tianocore/edk2/blob/master/BaseTools/Scripts/efi_lldb.py > > Thanks, > > Andrew Fish > >> Yours Sincerely, >> >> Ayush Singh >> >> >> On 7/26/22 00:24, Andrew Fish wrote: >>> I guess I could at least dump to the end (req)…. Going backwards is >>> a bit painful in x86. >>> >>> (lldb) dis -s 0x0000000140001B60 -b -c 30 >>> hello_world_std.efi[0x140001b60]: 48 8b 09 >>> movq (%rcx), %rcx >>> hello_world_std.efi[0x140001b63]: 48 01 c1 >>> addq %rax, %rcx >>> hello_world_std.efi[0x140001b66]: 4c 89 c2 >>> movq %r8, %rdx >>> hello_world_std.efi[0x140001b69]: 48 11 c2 >>> adcq %rax, %rdx >>> hello_world_std.efi[0x140001b6c]: 48 31 c1 >>> xorq %rax, %rcx >>> hello_world_std.efi[0x140001b6f]: 48 31 c2 >>> xorq %rax, %rdx >>> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 >>> movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >>> hello_world_std.efi[0x140001b7c]: 4c 21 c6 >>> andq %r8, %rsi >>> hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 >>> callq 0x1400070e0 >>> hello_world_std.efi[0x140001b84]: 48 09 f0 >>> orq %rsi, %rax >>> hello_world_std.efi[0x140001b87]: 48 83 c4 20 >>> addq $0x20, %rsp >>> hello_world_std.efi[0x140001b8b]: 5e >>> popq %rsi >>> hello_world_std.efi[0x140001b8c]: c3 retq >>> hello_world_std.efi[0x140001b8d]: cc int3 >>> hello_world_std.efi[0x140001b8e]: cc int3 >>> hello_world_std.efi[0x140001b8f]: cc int3 >>> hello_world_std.efi[0x140001b90]: e9 db 55 00 00 >>> jmp 0x140007170 >>> hello_world_std.efi[0x140001b95]: cc int3 >>> … >>> >>> Then we can guess based on how functions get aligned to find the start…. >>> >>> hello_world_std.efi[0x140001b50]: 56 >>> pushq %rsi >>> hello_world_std.efi[0x140001b51]: 48 83 ec 20 >>> subq $0x20, %rsp >>> hello_world_std.efi[0x140001b55]: 4c 8b 41 08 >>> movq 0x8(%rcx), %r8 >>> hello_world_std.efi[0x140001b59]: 4c 89 c0 >>> movq %r8, %rax >>> hello_world_std.efi[0x140001b5c]: 48 c1 f8 3f >>> sarq $0x3f, %rax >>> hello_world_std.efi[0x140001b60]: 48 8b 09 >>> movq (%rcx), %rcx >>> hello_world_std.efi[0x140001b63]: 48 01 c1 >>> addq %rax, %rcx >>> hello_world_std.efi[0x140001b66]: 4c 89 c2 >>> movq %r8, %rdx >>> hello_world_std.efi[0x140001b69]: 48 11 c2 >>> adcq %rax, %rdx >>> hello_world_std.efi[0x140001b6c]: 48 31 c1 >>> xorq %rax, %rcx >>> hello_world_std.efi[0x140001b6f]: 48 31 c2 >>> xorq %rax, %rdx >>> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 >>> movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >>> hello_world_std.efi[0x140001b7c]: 4c 21 c6 >>> andq %r8, %rsi >>> hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 >>> callq 0x1400070e0 >>> hello_world_std.efi[0x140001b84]: 48 09 f0 >>> orq %rsi, %rax >>> hello_world_std.efi[0x140001b87]: 48 83 c4 20 >>> addq $0x20, %rsp >>> hello_world_std.efi[0x140001b8b]: 5e >>> popq %rsi >>> hello_world_std.efi[0x140001b8c]: c3 >>> retq >>> >>> So the faulting function is getting passed a bad pointer as its 1st >>> arg. >>> >>> Thanks, >>> >>> Andrew Fish >>> >>>> On Jul 25, 2022, at 11:45 AM, Andrew Fish <afish@apple.com> wrote: >>>> >>>> Ops… Looks like your PE/COFF is linked at 0x0000000140000000, >>>> so 0x140001b60 is the interesting bit. >>>> >>>> (lldb) dis -s 0x0000000140001B60 -b >>>> hello_world_std.efi[0x140001b60]: 48 8b 09 >>>> movq (%rcx), %rcx >>>> hello_world_std.efi[0x140001b63]: 48 01 c1 >>>> addq %rax, %rcx >>>> hello_world_std.efi[0x140001b66]: 4c 89 c2 >>>> movq %r8, %rdx >>>> hello_world_std.efi[0x140001b69]: 48 11 c2 >>>> adcq %rax, %rdx >>>> hello_world_std.efi[0x140001b6c]: 48 31 c1 >>>> xorq %rax, %rcx >>>> hello_world_std.efi[0x140001b6f]: 48 31 c2 >>>> xorq %rax, %rdx >>>> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 >>>> movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >>>> hello_world_std.efi[0x140001b7c]: 4c 21 c6 >>>> andq %r8, %rsi >>>> >>>> RCX - FFFFFFFFFFFFFFFF >>>> >>>> So yea that looks like the fault. >>>> >>>> I don’t see that pattern in your .s file…. >>>> >>>> Can you figure out what function is @ 0x140001b60 in the PE/COFF >>>> image. Do you have a map file from the linker? >>>> >>>> Thanks, >>>> >>>> Andrew Fish >>>> >>>> PS Again sorry I don’t have anything installed to crack PDB files. >>>> >>>> Thanks, >>>> >>>> Andrew Fish >>>> >>>>> On Jul 25, 2022, at 10:51 AM, Andrew Fish via groups.io >>>>> <afish=apple.com@groups.io> wrote: >>>>> >>>>> Ayush, >>>>> >>>>> CR2 is the fault address so 0xFFFFFFFFFFFFFFFF. Given for EFI Virt >>>>> == Physical the fault address looks like a bad pointer. >>>>> >>>>> Sorry I’ve not used VC++ in a long time so I don’t know how to >>>>> debug with VC++, but If I was using clang/lldb I’d look at the >>>>> source and assembly for the fault address. >>>>> >>>>> The image base is: 0x000000000603C000 >>>>> The fault PC/RIP is: 000000000603DB60 >>>>> >>>>> So the faulting code is at 0x1B60 in the image. Given the images >>>>> are linked at zero you should be able to load the build product >>>>> into the debugger and look at what code is at offset 0x1B60. The >>>>> same should work for any tools that dump the binary. >>>>> >>>>> Thanks, >>>>> >>>>> Andrew Fish >>>>> >>>>>> On Jul 25, 2022, at 10:33 AM, Ayush Singh >>>>>> <ayushdevel1325@gmail.com> wrote: >>>>>> >>>>>> Hello everyone.While running Rust tests in UEFI environment, I >>>>>> have come across a numeric test that causes a pagefault. A simple >>>>>> reproducible example for this is given below: >>>>>> >>>>>> ```rust >>>>>> >>>>>> fn main() { >>>>>> use std::hint::black_box as b; >>>>>> >>>>>> let z: i128 = b(1); >>>>>> assert!((-z as f64) < 0.0); >>>>>> } >>>>>> >>>>>> ``` >>>>>> >>>>>> >>>>>> The exception output is as follows: >>>>>> >>>>>> ``` >>>>>> >>>>>> !!!! X64 Exception Type - 0E(#PF - Page-Fault) CPU Apic ID - >>>>>> 00000000 !!!! >>>>>> ExceptionData - 0000000000000000 I:0 R:0 U:0 W:0 P:0 PK:0 SS:0 SGX:0 >>>>>> RIP - 000000000603DB60, CS - 0000000000000038, RFLAGS - >>>>>> 0000000000000246 >>>>>> RAX - 0000000000000000, RCX - FFFFFFFFFFFFFFFF, RDX - >>>>>> FFFFFFFFFFFFFFFF >>>>>> RBX - 0000000000000000, RSP - 0000000007EDF1D0, RBP - >>>>>> 0000000007EDF4C0 >>>>>> RSI - 0000000007EDF360, RDI - 0000000007EDF3C0 >>>>>> R8 - 0000000000000000, R9 - 0000000000000038, R10 - >>>>>> 0000000000000000 >>>>>> R11 - 0000000000000000, R12 - 00000000060C6018, R13 - >>>>>> 0000000007EDF520 >>>>>> R14 - 0000000007EDF6A8, R15 - 0000000005FA9490 >>>>>> DS - 0000000000000030, ES - 0000000000000030, FS - >>>>>> 0000000000000030 >>>>>> GS - 0000000000000030, SS - 0000000000000030 >>>>>> CR0 - 0000000080010033, CR2 - FFFFFFFFFFFFFFFF, CR3 - >>>>>> 0000000007C01000 >>>>>> CR4 - 0000000000000668, CR8 - 0000000000000000 >>>>>> DR0 - 0000000000000000, DR1 - 0000000000000000, DR2 - >>>>>> 0000000000000000 >>>>>> DR3 - 0000000000000000, DR6 - 00000000FFFF0FF0, DR7 - >>>>>> 0000000000000400 >>>>>> GDTR - 00000000079DE000 0000000000000047, LDTR - 0000000000000000 >>>>>> IDTR - 0000000007418018 0000000000000FFF, TR - 0000000000000000 >>>>>> FXSAVE_STATE - 0000000007EDEE30 >>>>>> !!!! Find image based on IP(0x603DB60) >>>>>> /var/home/ayush/Documents/Programming/Rust/uefi/hello_world_std/target/x86_64-unknown-uefi/debug/deps/hello_world_std-338028f9369e2d42.pdb >>>>>> (ImageBase=000000000603C000, EntryPoint=000000000603D8C0) !!!! >>>>>> >>>>>> ``` >>>>>> >>>>>> >>>>>> From my testing, the exception only occurs when a few conditions >>>>>> are met. >>>>>> >>>>>> 1. The binary is compiled in Debug mode. No error in Release mode. >>>>>> >>>>>> 2. `i128` is in a black_box [1]. Does not occur if `black_box` is >>>>>> not present. >>>>>> >>>>>> 3. It has to be `i128`. `i64` or something else work fine. >>>>>> >>>>>> 4. The cast has to be done on `-z`. Doing the same with `+z` is fine. >>>>>> >>>>>> >>>>>> I have also been discussing this in the Rust zulipchat [2], so >>>>>> feel free to chime in there. >>>>>> >>>>>> >>>>>> Additionally, here are links for more information about this program: >>>>>> >>>>>> 1. >>>>>> Assembly:https://rust-lang.zulipchat.com/user_uploads/4715/od51Y9Dkfjahcg9HHcOud8Fm/hello_world_std-338028f9369e2d42.s >>>>>> >>>>>> 2. EFI >>>>>> Binary:https://rust-lang.zulipchat.com/user_uploads/4715/CknqtXLR8SaJZmyOnXctQkpL/hello_world_std.efi >>>>>> >>>>>> 3. PDB >>>>>> file:https://rust-lang.zulipchat.com/user_uploads/4715/zV4i6DsjgQXotp_gS1naEsU0/hello_world_std-338028f9369e2d42.pdb >>>>>> >>>>>> >>>>>> Yours Sincerely, >>>>>> >>>>>> Ayush Singh >>>>>> >>>>>> >>>>>> [1]:https://doc.rust-lang.org/std/hint/fn.black_box.html >>>>>> >>>>>> [2]:https://rust-lang.zulipchat.com/#narrow/stream/182449-t-compiler.2Fhelp/topic/Casting.20i128.20to.20f64.20in.20black_box.20causes.20exception.20in.20UEFI >>>>>> >>>>>> >>>>>> >>>>> >>>>> >>>> >>> > [-- Attachment #2: Type: text/html, Size: 179654 bytes --] ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [edk2-devel] Casting i128 into f64 in UEFI Rust pagefaults 2022-07-26 19:15 ` Ayush Singh @ 2022-07-26 21:38 ` Andrew Fish 2022-07-27 6:01 ` Ayush Singh 0 siblings, 1 reply; 11+ messages in thread From: Andrew Fish @ 2022-07-26 21:38 UTC (permalink / raw) To: edk2-devel-groups-io, ayushdevel1325 Cc: Mike Kinney, mikuback@linux.microsoft.com, Gaibusab, Jabeena B, Yao, Jiewen [-- Attachment #1: Type: text/plain, Size: 14682 bytes --] Ayush, Well bugs in the runtime are a classic case when have good debugging infrastructure pays off and that class of issue is what started this email thread. It is not hard to try out gdb to see what happens if you are using QEMU. >From the root of the edk2 repo: $ OvmfPkg/build.sh qemu -gdb tcp::9000 Then from another terminal $ cd BaseTools/Scripts $ gdb -ex "target remote localhost:9000" -ex "source efi_gdb.py" That should get you a symbolicated stack frame. The QEMU -gdb works like a JTAG debugger. You can put dead loops in your code, let it run, and then attach. Thanks, Andrew Fish > On Jul 26, 2022, at 12:15 PM, Ayush Singh <ayushdevel1325@gmail.com> wrote: > > Hi Andrew. I do agree with having better debugging support for Rust-UEFI. However, I am not much experienced with even the C side of UEFI debugging, so it has been difficult for me to do much on the Rust side either. It isn't like Rust UEFI debugging is not possible. There are some examples ([1]), but as you might guess, they are quite few. Additionally, most of them seem to be concentrated around Windows. Finally, there is actually quite good debugging support in uefi-rs [2], but well, that's licensed under MPL-2.0, so I have stayed clear of it. > > > > Another reason I have gone so long without using any actual debugger is because, well, Rust makes it quite explicit where wired errors can occur. Most functions, even inside the std, don't use pointers but rather use `NonNull`, `MaybeUninint` or some other safe abstraction. Even on the worst failure, the program will abort instead of crash. On aborting, Rust also gives a nice message on stderr stating exactly where the error occurred along with all the details of the error. Basically, it was always so clear what caused the error and where it occurred that I simply didn't feel the need to attach a debugger, till now. > > > > There is some work going on to actually document using Rust for UEFI in the rustc docs, sponsored by Red Hat [3], so the situation should improve soon. What I do know is that the `.pdb` files generated by Rust (which are always generated) should contain all the symbols for debugging. I can work on debugging once I finish up with solving all other errors which are due to my implementation of std rather than the ones that have been caused by the rust intrinsic. > > > > Ayush Singh > > > > [1]: https://xitan.me/posts/rust-uefi-runtime-driver/ > > [2]: https://github.com/rust-osdev/uefi-rs > > [3]: https://github.com/rust-lang/rust/pull/99760 > > > > On 7/26/22 23:20, Andrew Fish wrote: >>> On Jul 25, 2022, at 10:43 PM, Ayush Singh <ayushdevel1325@gmail.com> <mailto:ayushdevel1325@gmail.com> wrote: >>> >>> Hi Andrew. Thanks for all your work. The more I look at this, the more it feels like it might be a problem on the LLVM side instead of Rust. I also found some more tests (all related to numbers btw) which can cause different types of exceptions, so I think I will try filing bugs upstream. >>> >> >> Ayush, >> >> In general If we want to move to Rust we are going to need a way to debug issues like this down to the root cause. I think figuring out how to debug will make it easier to move forward with the Rust port in general. It will time well spent. >> >> The best way to get LLVM fixed, if it is even broken, is to provide a simple test case that reproduces the behavior. I don’t think at this point we know what is going on. It is very unlikely that some random LLVM developer is going to invest the time in trying to setup some UEFI environment to try and root cause this bug. I general find I have to create a simple at desk example and then I get stuff fixed quickly. Basically a test case the LLVM developer can compile at their desk and see the error in assembler, or at least run it at desk and have bogus output. >> >> I’m not 100% sure what toolchain you are using. Can you `objdump -d hello_world_std.efi`and get some symbols with the disassembly? For VC++ I think it would be `DUMPBIN /DISASM`. >> >> What are you planning on using for source level debugging Rust? I wrote some gdb[1] and lldb[2] debugging commands in Python. I’m guessing loading Rust symbols from PE/COFF images should be similar, as long as the debugger knows about rust. >> >> I’m happy to help you figure out stuff related to debugging Rust. >> >> [1] https://github.com/tianocore/edk2/blob/master/BaseTools/Scripts/efi_gdb.py >> [2] https://github.com/tianocore/edk2/blob/master/BaseTools/Scripts/efi_lldb.py >> >> Thanks, >> >> Andrew Fish >> >>> Yours Sincerely, >>> >>> Ayush Singh >>> >>> >>> >>> On 7/26/22 00:24, Andrew Fish wrote: >>>> I guess I could at least dump to the end (req)…. Going backwards is a bit painful in x86. >>>> >>>> (lldb) dis -s 0x0000000140001B60 -b -c 30 >>>> hello_world_std.efi[0x140001b60]: 48 8b 09 movq (%rcx), %rcx >>>> hello_world_std.efi[0x140001b63]: 48 01 c1 addq %rax, %rcx >>>> hello_world_std.efi[0x140001b66]: 4c 89 c2 movq %r8, %rdx >>>> hello_world_std.efi[0x140001b69]: 48 11 c2 adcq %rax, %rdx >>>> hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq %rax, %rcx >>>> hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq %rax, %rdx >>>> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >>>> hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq %r8, %rsi >>>> hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 callq 0x1400070e0 >>>> hello_world_std.efi[0x140001b84]: 48 09 f0 orq %rsi, %rax >>>> hello_world_std.efi[0x140001b87]: 48 83 c4 20 addq $0x20, %rsp >>>> hello_world_std.efi[0x140001b8b]: 5e popq %rsi >>>> hello_world_std.efi[0x140001b8c]: c3 retq >>>> hello_world_std.efi[0x140001b8d]: cc int3 >>>> hello_world_std.efi[0x140001b8e]: cc int3 >>>> hello_world_std.efi[0x140001b8f]: cc int3 >>>> hello_world_std.efi[0x140001b90]: e9 db 55 00 00 jmp 0x140007170 >>>> hello_world_std.efi[0x140001b95]: cc int3 >>>> … >>>> >>>> Then we can guess based on how functions get aligned to find the start…. >>>> >>>> hello_world_std.efi[0x140001b50]: 56 pushq %rsi >>>> hello_world_std.efi[0x140001b51]: 48 83 ec 20 subq $0x20, %rsp >>>> hello_world_std.efi[0x140001b55]: 4c 8b 41 08 movq 0x8(%rcx), %r8 >>>> hello_world_std.efi[0x140001b59]: 4c 89 c0 movq %r8, %rax >>>> hello_world_std.efi[0x140001b5c]: 48 c1 f8 3f sarq $0x3f, %rax >>>> hello_world_std.efi[0x140001b60]: 48 8b 09 movq (%rcx), %rcx >>>> hello_world_std.efi[0x140001b63]: 48 01 c1 addq %rax, %rcx >>>> hello_world_std.efi[0x140001b66]: 4c 89 c2 movq %r8, %rdx >>>> hello_world_std.efi[0x140001b69]: 48 11 c2 adcq %rax, %rdx >>>> hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq %rax, %rcx >>>> hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq %rax, %rdx >>>> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >>>> hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq %r8, %rsi >>>> hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 callq 0x1400070e0 >>>> hello_world_std.efi[0x140001b84]: 48 09 f0 orq %rsi, %rax >>>> hello_world_std.efi[0x140001b87]: 48 83 c4 20 addq $0x20, %rsp >>>> hello_world_std.efi[0x140001b8b]: 5e popq %rsi >>>> hello_world_std.efi[0x140001b8c]: c3 retq >>>> >>>> So the faulting function is getting passed a bad pointer as its 1st arg. >>>> >>>> Thanks, >>>> >>>> Andrew Fish >>>> >>>>> On Jul 25, 2022, at 11:45 AM, Andrew Fish <afish@apple.com> <mailto:afish@apple.com> wrote: >>>>> >>>>> Ops… Looks like your PE/COFF is linked at 0x0000000140000000, so 0x140001b60 is the interesting bit. >>>>> >>>>> (lldb) dis -s 0x0000000140001B60 -b >>>>> hello_world_std.efi[0x140001b60]: 48 8b 09 movq (%rcx), %rcx >>>>> hello_world_std.efi[0x140001b63]: 48 01 c1 addq %rax, %rcx >>>>> hello_world_std.efi[0x140001b66]: 4c 89 c2 movq %r8, %rdx >>>>> hello_world_std.efi[0x140001b69]: 48 11 c2 adcq %rax, %rdx >>>>> hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq %rax, %rcx >>>>> hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq %rax, %rdx >>>>> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >>>>> hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq %r8, %rsi >>>>> >>>>> RCX - FFFFFFFFFFFFFFFF >>>>> >>>>> So yea that looks like the fault. >>>>> >>>>> I don’t see that pattern in your .s file…. >>>>> >>>>> Can you figure out what function is @ 0x140001b60 in the PE/COFF image. Do you have a map file from the linker? >>>>> >>>>> Thanks, >>>>> >>>>> Andrew Fish >>>>> >>>>> PS Again sorry I don’t have anything installed to crack PDB files. >>>>> >>>>> Thanks, >>>>> >>>>> Andrew Fish >>>>> >>>>>> On Jul 25, 2022, at 10:51 AM, Andrew Fish via groups.io <afish=apple.com@groups.io> <mailto:afish=apple.com@groups.io> wrote: >>>>>> >>>>>> Ayush, >>>>>> >>>>>> CR2 is the fault address so 0xFFFFFFFFFFFFFFFF. Given for EFI Virt == Physical the fault address looks like a bad pointer. >>>>>> >>>>>> Sorry I’ve not used VC++ in a long time so I don’t know how to debug with VC++, but If I was using clang/lldb I’d look at the source and assembly for the fault address. >>>>>> >>>>>> The image base is: 0x000000000603C000 >>>>>> The fault PC/RIP is: 000000000603DB60 >>>>>> >>>>>> So the faulting code is at 0x1B60 in the image. Given the images are linked at zero you should be able to load the build product into the debugger and look at what code is at offset 0x1B60. The same should work for any tools that dump the binary. >>>>>> >>>>>> Thanks, >>>>>> >>>>>> Andrew Fish >>>>>> >>>>>>> On Jul 25, 2022, at 10:33 AM, Ayush Singh <ayushdevel1325@gmail.com> <mailto:ayushdevel1325@gmail.com> wrote: >>>>>>> >>>>>>> Hello everyone.While running Rust tests in UEFI environment, I have come across a numeric test that causes a pagefault. A simple reproducible example for this is given below: >>>>>>> >>>>>>> ```rust >>>>>>> >>>>>>> fn main() { >>>>>>> use std::hint::black_box as b; >>>>>>> >>>>>>> let z: i128 = b(1); >>>>>>> assert!((-z as f64) < 0.0); >>>>>>> } >>>>>>> >>>>>>> ``` >>>>>>> >>>>>>> >>>>>>> The exception output is as follows: >>>>>>> >>>>>>> ``` >>>>>>> >>>>>>> !!!! X64 Exception Type - 0E(#PF - Page-Fault) CPU Apic ID - 00000000 !!!! >>>>>>> ExceptionData - 0000000000000000 I:0 <i:0> R:0 <r:0> U:0 <u:0> W:0 <w:0> P:0 <p:0> PK:0 <pk:0> SS:0 <ss:0> SGX:0 <sgx:0> >>>>>>> RIP - 000000000603DB60, CS - 0000000000000038, RFLAGS - 0000000000000246 >>>>>>> RAX - 0000000000000000, RCX - FFFFFFFFFFFFFFFF, RDX - FFFFFFFFFFFFFFFF >>>>>>> RBX - 0000000000000000, RSP - 0000000007EDF1D0, RBP - 0000000007EDF4C0 >>>>>>> RSI - 0000000007EDF360, RDI - 0000000007EDF3C0 >>>>>>> R8 - 0000000000000000, R9 - 0000000000000038, R10 - 0000000000000000 >>>>>>> R11 - 0000000000000000, R12 - 00000000060C6018, R13 - 0000000007EDF520 >>>>>>> R14 - 0000000007EDF6A8, R15 - 0000000005FA9490 >>>>>>> DS - 0000000000000030, ES - 0000000000000030, FS - 0000000000000030 >>>>>>> GS - 0000000000000030, SS - 0000000000000030 >>>>>>> CR0 - 0000000080010033, CR2 - FFFFFFFFFFFFFFFF, CR3 - 0000000007C01000 >>>>>>> CR4 - 0000000000000668, CR8 - 0000000000000000 >>>>>>> DR0 - 0000000000000000, DR1 - 0000000000000000, DR2 - 0000000000000000 >>>>>>> DR3 - 0000000000000000, DR6 - 00000000FFFF0FF0, DR7 - 0000000000000400 >>>>>>> GDTR - 00000000079DE000 0000000000000047, LDTR - 0000000000000000 >>>>>>> IDTR - 0000000007418018 0000000000000FFF, TR - 0000000000000000 >>>>>>> FXSAVE_STATE - 0000000007EDEE30 >>>>>>> !!!! Find image based on IP(0x603DB60) /var/home/ayush/Documents/Programming/Rust/uefi/hello_world_std/target/x86_64-unknown-uefi/debug/deps/hello_world_std-338028f9369e2d42.pdb (ImageBase=000000000603C000, EntryPoint=000000000603D8C0) !!!! >>>>>>> >>>>>>> ``` >>>>>>> >>>>>>> >>>>>>> From my testing, the exception only occurs when a few conditions are met. >>>>>>> >>>>>>> 1. The binary is compiled in Debug mode. No error in Release mode. >>>>>>> >>>>>>> 2. `i128` is in a black_box [1]. Does not occur if `black_box` is not present. >>>>>>> >>>>>>> 3. It has to be `i128`. `i64` or something else work fine. >>>>>>> >>>>>>> 4. The cast has to be done on `-z`. Doing the same with `+z` is fine. >>>>>>> >>>>>>> >>>>>>> I have also been discussing this in the Rust zulipchat [2], so feel free to chime in there. >>>>>>> >>>>>>> >>>>>>> Additionally, here are links for more information about this program: >>>>>>> >>>>>>> 1. Assembly: https://rust-lang.zulipchat.com/user_uploads/4715/od51Y9Dkfjahcg9HHcOud8Fm/hello_world_std-338028f9369e2d42.s >>>>>>> >>>>>>> 2. EFI Binary: https://rust-lang.zulipchat.com/user_uploads/4715/CknqtXLR8SaJZmyOnXctQkpL/hello_world_std.efi >>>>>>> >>>>>>> 3. PDB file: https://rust-lang.zulipchat.com/user_uploads/4715/zV4i6DsjgQXotp_gS1naEsU0/hello_world_std-338028f9369e2d42.pdb >>>>>>> >>>>>>> >>>>>>> Yours Sincerely, >>>>>>> >>>>>>> Ayush Singh >>>>>>> >>>>>>> >>>>>>> [1]: https://doc.rust-lang.org/std/hint/fn.black_box.html >>>>>>> >>>>>>> [2]: https://rust-lang.zulipchat.com/#narrow/stream/182449-t-compiler.2Fhelp/topic/Casting.20i128.20to.20f64.20in.20black_box.20causes.20exception.20in.20UEFI >>>>>>> >>>>>>> >>>>>>> >>>>>> >>>>> >>>> >> > > [-- Attachment #2: Type: text/html, Size: 182236 bytes --] ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [edk2-devel] Casting i128 into f64 in UEFI Rust pagefaults 2022-07-26 21:38 ` Andrew Fish @ 2022-07-27 6:01 ` Ayush Singh 0 siblings, 0 replies; 11+ messages in thread From: Ayush Singh @ 2022-07-27 6:01 UTC (permalink / raw) To: devel, afish Cc: Mike Kinney, mikuback@linux.microsoft.com, Gaibusab, Jabeena B, Yao, Jiewen [-- Attachment #1: Type: text/plain, Size: 14842 bytes --] Thanks, Andrew. I will try it out and add it to UEFI Rust documentation as well. I will ask more questions in case I get stuck somewhere. Ayush Singh On 7/27/22 03:08, Andrew Fish via groups.io wrote: > Ayush, > > > Well bugs in the runtime are a classic case when have good debugging > infrastructure pays off and that class of issue is what started this > email thread. > > It is not hard to try out gdb to see what happens if you are using QEMU. > From the root of the edk2 repo: > $ OvmfPkg/build.sh qemu -gdb tcp::9000 > > Then from another terminal > $ cd BaseTools/Scripts > $ gdb -ex "target remote localhost:9000" -ex "source efi_gdb.py" > > That should get you a symbolicated stack frame. > > The QEMU -gdb works like a JTAG debugger. You can put dead loops in > your code, let it run, and then attach. > > Thanks, > > Andrew Fish > >> On Jul 26, 2022, at 12:15 PM, Ayush Singh <ayushdevel1325@gmail.com> >> wrote: >> >> Hi Andrew. I do agree with having better debugging support for >> Rust-UEFI. However, I am not much experienced with even the C side of >> UEFI debugging, so it has been difficult for me to do much on the >> Rust side either. It isn't like Rust UEFI debugging is not possible. >> There are some examples ([1]), but as you might guess, they are quite >> few. Additionally, most of them seem to be concentrated around >> Windows. Finally, there is actually quite good debugging support in >> uefi-rs [2], but well, that's licensed under MPL-2.0, so I have >> stayed clear of it. >> >> >> Another reason I have gone so long without using any actual debugger >> is because, well, Rust makes it quite explicit where wired errors can >> occur. Most functions, even inside the std, don't use pointers but >> rather use `NonNull`, `MaybeUninint` or some other safe abstraction. >> Even on the worst failure, the program will abort instead of crash. >> On aborting, Rust also gives a nice message on stderr stating exactly >> where the error occurred along with all the details of the error. >> Basically, it was always so clear what caused the error and where it >> occurred that I simply didn't feel the need to attach a debugger, >> till now. >> >> >> There is some work going on to actually document using Rust for UEFI >> in the rustc docs, sponsored by Red Hat [3], so the situation should >> improve soon. What I do know is that the `.pdb` files generated by >> Rust (which are always generated) should contain all the symbols for >> debugging. I can work on debugging once I finish up with solving all >> other errors which are due to my implementation of std rather than >> the ones that have been caused by the rust intrinsic. >> >> >> Ayush Singh >> >> >> [1]: https://xitan.me/posts/rust-uefi-runtime-driver/ >> >> [2]: https://github.com/rust-osdev/uefi-rs >> >> [3]: https://github.com/rust-lang/rust/pull/99760 >> >> >> On 7/26/22 23:20, Andrew Fish wrote: >>>> On Jul 25, 2022, at 10:43 PM, Ayush Singh >>>> <ayushdevel1325@gmail.com> wrote: >>>> >>>> Hi Andrew. Thanks for all your work. The more I look at this, the >>>> more it feels like it might be a problem on the LLVM side instead >>>> of Rust. I also found some more tests (all related to numbers btw) >>>> which can cause different types of exceptions, so I think I will >>>> try filing bugs upstream. >>>> >>> >>> Ayush, >>> >>> In general If we want to move to Rust we are going to need a way to >>> debug issues like this down to the root cause. I think figuring out >>> how to debug will make it easier to move forward with the Rust port >>> in general. It will time well spent. >>> >>> The best way to get LLVM fixed, if it is even broken, is to provide >>> a simple test case that reproduces the behavior. I don’t think at >>> this point we know what is going on. It is very unlikely that some >>> random LLVM developer is going to invest the time in trying to setup >>> some UEFI environment to try and root cause this bug. I general find >>> I have to create a simple at desk example and then I get stuff fixed >>> quickly. Basically a test case the LLVM developer can compile at >>> their desk and see the error in assembler, or at least run it at >>> desk and have bogus output. >>> >>> I’m not 100% sure what toolchain you are using. Can you `objdump >>> -d hello_world_std.efi`and get some symbols with the disassembly? >>> For VC++ I think it would be `DUMPBIN /DISASM`. >>> >>> What are you planning on using for source level debugging Rust? I >>> wrote some gdb[1] and lldb[2] debugging commands in Python. I’m >>> guessing loading Rust symbols from PE/COFF images should be similar, >>> as long as the debugger knows about rust. >>> >>> I’m happy to help you figure out stuff related to debugging Rust. >>> >>> [1] >>> https://github.com/tianocore/edk2/blob/master/BaseTools/Scripts/efi_gdb.py >>> [2] >>> https://github.com/tianocore/edk2/blob/master/BaseTools/Scripts/efi_lldb.py >>> >>> Thanks, >>> >>> Andrew Fish >>> >>>> Yours Sincerely, >>>> >>>> Ayush Singh >>>> >>>> >>>> On 7/26/22 00:24, Andrew Fish wrote: >>>>> I guess I could at least dump to the end (req)…. Going backwards >>>>> is a bit painful in x86. >>>>> >>>>> (lldb) dis -s 0x0000000140001B60 -b -c 30 >>>>> hello_world_std.efi[0x140001b60]: 48 8b 09 >>>>> movq (%rcx), %rcx >>>>> hello_world_std.efi[0x140001b63]: 48 01 c1 >>>>> addq %rax, %rcx >>>>> hello_world_std.efi[0x140001b66]: 4c 89 c2 >>>>> movq %r8, %rdx >>>>> hello_world_std.efi[0x140001b69]: 48 11 c2 >>>>> adcq %rax, %rdx >>>>> hello_world_std.efi[0x140001b6c]: 48 31 c1 >>>>> xorq %rax, %rcx >>>>> hello_world_std.efi[0x140001b6f]: 48 31 c2 >>>>> xorq %rax, %rdx >>>>> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 >>>>> movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >>>>> hello_world_std.efi[0x140001b7c]: 4c 21 c6 >>>>> andq %r8, %rsi >>>>> hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 >>>>> callq 0x1400070e0 >>>>> hello_world_std.efi[0x140001b84]: 48 09 f0 >>>>> orq %rsi, %rax >>>>> hello_world_std.efi[0x140001b87]: 48 83 c4 20 >>>>> addq $0x20, %rsp >>>>> hello_world_std.efi[0x140001b8b]: 5e >>>>> popq %rsi >>>>> hello_world_std.efi[0x140001b8c]: c3 retq >>>>> hello_world_std.efi[0x140001b8d]: cc int3 >>>>> hello_world_std.efi[0x140001b8e]: cc int3 >>>>> hello_world_std.efi[0x140001b8f]: cc int3 >>>>> hello_world_std.efi[0x140001b90]: e9 db 55 00 00 >>>>> jmp 0x140007170 >>>>> hello_world_std.efi[0x140001b95]: cc int3 >>>>> … >>>>> >>>>> Then we can guess based on how functions get aligned to find the >>>>> start…. >>>>> >>>>> hello_world_std.efi[0x140001b50]: 56 pushq %rsi >>>>> hello_world_std.efi[0x140001b51]: 48 83 ec 20 subq $0x20, %rsp >>>>> hello_world_std.efi[0x140001b55]: 4c 8b 41 08 movq 0x8(%rcx), %r8 >>>>> hello_world_std.efi[0x140001b59]: 4c 89 c0 movq %r8, %rax >>>>> hello_world_std.efi[0x140001b5c]: 48 c1 f8 3f sarq $0x3f, %rax >>>>> hello_world_std.efi[0x140001b60]: 48 8b 09 movq (%rcx), %rcx >>>>> hello_world_std.efi[0x140001b63]: 48 01 c1 addq %rax, %rcx >>>>> hello_world_std.efi[0x140001b66]: 4c 89 c2 movq %r8, %rdx >>>>> hello_world_std.efi[0x140001b69]: 48 11 c2 adcq %rax, %rdx >>>>> hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq %rax, %rcx >>>>> hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq %rax, %rdx >>>>> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 >>>>> movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >>>>> hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq %r8, %rsi >>>>> hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 callq 0x1400070e0 >>>>> hello_world_std.efi[0x140001b84]: 48 09 f0 orq %rsi, %rax >>>>> hello_world_std.efi[0x140001b87]: 48 83 c4 20 addq $0x20, %rsp >>>>> hello_world_std.efi[0x140001b8b]: 5e popq %rsi >>>>> hello_world_std.efi[0x140001b8c]: c3 retq >>>>> >>>>> So the faulting function is getting passed a bad pointer as its >>>>> 1st arg. >>>>> >>>>> Thanks, >>>>> >>>>> Andrew Fish >>>>> >>>>>> On Jul 25, 2022, at 11:45 AM, Andrew Fish <afish@apple.com> wrote: >>>>>> >>>>>> Ops… Looks like your PE/COFF is linked at 0x0000000140000000, >>>>>> so 0x140001b60 is the interesting bit. >>>>>> >>>>>> (lldb) dis -s 0x0000000140001B60 -b >>>>>> hello_world_std.efi[0x140001b60]: 48 8b 09 movq (%rcx), %rcx >>>>>> hello_world_std.efi[0x140001b63]: 48 01 c1 addq %rax, %rcx >>>>>> hello_world_std.efi[0x140001b66]: 4c 89 c2 movq %r8, %rdx >>>>>> hello_world_std.efi[0x140001b69]: 48 11 c2 adcq %rax, %rdx >>>>>> hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq %rax, %rcx >>>>>> hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq %rax, %rdx >>>>>> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 >>>>>> movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >>>>>> hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq %r8, %rsi >>>>>> >>>>>> RCX - FFFFFFFFFFFFFFFF >>>>>> >>>>>> So yea that looks like the fault. >>>>>> >>>>>> I don’t see that pattern in your .s file…. >>>>>> >>>>>> Can you figure out what function is @ 0x140001b60 in the PE/COFF >>>>>> image. Do you have a map file from the linker? >>>>>> >>>>>> Thanks, >>>>>> >>>>>> Andrew Fish >>>>>> >>>>>> PS Again sorry I don’t have anything installed to crack PDB files. >>>>>> >>>>>> Thanks, >>>>>> >>>>>> Andrew Fish >>>>>> >>>>>>> On Jul 25, 2022, at 10:51 AM, Andrew Fish via groups.io >>>>>>> <afish=apple.com@groups.io> wrote: >>>>>>> >>>>>>> Ayush, >>>>>>> >>>>>>> CR2 is the fault address so 0xFFFFFFFFFFFFFFFF. Given for EFI >>>>>>> Virt == Physical the fault address looks like a bad pointer. >>>>>>> >>>>>>> Sorry I’ve not used VC++ in a long time so I don’t know how to >>>>>>> debug with VC++, but If I was using clang/lldb I’d look at the >>>>>>> source and assembly for the fault address. >>>>>>> >>>>>>> The image base is: 0x000000000603C000 >>>>>>> The fault PC/RIP is: 000000000603DB60 >>>>>>> >>>>>>> So the faulting code is at 0x1B60 in the image. Given the images >>>>>>> are linked at zero you should be able to load the build product >>>>>>> into the debugger and look at what code is at offset 0x1B60. The >>>>>>> same should work for any tools that dump the binary. >>>>>>> >>>>>>> Thanks, >>>>>>> >>>>>>> Andrew Fish >>>>>>> >>>>>>>> On Jul 25, 2022, at 10:33 AM, Ayush Singh >>>>>>>> <ayushdevel1325@gmail.com> wrote: >>>>>>>> >>>>>>>> Hello everyone.While running Rust tests in UEFI environment, I >>>>>>>> have come across a numeric test that causes a pagefault. A >>>>>>>> simple reproducible example for this is given below: >>>>>>>> >>>>>>>> ```rust >>>>>>>> >>>>>>>> fn main() { >>>>>>>> use std::hint::black_box as b; >>>>>>>> >>>>>>>> let z: i128 = b(1); >>>>>>>> assert!((-z as f64) < 0.0); >>>>>>>> } >>>>>>>> >>>>>>>> ``` >>>>>>>> >>>>>>>> >>>>>>>> The exception output is as follows: >>>>>>>> >>>>>>>> ``` >>>>>>>> >>>>>>>> !!!! X64 Exception Type - 0E(#PF - Page-Fault) CPU Apic ID - >>>>>>>> 00000000 !!!! >>>>>>>> ExceptionData - 0000000000000000 I:0 R:0 U:0 W:0 P:0 PK:0 SS:0 >>>>>>>> SGX:0 >>>>>>>> RIP - 000000000603DB60, CS - 0000000000000038, RFLAGS - >>>>>>>> 0000000000000246 >>>>>>>> RAX - 0000000000000000, RCX - FFFFFFFFFFFFFFFF, RDX - >>>>>>>> FFFFFFFFFFFFFFFF >>>>>>>> RBX - 0000000000000000, RSP - 0000000007EDF1D0, RBP - >>>>>>>> 0000000007EDF4C0 >>>>>>>> RSI - 0000000007EDF360, RDI - 0000000007EDF3C0 >>>>>>>> R8 - 0000000000000000, R9 - 0000000000000038, R10 - >>>>>>>> 0000000000000000 >>>>>>>> R11 - 0000000000000000, R12 - 00000000060C6018, R13 - >>>>>>>> 0000000007EDF520 >>>>>>>> R14 - 0000000007EDF6A8, R15 - 0000000005FA9490 >>>>>>>> DS - 0000000000000030, ES - 0000000000000030, FS - >>>>>>>> 0000000000000030 >>>>>>>> GS - 0000000000000030, SS - 0000000000000030 >>>>>>>> CR0 - 0000000080010033, CR2 - FFFFFFFFFFFFFFFF, CR3 - >>>>>>>> 0000000007C01000 >>>>>>>> CR4 - 0000000000000668, CR8 - 0000000000000000 >>>>>>>> DR0 - 0000000000000000, DR1 - 0000000000000000, DR2 - >>>>>>>> 0000000000000000 >>>>>>>> DR3 - 0000000000000000, DR6 - 00000000FFFF0FF0, DR7 - >>>>>>>> 0000000000000400 >>>>>>>> GDTR - 00000000079DE000 0000000000000047, LDTR - 0000000000000000 >>>>>>>> IDTR - 0000000007418018 0000000000000FFF, TR - 0000000000000000 >>>>>>>> FXSAVE_STATE - 0000000007EDEE30 >>>>>>>> !!!! Find image based on IP(0x603DB60) >>>>>>>> /var/home/ayush/Documents/Programming/Rust/uefi/hello_world_std/target/x86_64-unknown-uefi/debug/deps/hello_world_std-338028f9369e2d42.pdb >>>>>>>> (ImageBase=000000000603C000, EntryPoint=000000000603D8C0) !!!! >>>>>>>> >>>>>>>> ``` >>>>>>>> >>>>>>>> >>>>>>>> From my testing, the exception only occurs when a few >>>>>>>> conditions are met. >>>>>>>> >>>>>>>> 1. The binary is compiled in Debug mode. No error in Release mode. >>>>>>>> >>>>>>>> 2. `i128` is in a black_box [1]. Does not occur if `black_box` >>>>>>>> is not present. >>>>>>>> >>>>>>>> 3. It has to be `i128`. `i64` or something else work fine. >>>>>>>> >>>>>>>> 4. The cast has to be done on `-z`. Doing the same with `+z` is >>>>>>>> fine. >>>>>>>> >>>>>>>> >>>>>>>> I have also been discussing this in the Rust zulipchat [2], so >>>>>>>> feel free to chime in there. >>>>>>>> >>>>>>>> >>>>>>>> Additionally, here are links for more information about this >>>>>>>> program: >>>>>>>> >>>>>>>> 1. >>>>>>>> Assembly:https://rust-lang.zulipchat.com/user_uploads/4715/od51Y9Dkfjahcg9HHcOud8Fm/hello_world_std-338028f9369e2d42.s >>>>>>>> >>>>>>>> 2. EFI >>>>>>>> Binary:https://rust-lang.zulipchat.com/user_uploads/4715/CknqtXLR8SaJZmyOnXctQkpL/hello_world_std.efi >>>>>>>> >>>>>>>> 3. PDB >>>>>>>> file:https://rust-lang.zulipchat.com/user_uploads/4715/zV4i6DsjgQXotp_gS1naEsU0/hello_world_std-338028f9369e2d42.pdb >>>>>>>> >>>>>>>> >>>>>>>> Yours Sincerely, >>>>>>>> >>>>>>>> Ayush Singh >>>>>>>> >>>>>>>> >>>>>>>> [1]:https://doc.rust-lang.org/std/hint/fn.black_box.html >>>>>>>> >>>>>>>> [2]:https://rust-lang.zulipchat.com/#narrow/stream/182449-t-compiler.2Fhelp/topic/Casting.20i128.20to.20f64.20in.20black_box.20causes.20exception.20in.20UEFI >>>>>>>> >>>>>>>> >>>>>>>> >>>>>>> >>>>>> >>>>> >>> > > [-- Attachment #2: Type: text/html, Size: 312723 bytes --] ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [edk2-devel] Casting i128 into f64 in UEFI Rust pagefaults 2022-07-26 5:43 ` Ayush Singh 2022-07-26 17:50 ` Andrew Fish @ 2022-07-26 19:12 ` Pedro Falcato 2022-07-26 19:24 ` Ayush Singh 1 sibling, 1 reply; 11+ messages in thread From: Pedro Falcato @ 2022-07-26 19:12 UTC (permalink / raw) To: edk2-devel-groups-io, Ayush Singh Cc: Andrew Fish, Mike Kinney, mikuback@linux.microsoft.com, Gaibusab, Jabeena B, Yao, Jiewen [-- Attachment #1: Type: text/plain, Size: 9625 bytes --] Fyi, please don't file bugs upstream just now. You're not sure if they're LLVM problems (and they're likely not, else they would affect everyone else, not just UEFI code). Try to get a simpler, reliable repro (and do share with us!) before saying it's an LLVM bug. In my experience, most "what the hell" "compiler bugs" ended up being things I accidentally set up wrong, or didn't set up at all, and broke things in a subtle way. On Tue, Jul 26, 2022 at 6:43 AM Ayush Singh <ayushdevel1325@gmail.com> wrote: > Hi Andrew. Thanks for all your work. The more I look at this, the more it > feels like it might be a problem on the LLVM side instead of Rust. I also > found some more tests (all related to numbers btw) which can cause > different types of exceptions, so I think I will try filing bugs upstream. > > Yours Sincerely, > > Ayush Singh > > > On 7/26/22 00:24, Andrew Fish wrote: > > I guess I could at least dump to the end (req)…. Going backwards is a bit > painful in x86. > > (lldb) dis -s 0x0000000140001B60 -b -c 30 > > hello_world_std.efi[0x140001b60]: 48 8b 09 movq > (%rcx), %rcx > > hello_world_std.efi[0x140001b63]: 48 01 c1 addq > %rax, %rcx > > hello_world_std.efi[0x140001b66]: 4c 89 c2 movq > %r8, %rdx > > hello_world_std.efi[0x140001b69]: 48 11 c2 adcq > %rax, %rdx > > hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq > %rax, %rcx > > hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq > %rax, %rdx > > hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 movabsq > $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 > > hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq > %r8, %rsi > > hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 callq > 0x1400070e0 > > hello_world_std.efi[0x140001b84]: 48 09 f0 orq > %rsi, %rax > > hello_world_std.efi[0x140001b87]: 48 83 c4 20 addq > $0x20, %rsp > > hello_world_std.efi[0x140001b8b]: 5e popq > %rsi > > hello_world_std.efi[0x140001b8c]: c3 retq > > hello_world_std.efi[0x140001b8d]: cc int3 > > hello_world_std.efi[0x140001b8e]: cc int3 > > hello_world_std.efi[0x140001b8f]: cc int3 > > hello_world_std.efi[0x140001b90]: e9 db 55 00 00 jmp > 0x140007170 > > hello_world_std.efi[0x140001b95]: cc int3 > … > > Then we can guess based on how functions get aligned to find the start…. > > hello_world_std.efi[0x140001b50]: 56 > pushq %rsi > > hello_world_std.efi[0x140001b51]: 48 83 ec 20 > subq $0x20, %rsp > > hello_world_std.efi[0x140001b55]: 4c 8b 41 08 > movq 0x8(%rcx), %r8 > > hello_world_std.efi[0x140001b59]: 4c 89 c0 > movq %r8, %rax > > hello_world_std.efi[0x140001b5c]: 48 c1 f8 3f > sarq $0x3f, %rax > > hello_world_std.efi[0x140001b60]: 48 8b 09 > movq (%rcx), %rcx > > hello_world_std.efi[0x140001b63]: 48 01 c1 > addq %rax, %rcx > > hello_world_std.efi[0x140001b66]: 4c 89 c2 > movq %r8, %rdx > > hello_world_std.efi[0x140001b69]: 48 11 c2 > adcq %rax, %rdx > > hello_world_std.efi[0x140001b6c]: 48 31 c1 > xorq %rax, %rcx > > hello_world_std.efi[0x140001b6f]: 48 31 c2 > xorq %rax, %rdx > > hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 > movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 > > hello_world_std.efi[0x140001b7c]: 4c 21 c6 > andq %r8, %rsi > > hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 > callq 0x1400070e0 > > hello_world_std.efi[0x140001b84]: 48 09 f0 > orq %rsi, %rax > > hello_world_std.efi[0x140001b87]: 48 83 c4 20 > addq $0x20, %rsp > > hello_world_std.efi[0x140001b8b]: 5e > popq %rsi > > hello_world_std.efi[0x140001b8c]: c3 > retq > > So the faulting function is getting passed a bad pointer as its 1st arg. > > Thanks, > > Andrew Fish > > On Jul 25, 2022, at 11:45 AM, Andrew Fish <afish@apple.com> > <afish@apple.com> wrote: > > Ops… Looks like your PE/COFF is linked at 0x0000000140000000, > so 0x140001b60 is the interesting bit. > > (lldb) dis -s 0x0000000140001B60 -b > hello_world_std.efi[0x140001b60]: 48 8b 09 movq > (%rcx), %rcx > hello_world_std.efi[0x140001b63]: 48 01 c1 addq > %rax, %rcx > hello_world_std.efi[0x140001b66]: 4c 89 c2 movq > %r8, %rdx > hello_world_std.efi[0x140001b69]: 48 11 c2 adcq > %rax, %rdx > hello_world_std.efi[0x140001b6c]: 48 31 c1 xorq > %rax, %rcx > hello_world_std.efi[0x140001b6f]: 48 31 c2 xorq > %rax, %rdx > hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 movabsq > $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 > hello_world_std.efi[0x140001b7c]: 4c 21 c6 andq > %r8, %rsi > > RCX - FFFFFFFFFFFFFFFF > > So yea that looks like the fault. > > I don’t see that pattern in your .s file…. > > Can you figure out what function is @ 0x140001b60 in the PE/COFF image. > Do you have a map file from the linker? > > Thanks, > > Andrew Fish > > PS Again sorry I don’t have anything installed to crack PDB files. > > Thanks, > > Andrew Fish > > On Jul 25, 2022, at 10:51 AM, Andrew Fish via groups.io > <afish=apple.com@groups.io> <afish=apple.com@groups.io> wrote: > > Ayush, > > CR2 is the fault address so 0xFFFFFFFFFFFFFFFF. Given for EFI Virt == > Physical the fault address looks like a bad pointer. > > Sorry I’ve not used VC++ in a long time so I don’t know how to debug with > VC++, but If I was using clang/lldb I’d look at the source and assembly for > the fault address. > > The image base is: 0x000000000603C000 > The fault PC/RIP is: 000000000603DB60 > > So the faulting code is at 0x1B60 in the image. Given the images are > linked at zero you should be able to load the build product into the > debugger and look at what code is at offset 0x1B60. The same should work > for any tools that dump the binary. > > Thanks, > > Andrew Fish > > On Jul 25, 2022, at 10:33 AM, Ayush Singh <ayushdevel1325@gmail.com> > <ayushdevel1325@gmail.com> wrote: > > Hello everyone.While running Rust tests in UEFI environment, I have come > across a numeric test that causes a pagefault. A simple reproducible > example for this is given below: > > ```rust > > fn main() { > use std::hint::black_box as b; > > let z: i128 = b(1); > assert!((-z as f64) < 0.0); > } > > ``` > > > The exception output is as follows: > > ``` > > !!!! X64 Exception Type - 0E(#PF - Page-Fault) CPU Apic ID - 00000000 !!!! > ExceptionData - 0000000000000000 I:0 R:0 U:0 W:0 P:0 PK:0 SS:0 SGX:0 > RIP - 000000000603DB60, CS - 0000000000000038, RFLAGS - 0000000000000246 > RAX - 0000000000000000, RCX - FFFFFFFFFFFFFFFF, RDX - FFFFFFFFFFFFFFFF > RBX - 0000000000000000, RSP - 0000000007EDF1D0, RBP - 0000000007EDF4C0 > RSI - 0000000007EDF360, RDI - 0000000007EDF3C0 > R8 - 0000000000000000, R9 - 0000000000000038, R10 - 0000000000000000 > R11 - 0000000000000000, R12 - 00000000060C6018, R13 - 0000000007EDF520 > R14 - 0000000007EDF6A8, R15 - 0000000005FA9490 > DS - 0000000000000030, ES - 0000000000000030, FS - 0000000000000030 > GS - 0000000000000030, SS - 0000000000000030 > CR0 - 0000000080010033, CR2 - FFFFFFFFFFFFFFFF, CR3 - 0000000007C01000 > CR4 - 0000000000000668, CR8 - 0000000000000000 > DR0 - 0000000000000000, DR1 - 0000000000000000, DR2 - 0000000000000000 > DR3 - 0000000000000000, DR6 - 00000000FFFF0FF0, DR7 - 0000000000000400 > GDTR - 00000000079DE000 0000000000000047, LDTR - 0000000000000000 > IDTR - 0000000007418018 0000000000000FFF, TR - 0000000000000000 > FXSAVE_STATE - 0000000007EDEE30 > !!!! Find image based on IP(0x603DB60) > /var/home/ayush/Documents/Programming/Rust/uefi/hello_world_std/target/x86_64-unknown-uefi/debug/deps/hello_world_std-338028f9369e2d42.pdb > (ImageBase=000000000603C000, EntryPoint=000000000603D8C0) !!!! > > ``` > > > From my testing, the exception only occurs when a few conditions are met. > > 1. The binary is compiled in Debug mode. No error in Release mode. > > 2. `i128` is in a black_box [1]. Does not occur if `black_box` is not > present. > > 3. It has to be `i128`. `i64` or something else work fine. > > 4. The cast has to be done on `-z`. Doing the same with `+z` is fine. > > > I have also been discussing this in the Rust zulipchat [2], so feel free > to chime in there. > > > Additionally, here are links for more information about this program: > > 1. Assembly: > https://rust-lang.zulipchat.com/user_uploads/4715/od51Y9Dkfjahcg9HHcOud8Fm/hello_world_std-338028f9369e2d42.s > > 2. EFI Binary: > https://rust-lang.zulipchat.com/user_uploads/4715/CknqtXLR8SaJZmyOnXctQkpL/hello_world_std.efi > > 3. PDB file: > https://rust-lang.zulipchat.com/user_uploads/4715/zV4i6DsjgQXotp_gS1naEsU0/hello_world_std-338028f9369e2d42.pdb > > > Yours Sincerely, > > Ayush Singh > > > [1]: https://doc.rust-lang.org/std/hint/fn.black_box.html > > [2]: > https://rust-lang.zulipchat.com/#narrow/stream/182449-t-compiler.2Fhelp/topic/Casting.20i128.20to.20f64.20in.20black_box.20causes.20exception.20in.20UEFI > > > > > > > > > -- Pedro Falcato [-- Attachment #2: Type: text/html, Size: 66207 bytes --] ^ permalink raw reply [flat|nested] 11+ messages in thread
* Re: [edk2-devel] Casting i128 into f64 in UEFI Rust pagefaults 2022-07-26 19:12 ` Pedro Falcato @ 2022-07-26 19:24 ` Ayush Singh 0 siblings, 0 replies; 11+ messages in thread From: Ayush Singh @ 2022-07-26 19:24 UTC (permalink / raw) To: Pedro Falcato, edk2-devel-groups-io Cc: Andrew Fish, Mike Kinney, mikuback@linux.microsoft.com, Gaibusab, Jabeena B, Yao, Jiewen [-- Attachment #1: Type: text/plain, Size: 13030 bytes --] When I mentioned upstream, I was talking about Rust repository, since as you said, I am not sure if this is LLVM problem yet. There is already a similar bug filed in rust repo about u128 division causing exception [1], and there is a possible fix [2] (which does not work for the page fault). I have also found 1 more edge case in numbers to cause `General Exception`, which just like the other two seems to be related to rust intrinsic or LLVM, but since I am not sure, and simply haven't done any testing on, I cannot really say. Anyway, filing them in Rust repository is helpful since the bug might affect other `msvc-like` tier-2 and tier-3 targets. There is also renewed interest in making UEFI targets Tier-2 from Tier-3 (sponsored by Red Hat), so it's possible that someone else might pick it up before I am done with the std errors I am trying to fix. Ayush Singh [1]: https://github.com/rust-lang/rust/issues/86494 [2]: https://github.com/rust-lang/compiler-builtins/pull/475 On 7/27/22 00:42, Pedro Falcato wrote: > Fyi, please don't file bugs upstream just now. You're not sure if > they're LLVM problems (and they're likely not, else they would affect > everyone else, not just UEFI code). Try to get a simpler, reliable > repro (and do share with us!) before saying it's an LLVM bug. > In my experience, most "what the hell" "compiler bugs" ended up being > things I accidentally set up wrong, or didn't set up at all, and broke > things in a subtle way. > > On Tue, Jul 26, 2022 at 6:43 AM Ayush Singh <ayushdevel1325@gmail.com> > wrote: > > Hi Andrew. Thanks for all your work. The more I look at this, the > more it feels like it might be a problem on the LLVM side instead > of Rust. I also found some more tests (all related to numbers btw) > which can cause different types of exceptions, so I think I will > try filing bugs upstream. > > Yours Sincerely, > > Ayush Singh > > > On 7/26/22 00:24, Andrew Fish wrote: >> I guess I could at least dump to the end (req)…. Going backwards >> is a bit painful in x86. >> >> (lldb) dis -s 0x0000000140001B60 -b -c 30 >> >> hello_world_std.efi[0x140001b60]: 48 8b 09 >> movq (%rcx), %rcx >> >> hello_world_std.efi[0x140001b63]: 48 01 c1 >> addq %rax, %rcx >> >> hello_world_std.efi[0x140001b66]: 4c 89 c2 >> movq %r8, %rdx >> >> hello_world_std.efi[0x140001b69]: 48 11 c2 >> adcq %rax, %rdx >> >> hello_world_std.efi[0x140001b6c]: 48 31 c1 >> xorq %rax, %rcx >> >> hello_world_std.efi[0x140001b6f]: 48 31 c2 >> xorq %rax, %rdx >> >> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 >> movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >> >> hello_world_std.efi[0x140001b7c]: 4c 21 c6 >> andq %r8, %rsi >> >> hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 >> callq 0x1400070e0 >> >> hello_world_std.efi[0x140001b84]: 48 09 f0 >> orq %rsi, %rax >> >> hello_world_std.efi[0x140001b87]: 48 83 c4 20 >> addq $0x20, %rsp >> >> hello_world_std.efi[0x140001b8b]: 5e >> popq %rsi >> >> hello_world_std.efi[0x140001b8c]: c3 >> retq >> >> hello_world_std.efi[0x140001b8d]: cc >> int3 >> >> hello_world_std.efi[0x140001b8e]: cc >> int3 >> >> hello_world_std.efi[0x140001b8f]: cc >> int3 >> >> hello_world_std.efi[0x140001b90]: e9 db 55 00 00 >> jmp 0x140007170 >> >> hello_world_std.efi[0x140001b95]: cc >> int3 >> >> … >> >> Then we can guess based on how functions get aligned to find the >> start…. >> >> hello_world_std.efi[0x140001b50]: 56 >> pushq %rsi >> >> hello_world_std.efi[0x140001b51]: 48 83 ec 20 >> subq $0x20, %rsp >> >> hello_world_std.efi[0x140001b55]: 4c 8b 41 08 >> movq 0x8(%rcx), %r8 >> >> hello_world_std.efi[0x140001b59]: 4c 89 c0 >> movq %r8, %rax >> >> hello_world_std.efi[0x140001b5c]: 48 c1 f8 3f >> sarq $0x3f, %rax >> >> hello_world_std.efi[0x140001b60]: 48 8b 09 >> movq (%rcx), %rcx >> >> hello_world_std.efi[0x140001b63]: 48 01 c1 >> addq %rax, %rcx >> >> hello_world_std.efi[0x140001b66]: 4c 89 c2 >> movq %r8, %rdx >> >> hello_world_std.efi[0x140001b69]: 48 11 c2 >> adcq %rax, %rdx >> >> hello_world_std.efi[0x140001b6c]: 48 31 c1 >> xorq %rax, %rcx >> >> hello_world_std.efi[0x140001b6f]: 48 31 c2 >> xorq %rax, %rdx >> >> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 >> movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >> >> hello_world_std.efi[0x140001b7c]: 4c 21 c6 >> andq %r8, %rsi >> >> hello_world_std.efi[0x140001b7f]: e8 5c 55 00 00 >> callq 0x1400070e0 >> >> hello_world_std.efi[0x140001b84]: 48 09 f0 >> orq %rsi, %rax >> >> hello_world_std.efi[0x140001b87]: 48 83 c4 20 >> addq $0x20, %rsp >> >> hello_world_std.efi[0x140001b8b]: 5e >> popq %rsi >> >> hello_world_std.efi[0x140001b8c]: c3 >> retq >> >> >> So the faulting function is getting passed a bad pointer as its >> 1st arg. >> >> Thanks, >> >> Andrew Fish >> >>> On Jul 25, 2022, at 11:45 AM, Andrew Fish <afish@apple.com> >>> <mailto:afish@apple.com> wrote: >>> >>> Ops… Looks like your PE/COFF is linked at 0x0000000140000000, >>> so 0x140001b60 is the interesting bit. >>> >>> (lldb) dis -s 0x0000000140001B60 -b >>> hello_world_std.efi[0x140001b60]: 48 8b 09 >>> movq (%rcx), %rcx >>> hello_world_std.efi[0x140001b63]: 48 01 c1 >>> addq %rax, %rcx >>> hello_world_std.efi[0x140001b66]: 4c 89 c2 >>> movq %r8, %rdx >>> hello_world_std.efi[0x140001b69]: 48 11 c2 >>> adcq %rax, %rdx >>> hello_world_std.efi[0x140001b6c]: 48 31 c1 >>> xorq %rax, %rcx >>> hello_world_std.efi[0x140001b6f]: 48 31 c2 >>> xorq %rax, %rdx >>> hello_world_std.efi[0x140001b72]: 48 be 00 00 00 00 00 00 00 80 >>> movabsq $-0x8000000000000000, %rsi ; imm = 0x8000000000000000 >>> hello_world_std.efi[0x140001b7c]: 4c 21 c6 >>> andq %r8, %rsi >>> >>> RCX - FFFFFFFFFFFFFFFF >>> >>> So yea that looks like the fault. >>> >>> I don’t see that pattern in your .s file…. >>> >>> Can you figure out what function is @ 0x140001b60 in the PE/COFF >>> image. Do you have a map file from the linker? >>> >>> Thanks, >>> >>> Andrew Fish >>> >>> PS Again sorry I don’t have anything installed to crack PDB files. >>> >>> Thanks, >>> >>> Andrew Fish >>> >>>> On Jul 25, 2022, at 10:51 AM, Andrew Fish via groups.io >>>> <http://groups.io> <afish=apple.com@groups.io> >>>> <mailto:afish=apple.com@groups.io> wrote: >>>> >>>> Ayush, >>>> >>>> CR2 is the fault address so 0xFFFFFFFFFFFFFFFF. Given for EFI >>>> Virt == Physical the fault address looks like a bad pointer. >>>> >>>> Sorry I’ve not used VC++ in a long time so I don’t know how to >>>> debug with VC++, but If I was using clang/lldb I’d look at the >>>> source and assembly for the fault address. >>>> >>>> The image base is: 0x000000000603C000 >>>> The fault PC/RIP is: 000000000603DB60 >>>> >>>> So the faulting code is at 0x1B60 in the image. Given the >>>> images are linked at zero you should be able to load the build >>>> product into the debugger and look at what code is at offset >>>> 0x1B60. The same should work for any tools that dump the binary. >>>> >>>> Thanks, >>>> >>>> Andrew Fish >>>> >>>>> On Jul 25, 2022, at 10:33 AM, Ayush Singh >>>>> <ayushdevel1325@gmail.com> <mailto:ayushdevel1325@gmail.com> >>>>> wrote: >>>>> >>>>> Hello everyone.While running Rust tests in UEFI environment, I >>>>> have come across a numeric test that causes a pagefault. A >>>>> simple reproducible example for this is given below: >>>>> >>>>> ```rust >>>>> >>>>> fn main() { >>>>> use std::hint::black_box as b; >>>>> >>>>> let z: i128 = b(1); >>>>> assert!((-z as f64) < 0.0); >>>>> } >>>>> >>>>> ``` >>>>> >>>>> >>>>> The exception output is as follows: >>>>> >>>>> ``` >>>>> >>>>> !!!! X64 Exception Type - 0E(#PF - Page-Fault) CPU Apic ID - >>>>> 00000000 !!!! >>>>> ExceptionData - 0000000000000000 I:0 R:0 U:0 W:0 P:0 PK:0 SS:0 >>>>> SGX:0 >>>>> RIP - 000000000603DB60, CS - 0000000000000038, RFLAGS - >>>>> 0000000000000246 >>>>> RAX - 0000000000000000, RCX - FFFFFFFFFFFFFFFF, RDX - >>>>> FFFFFFFFFFFFFFFF >>>>> RBX - 0000000000000000, RSP - 0000000007EDF1D0, RBP - >>>>> 0000000007EDF4C0 >>>>> RSI - 0000000007EDF360, RDI - 0000000007EDF3C0 >>>>> R8 - 0000000000000000, R9 - 0000000000000038, R10 - >>>>> 0000000000000000 >>>>> R11 - 0000000000000000, R12 - 00000000060C6018, R13 - >>>>> 0000000007EDF520 >>>>> R14 - 0000000007EDF6A8, R15 - 0000000005FA9490 >>>>> DS - 0000000000000030, ES - 0000000000000030, FS - >>>>> 0000000000000030 >>>>> GS - 0000000000000030, SS - 0000000000000030 >>>>> CR0 - 0000000080010033, CR2 - FFFFFFFFFFFFFFFF, CR3 - >>>>> 0000000007C01000 >>>>> CR4 - 0000000000000668, CR8 - 0000000000000000 >>>>> DR0 - 0000000000000000, DR1 - 0000000000000000, DR2 - >>>>> 0000000000000000 >>>>> DR3 - 0000000000000000, DR6 - 00000000FFFF0FF0, DR7 - >>>>> 0000000000000400 >>>>> GDTR - 00000000079DE000 0000000000000047, LDTR - 0000000000000000 >>>>> IDTR - 0000000007418018 0000000000000FFF, TR - 0000000000000000 >>>>> FXSAVE_STATE - 0000000007EDEE30 >>>>> !!!! Find image based on IP(0x603DB60) >>>>> /var/home/ayush/Documents/Programming/Rust/uefi/hello_world_std/target/x86_64-unknown-uefi/debug/deps/hello_world_std-338028f9369e2d42.pdb >>>>> (ImageBase=000000000603C000, EntryPoint=000000000603D8C0) !!!! >>>>> >>>>> ``` >>>>> >>>>> >>>>> From my testing, the exception only occurs when a few >>>>> conditions are met. >>>>> >>>>> 1. The binary is compiled in Debug mode. No error in Release mode. >>>>> >>>>> 2. `i128` is in a black_box [1]. Does not occur if `black_box` >>>>> is not present. >>>>> >>>>> 3. It has to be `i128`. `i64` or something else work fine. >>>>> >>>>> 4. The cast has to be done on `-z`. Doing the same with `+z` >>>>> is fine. >>>>> >>>>> >>>>> I have also been discussing this in the Rust zulipchat [2], so >>>>> feel free to chime in there. >>>>> >>>>> >>>>> Additionally, here are links for more information about this >>>>> program: >>>>> >>>>> 1. >>>>> Assembly:https://rust-lang.zulipchat.com/user_uploads/4715/od51Y9Dkfjahcg9HHcOud8Fm/hello_world_std-338028f9369e2d42.s >>>>> >>>>> 2. EFI >>>>> Binary:https://rust-lang.zulipchat.com/user_uploads/4715/CknqtXLR8SaJZmyOnXctQkpL/hello_world_std.efi >>>>> >>>>> 3. PDB >>>>> file:https://rust-lang.zulipchat.com/user_uploads/4715/zV4i6DsjgQXotp_gS1naEsU0/hello_world_std-338028f9369e2d42.pdb >>>>> >>>>> >>>>> Yours Sincerely, >>>>> >>>>> Ayush Singh >>>>> >>>>> >>>>> [1]:https://doc.rust-lang.org/std/hint/fn.black_box.html >>>>> >>>>> [2]:https://rust-lang.zulipchat.com/#narrow/stream/182449-t-compiler.2Fhelp/topic/Casting.20i128.20to.20f64.20in.20black_box.20causes.20exception.20in.20UEFI >>>>> >>>>> >>>>> >>>> >>> >> > > > > > -- > Pedro Falcato [-- Attachment #2: Type: text/html, Size: 75463 bytes --] ^ permalink raw reply [flat|nested] 11+ messages in thread
end of thread, other threads:[~2022-07-27 6:01 UTC | newest] Thread overview: 11+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2022-07-25 17:33 Casting i128 into f64 in UEFI Rust pagefaults Ayush Singh 2022-07-25 17:51 ` [edk2-devel] " Andrew Fish [not found] ` <170523E2507C1293.4676@groups.io> 2022-07-25 18:45 ` Andrew Fish 2022-07-25 18:54 ` Andrew Fish 2022-07-26 5:43 ` Ayush Singh 2022-07-26 17:50 ` Andrew Fish 2022-07-26 19:15 ` Ayush Singh 2022-07-26 21:38 ` Andrew Fish 2022-07-27 6:01 ` Ayush Singh 2022-07-26 19:12 ` Pedro Falcato 2022-07-26 19:24 ` Ayush Singh
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox