168 return String.format("Range check failed: %s", args);
169 } else if (args == null) {
170 return String.format("Range check failed: %s", checkKind);
171 }
172
173 int argSize = 0;
174 switch (checkKind) {
175 case "checkIndex":
176 argSize = 2;
177 break;
178 case "checkFromToIndex":
179 case "checkFromIndexSize":
180 argSize = 3;
181 break;
182 default:
183 }
184
185 // Switch to default if fewer or more arguments than required are supplied
186 switch ((args.size() != argSize) ? "" : checkKind) {
187 case "checkIndex":
188 return String.format("Index %d out-of-bounds for length %d",
189 args.get(0), args.get(1));
190 case "checkFromToIndex":
191 return String.format("Range [%d, %d) out-of-bounds for length %d",
192 args.get(0), args.get(1), args.get(2));
193 case "checkFromIndexSize":
194 return String.format("Range [%d, %<d + %d) out-of-bounds for length %d",
195 args.get(0), args.get(1), args.get(2));
196 default:
197 return String.format("Range check failed: %s %s", checkKind, args);
198 }
199 }
200
201 /**
202 * Checks if the {@code index} is within the bounds of the range from
203 * {@code 0} (inclusive) to {@code length} (exclusive).
204 *
205 * <p>The {@code index} is defined to be out-of-bounds if any of the
206 * following inequalities is true:
207 * <ul>
208 * <li>{@code index < 0}</li>
209 * <li>{@code index >= length}</li>
210 * <li>{@code length < 0}, which is implied from the former inequalities</li>
211 * </ul>
212 *
213 * <p>If the {@code index} is out-of-bounds, then a runtime exception is
214 * thrown that is the result of applying the following arguments to the
215 * exception formatter: the name of this method, {@code checkIndex};
216 * and an unmodifiable list integers whose values are, in order, the
217 * out-of-bounds arguments {@code index} and {@code length}.
218 *
219 * @param <X> the type of runtime exception to throw if the arguments are
220 * out-of-bounds
221 * @param index the index
222 * @param length the upper-bound (exclusive) of the range
223 * @param oobef the exception formatter that when applied with this
224 * method name and out-of-bounds arguments returns a runtime
225 * exception. If {@code null} or returns {@code null} then, it is as
226 * if an exception formatter produced from an invocation of
227 * {@code outOfBoundsExceptionFormatter(IndexOutOfBounds::new)} is used
228 * instead (though it may be more efficient).
229 * Exceptions thrown by the formatter are relayed to the caller.
230 * @return {@code index} if it is within bounds of the range
231 * @throws X if the {@code index} is out-of-bounds and the exception
232 * formatter is non-{@code null}
233 * @throws IndexOutOfBoundsException if the {@code index} is out-of-bounds
234 * and the exception formatter is {@code null}
235 * @since 9
236 *
237 * @implNote
238 * This method is made intrinsic in optimizing compilers to guide them to
239 * perform unsigned comparisons of the index and length when it is known the
240 * length is a non-negative value (such as that of an array length or from
241 * the upper bound of a loop)
242 */
243 @HotSpotIntrinsicCandidate
244 public static <X extends RuntimeException>
245 int checkIndex(int index, int length,
246 BiFunction<String, List<Integer>, X> oobef) {
247 if (index < 0 || index >= length)
248 throw outOfBoundsCheckIndex(oobef, index, length);
249 return index;
250 }
251
252 /**
253 * Checks if the sub-range from {@code fromIndex} (inclusive) to
254 * {@code toIndex} (exclusive) is within the bounds of range from {@code 0}
255 * (inclusive) to {@code length} (exclusive).
256 *
257 * <p>The sub-range is defined to be out-of-bounds if any of the following
258 * inequalities is true:
259 * <ul>
260 * <li>{@code fromIndex < 0}</li>
261 * <li>{@code fromIndex > toIndex}</li>
262 * <li>{@code toIndex > length}</li>
263 * <li>{@code length < 0}, which is implied from the former inequalities</li>
264 * </ul>
265 *
266 * <p>If the sub-range is out-of-bounds, then a runtime exception is
267 * thrown that is the result of applying the following arguments to the
268 * exception formatter: the name of this method, {@code checkFromToIndex};
269 * and an unmodifiable list integers whose values are, in order, the
270 * out-of-bounds arguments {@code fromIndex}, {@code toIndex}, and {@code length}.
271 *
272 * @param <X> the type of runtime exception to throw if the arguments are
273 * out-of-bounds
274 * @param fromIndex the lower-bound (inclusive) of the sub-range
275 * @param toIndex the upper-bound (exclusive) of the sub-range
276 * @param length the upper-bound (exclusive) the range
277 * @param oobef the exception formatter that when applied with this
278 * method name and out-of-bounds arguments returns a runtime
279 * exception. If {@code null} or returns {@code null} then, it is as
280 * if an exception formatter produced from an invocation of
281 * {@code outOfBoundsExceptionFormatter(IndexOutOfBounds::new)} is used
282 * instead (though it may be more efficient).
283 * Exceptions thrown by the formatter are relayed to the caller.
284 * @return {@code fromIndex} if the sub-range within bounds of the range
285 * @throws X if the sub-range is out-of-bounds and the exception factory
286 * function is non-{@code null}
287 * @throws IndexOutOfBoundsException if the sub-range is out-of-bounds and
288 * the exception factory function is {@code null}
289 * @since 9
290 */
291 public static <X extends RuntimeException>
292 int checkFromToIndex(int fromIndex, int toIndex, int length,
293 BiFunction<String, List<Integer>, X> oobef) {
294 if (fromIndex < 0 || fromIndex > toIndex || toIndex > length)
295 throw outOfBoundsCheckFromToIndex(oobef, fromIndex, toIndex, length);
296 return fromIndex;
297 }
298
299 /**
300 * Checks if the sub-range from {@code fromIndex} (inclusive) to
301 * {@code fromIndex + size} (exclusive) is within the bounds of range from
302 * {@code 0} (inclusive) to {@code length} (exclusive).
303 *
304 * <p>The sub-range is defined to be out-of-bounds if any of the following
305 * inequalities is true:
306 * <ul>
307 * <li>{@code fromIndex < 0}</li>
308 * <li>{@code size < 0}</li>
309 * <li>{@code fromIndex + size > length}, taking into account integer overflow</li>
310 * <li>{@code length < 0}, which is implied from the former inequalities</li>
311 * </ul>
312 *
313 * <p>If the sub-range is out-of-bounds, then a runtime exception is
314 * thrown that is the result of applying the following arguments to the
315 * exception formatter: the name of this method, {@code checkFromIndexSize};
316 * and an unmodifiable list integers whose values are, in order, the
317 * out-of-bounds arguments {@code fromIndex}, {@code size}, and
318 * {@code length}.
319 *
320 * @param <X> the type of runtime exception to throw if the arguments are
321 * out-of-bounds
322 * @param fromIndex the lower-bound (inclusive) of the sub-interval
323 * @param size the size of the sub-range
324 * @param length the upper-bound (exclusive) of the range
325 * @param oobef the exception formatter that when applied with this
326 * method name and out-of-bounds arguments returns a runtime
327 * exception. If {@code null} or returns {@code null} then, it is as
328 * if an exception formatter produced from an invocation of
329 * {@code outOfBoundsExceptionFormatter(IndexOutOfBounds::new)} is used
330 * instead (though it may be more efficient).
331 * Exceptions thrown by the formatter are relayed to the caller.
332 * @return {@code fromIndex} if the sub-range within bounds of the range
333 * @throws X if the sub-range is out-of-bounds and the exception factory
334 * function is non-{@code null}
335 * @throws IndexOutOfBoundsException if the sub-range is out-of-bounds and
336 * the exception factory function is {@code null}
337 * @since 9
338 */
339 public static <X extends RuntimeException>
340 int checkFromIndexSize(int fromIndex, int size, int length,
341 BiFunction<String, List<Integer>, X> oobef) {
342 if ((length | fromIndex | size) < 0 || size > length - fromIndex)
343 throw outOfBoundsCheckFromIndexSize(oobef, fromIndex, size, length);
344 return fromIndex;
345 }
346 }
|
168 return String.format("Range check failed: %s", args);
169 } else if (args == null) {
170 return String.format("Range check failed: %s", checkKind);
171 }
172
173 int argSize = 0;
174 switch (checkKind) {
175 case "checkIndex":
176 argSize = 2;
177 break;
178 case "checkFromToIndex":
179 case "checkFromIndexSize":
180 argSize = 3;
181 break;
182 default:
183 }
184
185 // Switch to default if fewer or more arguments than required are supplied
186 switch ((args.size() != argSize) ? "" : checkKind) {
187 case "checkIndex":
188 return String.format("Index %d out of bounds for length %d",
189 args.get(0), args.get(1));
190 case "checkFromToIndex":
191 return String.format("Range [%d, %d) out of bounds for length %d",
192 args.get(0), args.get(1), args.get(2));
193 case "checkFromIndexSize":
194 return String.format("Range [%d, %<d + %d) out of bounds for length %d",
195 args.get(0), args.get(1), args.get(2));
196 default:
197 return String.format("Range check failed: %s %s", checkKind, args);
198 }
199 }
200
201 /**
202 * Checks if the {@code index} is within the bounds of the range from
203 * {@code 0} (inclusive) to {@code length} (exclusive).
204 *
205 * <p>The {@code index} is defined to be out of bounds if any of the
206 * following inequalities is true:
207 * <ul>
208 * <li>{@code index < 0}</li>
209 * <li>{@code index >= length}</li>
210 * <li>{@code length < 0}, which is implied from the former inequalities</li>
211 * </ul>
212 *
213 * <p>If the {@code index} is out of bounds, then a runtime exception is
214 * thrown that is the result of applying the following arguments to the
215 * exception formatter: the name of this method, {@code checkIndex};
216 * and an unmodifiable list integers whose values are, in order, the
217 * out-of-bounds arguments {@code index} and {@code length}.
218 *
219 * @param <X> the type of runtime exception to throw if the arguments are
220 * out of bounds
221 * @param index the index
222 * @param length the upper-bound (exclusive) of the range
223 * @param oobef the exception formatter that when applied with this
224 * method name and out-of-bounds arguments returns a runtime
225 * exception. If {@code null} or returns {@code null} then, it is as
226 * if an exception formatter produced from an invocation of
227 * {@code outOfBoundsExceptionFormatter(IndexOutOfBounds::new)} is used
228 * instead (though it may be more efficient).
229 * Exceptions thrown by the formatter are relayed to the caller.
230 * @return {@code index} if it is within bounds of the range
231 * @throws X if the {@code index} is out of bounds and the exception
232 * formatter is non-{@code null}
233 * @throws IndexOutOfBoundsException if the {@code index} is out of bounds
234 * and the exception formatter is {@code null}
235 * @since 9
236 *
237 * @implNote
238 * This method is made intrinsic in optimizing compilers to guide them to
239 * perform unsigned comparisons of the index and length when it is known the
240 * length is a non-negative value (such as that of an array length or from
241 * the upper bound of a loop)
242 */
243 @HotSpotIntrinsicCandidate
244 public static <X extends RuntimeException>
245 int checkIndex(int index, int length,
246 BiFunction<String, List<Integer>, X> oobef) {
247 if (index < 0 || index >= length)
248 throw outOfBoundsCheckIndex(oobef, index, length);
249 return index;
250 }
251
252 /**
253 * Checks if the sub-range from {@code fromIndex} (inclusive) to
254 * {@code toIndex} (exclusive) is within the bounds of range from {@code 0}
255 * (inclusive) to {@code length} (exclusive).
256 *
257 * <p>The sub-range is defined to be out of bounds if any of the following
258 * inequalities is true:
259 * <ul>
260 * <li>{@code fromIndex < 0}</li>
261 * <li>{@code fromIndex > toIndex}</li>
262 * <li>{@code toIndex > length}</li>
263 * <li>{@code length < 0}, which is implied from the former inequalities</li>
264 * </ul>
265 *
266 * <p>If the sub-range is out of bounds, then a runtime exception is
267 * thrown that is the result of applying the following arguments to the
268 * exception formatter: the name of this method, {@code checkFromToIndex};
269 * and an unmodifiable list integers whose values are, in order, the
270 * out-of-bounds arguments {@code fromIndex}, {@code toIndex}, and {@code length}.
271 *
272 * @param <X> the type of runtime exception to throw if the arguments are
273 * out of bounds
274 * @param fromIndex the lower-bound (inclusive) of the sub-range
275 * @param toIndex the upper-bound (exclusive) of the sub-range
276 * @param length the upper-bound (exclusive) the range
277 * @param oobef the exception formatter that when applied with this
278 * method name and out-of-bounds arguments returns a runtime
279 * exception. If {@code null} or returns {@code null} then, it is as
280 * if an exception formatter produced from an invocation of
281 * {@code outOfBoundsExceptionFormatter(IndexOutOfBounds::new)} is used
282 * instead (though it may be more efficient).
283 * Exceptions thrown by the formatter are relayed to the caller.
284 * @return {@code fromIndex} if the sub-range within bounds of the range
285 * @throws X if the sub-range is out of bounds and the exception factory
286 * function is non-{@code null}
287 * @throws IndexOutOfBoundsException if the sub-range is out of bounds and
288 * the exception factory function is {@code null}
289 * @since 9
290 */
291 public static <X extends RuntimeException>
292 int checkFromToIndex(int fromIndex, int toIndex, int length,
293 BiFunction<String, List<Integer>, X> oobef) {
294 if (fromIndex < 0 || fromIndex > toIndex || toIndex > length)
295 throw outOfBoundsCheckFromToIndex(oobef, fromIndex, toIndex, length);
296 return fromIndex;
297 }
298
299 /**
300 * Checks if the sub-range from {@code fromIndex} (inclusive) to
301 * {@code fromIndex + size} (exclusive) is within the bounds of range from
302 * {@code 0} (inclusive) to {@code length} (exclusive).
303 *
304 * <p>The sub-range is defined to be out of bounds if any of the following
305 * inequalities is true:
306 * <ul>
307 * <li>{@code fromIndex < 0}</li>
308 * <li>{@code size < 0}</li>
309 * <li>{@code fromIndex + size > length}, taking into account integer overflow</li>
310 * <li>{@code length < 0}, which is implied from the former inequalities</li>
311 * </ul>
312 *
313 * <p>If the sub-range is out of bounds, then a runtime exception is
314 * thrown that is the result of applying the following arguments to the
315 * exception formatter: the name of this method, {@code checkFromIndexSize};
316 * and an unmodifiable list integers whose values are, in order, the
317 * out-of-bounds arguments {@code fromIndex}, {@code size}, and
318 * {@code length}.
319 *
320 * @param <X> the type of runtime exception to throw if the arguments are
321 * out of bounds
322 * @param fromIndex the lower-bound (inclusive) of the sub-interval
323 * @param size the size of the sub-range
324 * @param length the upper-bound (exclusive) of the range
325 * @param oobef the exception formatter that when applied with this
326 * method name and out-of-bounds arguments returns a runtime
327 * exception. If {@code null} or returns {@code null} then, it is as
328 * if an exception formatter produced from an invocation of
329 * {@code outOfBoundsExceptionFormatter(IndexOutOfBounds::new)} is used
330 * instead (though it may be more efficient).
331 * Exceptions thrown by the formatter are relayed to the caller.
332 * @return {@code fromIndex} if the sub-range within bounds of the range
333 * @throws X if the sub-range is out of bounds and the exception factory
334 * function is non-{@code null}
335 * @throws IndexOutOfBoundsException if the sub-range is out of bounds and
336 * the exception factory function is {@code null}
337 * @since 9
338 */
339 public static <X extends RuntimeException>
340 int checkFromIndexSize(int fromIndex, int size, int length,
341 BiFunction<String, List<Integer>, X> oobef) {
342 if ((length | fromIndex | size) < 0 || size > length - fromIndex)
343 throw outOfBoundsCheckFromIndexSize(oobef, fromIndex, size, length);
344 return fromIndex;
345 }
346 }
|