Christian Sayer
2009-Mar-31 09:18 UTC
[LLVMdev] adjust address calculus for an architecture that does not address bytes
Hi, my target architecture has a kind of "16bit addressing mode", i.e. one address does not address 8 bit but a 16bit chunk. Consequently, every constant used to calculate effective addresses must be divided by two. So far this is not such a problem for stack objects since FrameIndexes, function arguments etc. have a lot of custom lowering code where this can be done. But when it comes to pointer arithmetic resulting from the GetElementPtr instruction this is less obvious. At first I thought this could be handled when lowering loads and stores, but I realize that I can only catch the targeted addresses of loads/stores here - however address calculation nodes may occur anywhere in a DAG. So my first impulse would be to adjust the constants when the GEP instructions are transformed to ADDs. Afaics his would mean to change the TargetData class, which is not meant to be subclassed. Is there a cleaner solution without modifying llvm? Regards, Christian -- CONFIDENTIAL NOTICE: The contents of this message, including any attachments, are confidential and are intended solely for the use of the person or entity to whom the message was addressed. If you are not the intended recipient of this message, please be advised that any dissemination, distribution, or use of the contents of this message is strictly prohibited. If you received this message in error, please notify the sender. Please also permanently delete all copies of the original message and any attached documentation. Thank you.
Richard Osborne
2009-Mar-31 19:22 UTC
[LLVMdev] adjust address calculus for an architecture that does not address bytes
Christian Sayer wrote:> Hi, > my target architecture has a kind of "16bit addressing mode", i.e. one address does not address 8 bit but a 16bit chunk. Consequently, every constant used to calculate effective addresses must be divided by two. > So far this is not such a problem for stack objects since FrameIndexes, function arguments etc. have a lot of custom lowering code where this can be done. > But when it comes to pointer arithmetic resulting from the GetElementPtr instruction this is less obvious. > At first I thought this could be handled when lowering loads and stores, but I realize that I can only catch the targeted addresses of loads/stores here - however address calculation nodes may occur anywhere in a DAG. > > So my first impulse would be to adjust the constants when the GEP instructions are transformed to ADDs. Afaics his would mean to change the TargetData class, which is not meant to be subclassed. > Is there a cleaner solution without modifying llvm? > > Regards, ChristianThe XCore has loads / stores where the offset is scaled by the size of the load or store. For example the load word instruction LDW takes an offset which is multiplied by 4 and added to the base pointer. This is dealt with in the patterns defined in XCoreInstrInfo.td. The following pattern is used for LDW: def : Pat<(load (add GRRegs:$addr, immUs4:$offset)), (LDW_2rus GRRegs:$addr, (div4_xform immUs4:$offset))>; immUs4 is true when offset is a multiple of 4 and the offset divided by 4 fits in an immediate. The div4_xform xform divides a constant by 4. These are both defined in XCoreInstrInfo.td. It sounds like your target may be able to use a similar approach. -- Richard Osborne | XMOS http://www.xmos.com
Christian Sayer
2009-Apr-01 08:40 UTC
[LLVMdev] adjust address calculus for an architecture that does not address bytes
> > At first I thought this could be handled when lowering > loads and stores, but I realize that I can only catch the > targeted addresses of loads/stores here - however address > calculation nodes may occur anywhere in a DAG. > > > > So my first impulse would be to adjust the constants when > the GEP instructions are transformed to ADDs. Afaics his > would mean to change the TargetData class, which is not meant > to be subclassed. > > Is there a cleaner solution without modifying llvm? > > > > Regards, Christian > The XCore has loads / stores where the offset is scaled by the size of > the load or store. For example the load word instruction LDW takes an > offset which is multiplied by 4 and added to the base pointer. This is > dealt with in the patterns defined in XCoreInstrInfo.td. The following > pattern is used for LDW: > > def : Pat<(load (add GRRegs:$addr, immUs4:$offset)), > (LDW_2rus GRRegs:$addr, (div4_xform immUs4:$offset))>; >Richard, thanks for your suggestion. However, I think what you describe is what I meant by 'only catch the targeted addresses of loads/stores', i.e. the address the instruction is reading from/writing to. However, if I have e.g. a chunk of code which stores the address of the second element of struct str somewhere into another struct pstr: %0 = getelementptr %struct.str* %s, i32 0, i32 1 ; <i16*> [#uses=1] %1 = getelementptr %struct.pstr* %ps, i32 0, i32 5 ; <i16**> [#uses=1] store i16* %0, i16** %1, align 4 Your suggestion allows to store the i32* at the right place in %struct.pstr, but the first GEP instruction adds the size of the first element - in bytes! - of str to the address of str to get the address of the second element. I need that size (aka offset) to be in respect of 16bit. (Note also that e.g. arbitrary pointer arithmetics could be done on %0 - when it comes to lowering, we cannot know if an ADD node comes from a GEP or not) Or to put it shortly, regarding the property of char being the smallest addressable piece of data, sizeof(char) is 16 on my architecture, but "8" is hard coded in TargetData (maybe 'char' should rather be replaced by 'byte' in the last sentence). Well my current workaround is just to divide offsets by 2 when resolving GEP instructions but I still hope there is a good way to do this in the backend. I think this would be to subclass TargetData in the backend - I'd appreciate if someone could confirm or not that there isn't another option within the current way of designing a backend. Thanks a lot, Christian -- CONFIDENTIAL NOTICE: The contents of this message, including any attachments, are confidential and are intended solely for the use of the person or entity to whom the message was addressed. If you are not the intended recipient of this message, please be advised that any dissemination, distribution, or use of the contents of this message is strictly prohibited. If you received this message in error, please notify the sender. Please also permanently delete all copies of the original message and any attached documentation. Thank you.
Reasonably Related Threads
- [LLVMdev] adjust address calculus for an architecture that does not address bytes
- [LLVMdev] adjust address calculus for an architecture that does not address bytes
- Backend subtraction changed to negative addition
- Converting a string vector with names to a numeric vector with names
- ISelDAGToDAG breaks node ordering