Skip to content

Commit

Permalink
Merge pull request #697 from zakkak/2024-03-13-backports-17-sync
Browse files Browse the repository at this point in the history
2024-03-13 backports 17 sync
  • Loading branch information
zakkak authored Mar 26, 2024
2 parents 556d068 + 4ec27e3 commit 74017a3
Show file tree
Hide file tree
Showing 125 changed files with 2,634 additions and 1,087 deletions.
2 changes: 1 addition & 1 deletion ci/common.jsonnet
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ local common_json = import "../common.json";

# The devkits versions reflect those used to build the JVMCI JDKs (e.g., see devkit_platform_revisions in <jdk>/make/conf/jib-profiles.js)
devkits: {
"windows-jdk17": { packages+: { "devkit:VS2022-17.1.0+1": "==0" }},
"windows-jdk17": { packages+: { "devkit:VS2022-17.6.5+1": "==0" }},
"windows-jdk19": { packages+: { "devkit:VS2022-17.1.0+1": "==0" }},
"windows-jdk20": { packages+: { "devkit:VS2022-17.1.0+1": "==0" }},
"linux-jdk17": { packages+: { "devkit:gcc10.3.0-OL6.4+1": "==0" }},
Expand Down
6 changes: 3 additions & 3 deletions common.json
Original file line number Diff line number Diff line change
Expand Up @@ -14,9 +14,9 @@
"labsjdk-ce-17": {"name": "labsjdk", "version": "ce-17.0.9+9-jvmci-23.0-b22", "platformspecific": true },
"labsjdk-ce-17Debug": {"name": "labsjdk", "version": "ce-17.0.9+9-jvmci-23.0-b22-debug", "platformspecific": true },
"labsjdk-ce-17-llvm": {"name": "labsjdk", "version": "ce-17.0.9+9-jvmci-23.0-b22-sulong", "platformspecific": true },
"labsjdk-ee-17": {"name": "labsjdk", "version": "ee-17.0.10+9-jvmci-23.0-b25", "platformspecific": true },
"labsjdk-ee-17Debug": {"name": "labsjdk", "version": "ee-17.0.10+9-jvmci-23.0-b25-debug", "platformspecific": true },
"labsjdk-ee-17-llvm": {"name": "labsjdk", "version": "ee-17.0.10+9-jvmci-23.0-b25-sulong", "platformspecific": true },
"labsjdk-ee-17": {"name": "labsjdk", "version": "ee-17.0.11+6-jvmci-23.0-b33", "platformspecific": true },
"labsjdk-ee-17Debug": {"name": "labsjdk", "version": "ee-17.0.11+6-jvmci-23.0-b33-debug", "platformspecific": true },
"labsjdk-ee-17-llvm": {"name": "labsjdk", "version": "ee-17.0.11+6-jvmci-23.0-b33-sulong", "platformspecific": true },

"oraclejdk19": {"name": "jpg-jdk", "version": "19", "build_id": "26", "release": true, "platformspecific": true, "extrabundles": ["static-libs"]},
"labsjdk-ce-19": {"name": "labsjdk", "version": "ce-19.0.1+10-jvmci-23.0-b04", "platformspecific": true },
Expand Down
2 changes: 1 addition & 1 deletion compiler/mx.compiler/suite.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"sourceinprojectwhitelist" : [],

"groupId" : "org.graalvm.compiler",
"version" : "23.0.3.1",
"version" : "23.0.4.0",
"release" : False,
"url" : "http://www.graalvm.org/",
"developer" : {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -257,7 +257,7 @@ public String toString() {
private Assumption[] assumptions;

/**
* The list of the methods whose bytecodes were used as input to the compilation. If
* The set of the methods whose bytecodes were used as input to the compilation. If
* {@code null}, then the compilation did not record method dependencies. Otherwise, the first
* element of this array is the root method of the compilation.
*/
Expand Down Expand Up @@ -361,45 +361,36 @@ public Assumption[] getAssumptions() {
}

/**
* Sets the methods whose bytecodes were used as input to the compilation.
* Records the set of methods whose bytecodes were used as input to the compilation.
*
* @param rootMethod the root method of the compilation
* @param inlinedMethods the methods inlined during compilation
* @param inlinedMethods the methods inlined during compilation (may contain duplicates)
*/
public void setMethods(ResolvedJavaMethod rootMethod, Collection<ResolvedJavaMethod> inlinedMethods) {
checkOpen();
assert rootMethod != null;
assert inlinedMethods != null;
if (inlinedMethods.contains(rootMethod)) {
methods = inlinedMethods.toArray(new ResolvedJavaMethod[inlinedMethods.size()]);
for (int i = 0; i < methods.length; i++) {
if (methods[i].equals(rootMethod)) {
if (i != 0) {
ResolvedJavaMethod tmp = methods[0];
methods[0] = methods[i];
methods[i] = tmp;
}
break;
}
}
} else {
methods = new ResolvedJavaMethod[1 + inlinedMethods.size()];
methods[0] = rootMethod;
int i = 1;
for (ResolvedJavaMethod m : inlinedMethods) {
methods[i++] = m;
}

EconomicSet<ResolvedJavaMethod> methodSet = EconomicSet.create(inlinedMethods.size());
methodSet.addAll(inlinedMethods);
methodSet.remove(rootMethod);
methods = new ResolvedJavaMethod[1 + methodSet.size()];
methods[0] = rootMethod;
int i = 1;
for (ResolvedJavaMethod m : methodSet) {
methods[i++] = m;
}
}

/**
* Gets the methods whose bytecodes were used as input to the compilation.
* Gets the set of methods whose bytecodes were used as input to the compilation.
*
* The caller must not modify the contents of the returned array.
*
* @return {@code null} if the compilation did not record method dependencies otherwise the
* methods whose bytecodes were used as input to the compilation with the first element
* being the root method of the compilation
* being the root method of the compilation. The entries in a non-null returned array
* are guaranteed to be unique.
*/
public ResolvedJavaMethod[] getMethods() {
return methods;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -985,7 +985,16 @@ public IntegerConvertOp<T> unwrap() {
}

/**
* Computes the stamp of the input for the given output stamp.
* Computes the stamp of the input for the given output stamp. This method returns
* {@code null} if a stamp cannot be inverted for an operation (i.e., {@link Narrow}). When
* inverting non-exact stamps, i.e. {@code 0xx0xxxx}, the inversion keeps all available
* information. If the stamp to invert contains contradictions regarding the post condition
* of the operation, an empty stamp is returned. An example for a contradiction would be a
* {@code SignExtend} with both {@code 0} and {@code 1} in the extension.
*
* @return {@code null} - if stamp inversion is not supported </br>
* empty stamp - if the output stamp contains contradictions </br>
* inverted output stamp - otherwise </br>
*/
public abstract Stamp invertStamp(int inputBits, int resultBits, Stamp outStamp);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1976,24 +1976,31 @@ public Stamp invertStamp(int inputBits, int resultBits, Stamp outStamp) {
}

/*
* there is no guarantee that a given result is in the range of the
* There is no guarantee that a given result is in the range of the
* input because of holes in ranges resulting from signed / unsigned
* extension, so we must ensure that the extension bits are all zeros
* otherwise we cannot represent the result, and we have to return an
* unrestricted stamp
* empty stamp.
*
* This case is much less likely to happen than the case for SignExtend
* but the following is defensive to ensure that we only perform valid
* inversions.
*/
long alwaysSetOutputBits = stamp.mustBeSet();
long alwaysSetExtensionBits = alwaysSetOutputBits >>> inputBits;
if (alwaysSetExtensionBits != 0) {
createEmptyStamp(inputBits);
long mustBeSetOutputBits = stamp.mustBeSet();
long mustBeSetExtensionBits = mustBeSetOutputBits >>> inputBits;
if (mustBeSetExtensionBits != 0) {
return createEmptyStamp(inputBits);
}

long inputMask = CodeUtil.mask(inputBits);
return StampFactory.forUnsignedInteger(inputBits, stamp.lowerBound(), stamp.upperBound(), stamp.mustBeSet() & inputMask, stamp.mayBeSet() & inputMask);
/*
* The output of a zero extend cannot be negative. Setting the lower
* bound > 0 enables inverting stamps like [-8, 16] without having to
* return an unrestricted stamp.
*/
long lowerBound = Math.max(stamp.lowerBound(), 0);
assert stamp.upperBound() >= 0 : "Cannot invert ZeroExtend for stamp with msb=1, which implies a negative value after ZeroExtend!";

return StampFactory.forUnsignedInteger(inputBits, lowerBound, stamp.upperBound(), stamp.mustBeSet(), stamp.mayBeSet());
}
},

Expand Down Expand Up @@ -2029,11 +2036,11 @@ public Stamp invertStamp(int inputBits, int resultBits, Stamp outStamp) {
}

/*
* there is no guarantee that a given result bit is in the range of the
* There is no guarantee that a given result bit is in the range of the
* input because of holes in ranges resulting from signed / unsigned
* extension, so we must ensure that the extension bits are either all
* zeros or all ones otherwise we cannot represent the result, and we
* have to return an unrestricted stamp
* have to return an empty stamp.
*
* As an example:
* @formatter:off
Expand All @@ -2056,21 +2063,75 @@ public Stamp invertStamp(int inputBits, int resultBits, Stamp outStamp) {
* ZeroExtend to get 0xb308, but then we try to invert the SignExtend.
* The sign extend could only have produced 0xff__ or 0x00__ from a byte
* but 0xb308 has 0xb3, and so we cannot invert the stamp. In this case
* the only sensible inversion is the unrestricted stamp.
* the only sensible inversion is the empty stamp.
*/
long alwaysSetOutputBits = stamp.mustBeSet();
long alwaysSetExtensionBits = alwaysSetOutputBits >>> inputBits;
long outputMask = CodeUtil.mask(resultBits);
if (alwaysSetExtensionBits != 0 && alwaysSetExtensionBits != (outputMask >>> inputBits)) {
long mustBeSetExtensionBits = stamp.mustBeSet() >>> inputBits;
long mayBeSetExtensionBits = stamp.mayBeSet() >>> inputBits;
long extensionMask = CodeUtil.mask(stamp.getBits()) >>> inputBits;

boolean zeroInExtension = mayBeSetExtensionBits != extensionMask;
boolean oneInExtension = mustBeSetExtensionBits != 0;
boolean inputMSBOne = significantBit(inputBits, stamp.mustBeSet()) == 1;
boolean inputMSBZero = significantBit(inputBits, stamp.mayBeSet()) == 0;

/*
* Checks for contradictions in the extension and returns an empty stamp in such cases.
* Examples for contradictions for a stamp after an artificial 4->8 bit sign extension:
*
* @formatter:off
*
* 1) 01xx xxxx --> extension cannot contain zeroes and ones
* 2) x0xx 1xxx --> extension cannot contain a zero if the MSB of the extended value is 1
* 3) xx1x 0xxx --> extension cannot contain a one if the MSB of the extended value is 0
*
* @formatter:on
*/
if ((zeroInExtension && oneInExtension) || (inputMSBOne && zeroInExtension) || (inputMSBZero && oneInExtension)) {
return createEmptyStamp(inputBits);
}

long inputMask = CodeUtil.mask(inputBits);
if (inputBits < stamp.getBits() && (stamp.contains(CodeUtil.minValue(inputBits) - 1) || stamp.contains(CodeUtil.maxValue(inputBits) + 1))) {
// Truncation will cause this value to wrap around
return create(inputBits).unrestricted();
long inputMustBeSet = stamp.mustBeSet() & inputMask;
long inputMayBeSet = stamp.mayBeSet() & inputMask;

if (!inputMSBOne && !inputMSBZero) {
/*
* Input MSB yet unknown, try to infer it from the extension:
*
* @formatter:off
*
* xx0x xxxx implies that the extension is 0000 which implies that the MSB of the input is 0
* x1xx xxxx implies that the extension is 1111 which implies that the MSB of the input is 1
*
* @formatter:on
*/
if (zeroInExtension) {
long msbZeroMask = ~(1 << (inputBits - 1));
inputMustBeSet &= msbZeroMask;
inputMayBeSet &= msbZeroMask;
} else if (oneInExtension) {
long msbOneMask = 1 << (inputBits - 1);
inputMustBeSet |= msbOneMask;
inputMayBeSet |= msbOneMask;
}
}
return StampFactory.forIntegerWithMask(inputBits, stamp.lowerBound(), stamp.upperBound(), stamp.mustBeSet() & inputMask, stamp.mayBeSet() & inputMask);

// Calculate conservative bounds for the input.
long inputUpperBound = maxValueForMasks(inputBits, inputMustBeSet, inputMayBeSet);
long inputLowerBound = minValueForMasks(inputBits, inputMustBeSet, inputMayBeSet);

/*
* If the bounds calculated for the input stamp do not overlap with the
* bounds for the stamp to invert, return an empty stamp. Otherwise,
* refine the conservative stamp for the input.
*/
if ((stamp.upperBound() < inputLowerBound) || (stamp.lowerBound() > inputUpperBound)) {
return createEmptyStamp(inputBits);
}
inputUpperBound = Math.min(inputUpperBound, stamp.upperBound());
inputLowerBound = Math.max(inputLowerBound, stamp.lowerBound());

return StampFactory.forIntegerWithMask(inputBits, inputLowerBound, inputUpperBound, inputMustBeSet, inputMayBeSet);
}
},

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -161,6 +161,30 @@ public static IntegerStamp forUnsignedInteger(int bits, long unsignedLowerBound,
return forUnsignedInteger(bits, unsignedLowerBound, unsignedUpperBound, 0, CodeUtil.mask(bits));
}

/**
* Creates an IntegerStamp from the given unsigned bounds and bit masks. This method returns an
* empty stamp if the unsigned lower bound is larger than the unsigned upper bound. If the sign
* of lower and upper bound differs after sign extension to the specified length ({@code bits}),
* this method returns an unrestricted stamp with respect to the bounds. {@code mayBeSet} or
* {@code mustBeSet} can restrict the bounds nevertheless. Take the following example when
* inverting a zero extended 32bit stamp to the 8bit stamp before extension:
*
* </p>
* 32bit stamp [0, 192] 00...00 xxxxxxx0
* </p>
* When converting the bounds to 8bit, they have different signs, i.e.:
* </p>
* lowerUnsigned = 0000 0000 and upperUnsigned = 1100 0000
* </p>
* In order to respect the (unsigned) boundaries of the extended value, the signed input can be:
* </p>
* 0000 0000 - 0111 1111, i.e. 0 to 127 </br>
* or </br>
* 1000 0000 - 1100 0000, i.e. -128 to -64
* </p>
* The resulting interval [-128, -64]u[0, 127] cannot be represented by a single upper and lower
* bound. Thus, we have to return an unrestricted stamp, with respect to the bounds.
*/
public static IntegerStamp forUnsignedInteger(int bits, long unsignedLowerBound, long unsignedUpperBound, long mustBeSet, long mayBeSet) {
if (Long.compareUnsigned(unsignedLowerBound, unsignedUpperBound) > 0) {
return IntegerStamp.createEmptyStamp(bits);
Expand Down
Loading

0 comments on commit 74017a3

Please sign in to comment.