Richard Guenther <richard.guent...@gmail.com> writes: > On Fri, Oct 5, 2012 at 2:26 PM, Richard Sandiford > <rdsandif...@googlemail.com> wrote: >> Richard Guenther <richard.guent...@gmail.com> writes: >>> On Fri, Oct 5, 2012 at 1:24 PM, Richard Sandiford >>> <rdsandif...@googlemail.com> wrote: >>>> Richard Guenther <richard.guent...@gmail.com> writes: >>>>> The issue is that unlike RTL where we "construct" double-ints from >>>>> CONST_INT/CONST_DOUBLE right now, tree has the double-int >>>>> _embedded_. That's why I say that the thing we embed in >>>>> a CONST_WIDE_INT or a tree INTEGER_CST needs to be >>>>> "bare metal", and that's what I would call wide-int. >>>> >>>> OK, but that's deliberately not what Kenny's patch calls "wide int". >>>> The whole idea is that the "bare metal" thing we embed in a >>>> CONST_WIDE_INT or tree isn't (and doesn't need to be) the same >>>> as the type that we use to operate on integers. That bare-metal >>>> thing doesn't even have to have a fixed width. (CONST_WIDE_INT >>>> doesn't have a fixed width, it's only as big as the integer >>>> needs it to be.) >>> >>> Ok, let's rephrase it this way then: the "bare metal" thing used >>> for the storage should ideally be the same in the tree IL and the RTL >>> IL _and_ the higher-level abstract wide-int. >> >> Hmm, OK, that's a straight disagreement then. >> >>>>> So to me wide-ints provide the higher-level abstraction ontop of >>>>> double-ints (which would remain the storage entity). >>>>> >>>>> Such higher-level abstraction is very useful, also for double-ints and >>>>> also on the tree level. There is no requirement to provide bigger >>>>> double-int (or wide-int) for this. Let's call this abstraction >>>>> wide-int (as opposed to my suggested more piecemail double_sint, >>>>> double_uint). You can perfectly model it ontop of the existing >>>>> double_int storage. >>>>> >>>>> As of providing larger "double-ints" - there is not much code left >>>>> (ok, quite an overstatement ;)) that relies on the implementation >>>>> detail of double-int containing exactly two HOST_WIDE_INTs. >>>>> The exact purpose of double-ints was to _hide_ this (previously >>>>> we only had routines like mul_double_with_sign which take >>>>> two HOST_WIDE_INT components). Most code dealing with >>>>> the implementation detail is code interfacing with middle-end >>>>> routines that take a HOST_WIDE_INT argument (thus the >>>>> double_int_fits_hwi_p predicates) - even wide_int has to support >>>>> this kind of interfacing. >>>>> >>>>> So, after introducing wide_int that just wraps double_int and >>>>> changing all user code (hopefully all, I guess mostly all), we'd >>>>> tackle the issue that the size of double_int's is host dependent. >>>>> A simple solution is to make it's size dependent on a target macro >>>>> (yes, macro ...), so on a 32bit HWI host targeting a 64bit 'HWI' target >>>>> you'd simply have four HWIs in the 'double-int' storage (and >>>>> arithmetic needs to be generalized to support this). >>>> >>>> I just don't see why this is a good thing. The constraints >>>> are different when storing integers and when operating on them. >>>> When operating on them, we want something that is easily constructed >>>> on the stack, so we can create temporary structures very cheaply, >>>> and can easily pass and return them. We happen to know at GCC's >>>> compile time how big the biggest integer will ever be, so it makes >>>> sense for wide_int to be that wide. >>> >>> I'm not arguing against this. I'm just saying that the internal >>> representation will depend on the host - not the number of total >>> bits, but the number of pieces. >> >> Sure, but Kenny already has a macro to specify how many bits we need >> (MAX_BITSIZE_MODE_ANY_INT). We can certainly wrap: >> >> HOST_WIDE_INT val[MAX_BITSIZE_MODE_ANY_INT / HOST_BITS_PER_WIDE_INT]; >> >> in a typedef if that's what you prefer. > > I'd prefer it to be initially double_int, and later "fixed" to double_int > with a member like the above. Possibly renamed as well.
I'd like to avoid that. The current double_int code really isn't useful to the patch. double_int doesn't have the right representation because it uses a low/high pair (of slightly different types) rather than a parameterised array. The operators don't have the right interface, for the reasons I described later. They don't have the right implementation because they're specific to HWI pairs rather than parameterised based on the number of HWIs. Once you change the name, the internal representation, the operator interface, and the operator implementation, there isn't a lot left to keep. >>> How is CONST_WIDE_INT variable size? >> >> It's just the usual trailing variable-length array thing. > > Good. Do you get rid of CONST_DOUBLE (for integers) at the same time? Yeah. I initially thought it might be OK to keep them and have CONST_INT, integer CONST_DOUBLEs and CONST_WIDE_INT alongside each other. (The way the patch is structured means that the choice of whether to keep integer CONST_DOUBLEs can be changed very easily.) But Kenny convinced me it was a bad idea. Richard