When the IR specifies a 32 bit load can it be changed to a narrower load? What if the load is from memory (e.g. a peripheral) that only supports 32-bit access? Consider the following IR: ---- target datalayout = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:32:32" target triple = "thumbv7m-unknown-unknown" @f = external global i32 define zeroext i8 @bar() nounwind { L.0: %rv.0 = alloca i8 %0 = load i32* @f %1 = trunc i32 %0 to i8 ret i8 %1 } ---- Which for the arm cortex-m3 generates: ---- bar: movw r0, :lower16:f movt r0, :upper16:f ldrb r0, [r0] bx lr ---- Although we are only interested in low 8-bits, the load MUST be a 32-bit load. Using a "load volatile" fixes this, but this is overkill as the memory location is not volatile. Am I missing something, or is this a bug? brian
Hi Brian, On Sep 11, 2014, at 3:03 PM, Bagel <bagel99 at gmail.com> wrote:> When the IR specifies a 32 bit load can it be changed to a narrower load? > What if the load is from memory (e.g. a peripheral) that only supports 32-bit > access? > Consider the following IR: > ---- > target datalayout = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:32:32" > target triple = "thumbv7m-unknown-unknown" > @f = external global i32 > define zeroext i8 @bar() nounwind { > L.0: > %rv.0 = alloca i8 > %0 = load i32* @f > %1 = trunc i32 %0 to i8 > ret i8 %1 > } > ---- > Which for the arm cortex-m3 generates: > ---- > bar: > movw r0, :lower16:f > movt r0, :upper16:f > ldrb r0, [r0] > bx lr > ---- > Although we are only interested in low 8-bits, the load MUST be a 32-bit load.I believe this is correct. As long as loading an i8 is legal, I do not think we should bother loading the whole 32 bits. Why do you think this is a bug? Thanks, -Quentin> > Using a "load volatile" fixes this, but this is overkill as the memory location > is not volatile. > > Am I missing something, or is this a bug? > > brian > _______________________________________________ > LLVM Developers mailing list > LLVMdev at cs.uiuc.edu http://llvm.cs.uiuc.edu > http://lists.cs.uiuc.edu/mailman/listinfo/llvmdev
On 09/11/2014 05:33 PM, Quentin Colombet wrote:> Hi Brian, > > On Sep 11, 2014, at 3:03 PM, Bagel <bagel99 at gmail.com> wrote: > >> When the IR specifies a 32 bit load can it be changed to a narrower >> load? What if the load is from memory (e.g. a peripheral) that only >> supports 32-bit access? Consider the following IR: ---- target datalayout >> = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:32:32" target >> triple = "thumbv7m-unknown-unknown" @f = external global i32 define >> zeroext i8 @bar() nounwind { L.0: %rv.0 = alloca i8 %0 = load i32* @f %1 >> = trunc i32 %0 to i8 ret i8 %1 } ---- Which for the arm cortex-m3 >> generates: ---- bar: movw r0, :lower16:f movt r0, :upper16:f ldrb r0, >> [r0] bx lr ---- Although we are only interested in low 8-bits, the load >> MUST be a 32-bit load. > > I believe this is correct. As long as loading an i8 is legal, I do not > think we should bother loading the whole 32 bits. > > Why do you think this is a bug? > > Thanks, -QuentinThe phrase "As long as loading an i8 is legal" is the whole point. What if it isn't? How do I specify that (should of specifying the load as volatile, which is overkill)? As an author of a front end, I want to know what the contract is when I say load 32-bits? When I say load 32-bits I mean load 32-bits. I think it's a bug because there is no good way do avoid it and it breaks device drivers. brian