RFR: 8315066: Add unsigned bounds and known bits to TypeInt/Long [v53]

Emanuel Peter epeter at openjdk.org
Thu May 1 07:37:01 UTC 2025


On Thu, 1 May 2025 07:00:46 GMT, Quan Anh Mai <qamai at openjdk.org> wrote:

>> Hi,
>> 
>> This patch adds unsigned bounds and known bits constraints to TypeInt and TypeLong. This opens more transformation opportunities in an elegant manner as well as helps avoid some ad-hoc rules in Hotspot.
>> 
>> In general, a `TypeInt/Long` represents a set of values `x` that satisfies: `x s>= lo && x s<= hi && x u>= ulo && x u<= uhi && (x & zeros) == 0 && (x & ones) == ones`. These constraints are not independent, e.g. an int that lies in [0, 3] in signed domain must also lie in [0, 3] in unsigned domain and have all bits but the last 2 being unset. As a result, we must canonicalize the constraints (tighten the constraints so that they are optimal) before constructing a `TypeInt/Long` instance.
>> 
>> This is extracted from #15440 , node value transformations are left for later PRs. I have also added unit tests to verify the soundness of constraint normalization.
>> 
>> Please kindly review, thanks a lot.
>> 
>> Testing
>> 
>> - [x] GHA
>> - [x] Linux x64, tier 1-4
>
> Quan Anh Mai has updated the pull request incrementally with two additional commits since the last revision:
> 
>  - wording
>  - grammar, more details for non-existence

Can you do the analogue with the else (one violation) case?
That one is probably a bit harder, but I have faith in you ;)

src/hotspot/share/opto/rangeinference.cpp line 297:

> 295:     // lo up to a multiple of alignment, we add alignment to the rounded down
> 296:     // value.
> 297:     //           1 1 0 1 0 0 0 0

Suggestion:

    // This is the first value which have the violated bit being 1, which means
    // that the result should not be smaller than this. This is a standard
    // operation to align a value up to a certain power of 2.
    // Since alignment is a power of 2, -alignment is a value having all the
    // bits being 1 upto the location of the bit in alignment (in the example,
    // -alignment = 11110000). As a result, lo & -alignment set all bits after
    // the bit in alignment to 0, which is equivalent to rounding lo down to a
    // multiple of alignment. Since lo is not divisible by alignment, to round
    // lo up to a multiple of alignment, we add alignment to the rounded down
    // value.
    //           1 1 0 1 0 0 0 0
    // We now have:
    // - new_lo[x] = lo[x], for 0 <= x < i        (2.5)
    // - new_lo[i] = 1                            (2.6)
    // - new_lo[x] = 0, for x > i                 (not yet 2.7)

src/hotspot/share/opto/rangeinference.cpp line 301:

> 299:     // Our current new_lo satisfies zeros, just OR it with ones to obtain the
> 300:     // correct result
> 301:     //           1 1 0 1 0 0 1 0

Suggestion:

    // Our current new_lo satisfies zeros, just OR it with ones to obtain the
    // correct result
    //           1 1 0 1 0 0 1 0
    // Since the bits at i and before are not changed, we now have:
    // - new_lo[x] = lo[x], for 0 <= x < i        (2.5)
    // - new_lo[i] = 1                            (2.6)
    // - new_lo[x] = ones[x], for x > i           (2.7)
    // Hence: new_lo = r

-------------

PR Comment: https://git.openjdk.org/jdk/pull/17508#issuecomment-2844258870
PR Review Comment: https://git.openjdk.org/jdk/pull/17508#discussion_r2069933569
PR Review Comment: https://git.openjdk.org/jdk/pull/17508#discussion_r2069935004


More information about the hotspot-compiler-dev mailing list