[Bug java/21855] array bounds checking elimination

2015-10-20 Thread aph at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=21855

Andrew Haley  changed:

   What|Removed |Added

 Status|NEW |RESOLVED
 Resolution|--- |WONTFIX

--- Comment #25 from Andrew Haley  ---
We'll never do this.


[Bug java/21855] array bounds checking elimination

2012-01-10 Thread rguenth at gcc dot gnu.org
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=21855

Richard Guenther rguenth at gcc dot gnu.org changed:

   What|Removed |Added

 Status|WAITING |NEW
  Component|tree-optimization   |java

--- Comment #15 from Richard Guenther rguenth at gcc dot gnu.org 2012-01-10 
16:20:13 UTC ---
(In reply to comment #14)
 (In reply to comment #13)
  We can't optimize this because System.out.println can change args[].
 
 That's the whole point: System.out.println cannot change args[], which is a
 java array, and the length of a Java array is constant.  It is not an invalid
 test case.

I suppose

  public static void main(String[] args)

is passing args by value (but the implementation detail uses reference
passing for efficiency?).  In this case the Java frontend should do
like the C++ frontend and tell this to the middle-end by properly
marking args as 1) DECL_BY_REFERENCE, 2) use a TYPE_RESTRICT qualified
pointer for the reference.  Then we would optimize this case.

Java frontend issue.


[Bug java/21855] array bounds checking elimination

2012-01-10 Thread aph at gcc dot gnu.org
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=21855

--- Comment #16 from Andrew Haley aph at gcc dot gnu.org 2012-01-10 16:26:51 
UTC ---
(In reply to comment #15)
 (In reply to comment #14)
  (In reply to comment #13)
   We can't optimize this because System.out.println can change args[].
  
  That's the whole point: System.out.println cannot change args[], which is a
  java array, and the length of a Java array is constant.  It is not an 
  invalid
  test case.
 
 I suppose
 
   public static void main(String[] args)
 
 is passing args by value (but the implementation detail uses reference
 passing for efficiency?).

args is indeed a reference to a Java array.  The length field of a Java
array is immutable.  The elements of an array are not immutable.

 In this case the Java frontend should do
 like the C++ frontend and tell this to the middle-end by properly
 marking args as 1) DECL_BY_REFERENCE, 2) use a TYPE_RESTRICT qualified
 pointer for the reference.  Then we would optimize this case.

If we could mark the length field as immutable that would fix it.  Is there any
way to do that?


[Bug java/21855] array bounds checking elimination

2012-01-10 Thread rguenth at gcc dot gnu.org
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=21855

--- Comment #17 from Richard Guenther rguenth at gcc dot gnu.org 2012-01-10 
16:30:30 UTC ---
(In reply to comment #16)
 (In reply to comment #15)
  (In reply to comment #14)
   (In reply to comment #13)
We can't optimize this because System.out.println can change args[].
   
   That's the whole point: System.out.println cannot change args[], which is 
   a
   java array, and the length of a Java array is constant.  It is not an 
   invalid
   test case.
  
  I suppose
  
public static void main(String[] args)
  
  is passing args by value (but the implementation detail uses reference
  passing for efficiency?).
 
 args is indeed a reference to a Java array.  The length field of a Java
 array is immutable.  The elements of an array are not immutable.

You mean that System.out.println could change the elements of the array
(well, it doesn't, but theoretically it could)?

  In this case the Java frontend should do
  like the C++ frontend and tell this to the middle-end by properly
  marking args as 1) DECL_BY_REFERENCE, 2) use a TYPE_RESTRICT qualified
  pointer for the reference.  Then we would optimize this case.
 
 If we could mark the length field as immutable that would fix it.  Is there 
 any
 way to do that?

No.  What you can do is, via the method I outlined, tell GCC that
args is to be treated similar to a local automatic variable - thus
it cannot be refered to from other functions (unless you pass them
its address of course).


[Bug java/21855] array bounds checking elimination

2012-01-10 Thread rguenth at gcc dot gnu.org
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=21855

--- Comment #18 from Richard Guenther rguenth at gcc dot gnu.org 2012-01-10 
16:35:46 UTC ---
(In reply to comment #17)
 (In reply to comment #16)
  (In reply to comment #15)
   (In reply to comment #14)
(In reply to comment #13)
 We can't optimize this because System.out.println can change args[].

That's the whole point: System.out.println cannot change args[], which 
is a
java array, and the length of a Java array is constant.  It is not an 
invalid
test case.
   
   I suppose
   
 public static void main(String[] args)
   
   is passing args by value (but the implementation detail uses reference
   passing for efficiency?).
  
  args is indeed a reference to a Java array.  The length field of a Java
  array is immutable.  The elements of an array are not immutable.
 
 You mean that System.out.println could change the elements of the array
 (well, it doesn't, but theoretically it could)?
 
   In this case the Java frontend should do
   like the C++ frontend and tell this to the middle-end by properly
   marking args as 1) DECL_BY_REFERENCE, 2) use a TYPE_RESTRICT qualified
   pointer for the reference.  Then we would optimize this case.
  
  If we could mark the length field as immutable that would fix it.  Is there 
  any
  way to do that?
 
 No.  What you can do is, via the method I outlined, tell GCC that
 args is to be treated similar to a local automatic variable - thus
 it cannot be refered to from other functions (unless you pass them
 its address of course).

Thus, similar to the C++ case with

struct Array { int length; void data[]; }

void foo (Array args)
{
 ...
}

foo cannot change the callers args.length (only its own copy) but it
can change the callers args.data[] contents.  If the C++ frontend
decides to pass args by reference then it sets DECL_BY_REFERENCE
and uses a TYPE_RESTRICT qualified pointer.  This way the optimization
will be the same as if it was passed really by value.

Not sure if the Java situation is similar enough.


[Bug java/21855] array bounds checking elimination

2012-01-10 Thread aph at gcc dot gnu.org
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=21855

--- Comment #19 from Andrew Haley aph at gcc dot gnu.org 2012-01-10 16:44:16 
UTC ---
(In reply to comment #17)
 (In reply to comment #16)
  (In reply to comment #15)
   (In reply to comment #14)
(In reply to comment #13)
 We can't optimize this because System.out.println can change args[].

That's the whole point: System.out.println cannot change args[], which 
is a
java array, and the length of a Java array is constant.  It is not an 
invalid
test case.
   
   I suppose
   
 public static void main(String[] args)
   
   is passing args by value (but the implementation detail uses reference
   passing for efficiency?).
  
  args is indeed a reference to a Java array.  The length field of a Java
  array is immutable.  The elements of an array are not immutable.
 
 You mean that System.out.println could change the elements of the array
 (well, it doesn't, but theoretically it could)?

In theory yes, it could.

   In this case the Java frontend should do
   like the C++ frontend and tell this to the middle-end by properly
   marking args as 1) DECL_BY_REFERENCE, 2) use a TYPE_RESTRICT qualified
   pointer for the reference.  Then we would optimize this case.
  
  If we could mark the length field as immutable that would fix it.  Is there 
  any
  way to do that?
 
 No.  What you can do is, via the method I outlined, tell GCC that
 args is to be treated similar to a local automatic variable - thus
 it cannot be refered to from other functions (unless you pass them
 its address of course).

But that doesn't help.  args *can* potentially be referred to by other
functions.  The special property we need to make use of its that fact that once
an array is created, its length can never change.


[Bug java/21855] array bounds checking elimination

2012-01-10 Thread rguenth at gcc dot gnu.org
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=21855

--- Comment #21 from Richard Guenther rguenth at gcc dot gnu.org 2012-01-10 
16:57:36 UTC ---
The Java frontend could handle this by performing loads of the length field
via a SAVE_EXPR and sharing this across a function.  That way CSE would
happen automagically.


[Bug java/21855] array bounds checking elimination

2012-01-10 Thread rguenth at gcc dot gnu.org
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=21855

--- Comment #20 from Richard Guenther rguenth at gcc dot gnu.org 2012-01-10 
16:55:52 UTC ---
(In reply to comment #19)

  No.  What you can do is, via the method I outlined, tell GCC that
  args is to be treated similar to a local automatic variable - thus
  it cannot be refered to from other functions (unless you pass them
  its address of course).
 
 But that doesn't help.  args *can* potentially be referred to by other
 functions.  The special property we need to make use of its that fact that 
 once
 an array is created, its length can never change.

That is something we cannot express at the moment, and I think it would
be hard to implement reliably (thinking of the RTX_UNCHANGING saga - we
do have to exclude the stmts that initialize the length field).


[Bug java/21855] array bounds checking elimination

2012-01-10 Thread aph at gcc dot gnu.org
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=21855

--- Comment #22 from Andrew Haley aph at gcc dot gnu.org 2012-01-10 17:08:30 
UTC ---
(In reply to comment #21)
 The Java frontend could handle this by performing loads of the length field
 via a SAVE_EXPR and sharing this across a function.  That way CSE would
 happen automagically.

Now that's a nice idea.  

In this specific case it should be easy, because array.length is used in the
control expression for the loop.  So. we can create the SAVE_EXPR when the loop
is initialized.

The problem with doing this in general is that we don't have a CFG, so we don't
always know when to create that SAVE_EXPR.  If we can find an initial use of an
array that dominates all other uses we can create the SAVE_EXPR at that point.


[Bug java/21855] array bounds checking elimination

2012-01-10 Thread tromey at gcc dot gnu.org
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=21855

--- Comment #23 from Tom Tromey tromey at gcc dot gnu.org 2012-01-10 17:17:50 
UTC ---
I thought I wrote a pass to do this optimization, but I can't find it now.
Anyway I think that would be the simplest approach by far.


[Bug java/21855] array bounds checking elimination

2012-01-10 Thread tromey at gcc dot gnu.org
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=21855

--- Comment #24 from Tom Tromey tromey at gcc dot gnu.org 2012-01-10 17:21:02 
UTC ---
I found my code and it turns out I never finished it.
(I did write a java-specific devirtualization pass.)
Here is an introductory comment that explains my plans:

/* This pass implements a few simple gcj-specific optimizations
   related to handling of invariants.  In Java, certain fields of
   some objects are known to be invariant after the object has been
   created.  For instance, the vtable pointer of an object cannot
   change; neither can the length of an array.

   Also, this pass knows that 'new Type[n]' sets the length of an
   array to 'n'.

   Ideally GCC would recognize these cases and optimize for us.
   However, currently there is no way to express these properties to
   the optimizers.
 */