java/1345: A boolean expression containing two qualified expressions makes jc1 die.
apbianco@cygnus.com
apbianco@cygnus.com
Wed Dec 20 12:25:00 GMT 2000
>Number: 1345
>Category: java
>Synopsis: A boolean expression containing two qualified expressions makes jc1 die.
>Confidential: no
>Severity: serious
>Priority: medium
>Responsible: apbianco
>State: closed
>Class: sw-bug
>Submitter-Id: net
>Arrival-Date: Wed Dec 20 12:19:15 PST 2000
>Closed-Date: Thu Aug 26 09:56:38 PDT 1999
>Last-Modified: Thu Aug 26 09:56:38 PDT 1999
>Originator: Mark K. Gardner (mkgardne@cs.uiuc.edu)
>Release: Current
>Organization:
>Environment:
Originally unknown. Reproduced on Debian2.0/x86
>Description:
jc1 dies processing the following expression:
stacks[to].non_empty()
&& ((disk)stacks[to].top()).id < d.id
which happens to be a `if' statement boolean expression.
>How-To-Repeat:
Run `jc1' on the following source code:
/* Copyright 1993-1999, by the Cecil Project
* Department of Computer Science and Engineering, University of Washington
* See the $VORTEX_HOME/notes/LICENSE file for license information.
*/
package towers;
class disk {
int id;
disk(int i) { id = i;}
}
class simple_list {
Object value;
simple_list next;
simple_list(Object v, simple_list n) {
value = v;
next = n;
}
simple_list() {
value = null;
next = null;
}
}
class list extends simple_list {
simple_list head;
list() { head = null; }
void add_first(Object v) { head = new simple_list(v, head); }
Object remove_first() {
Object v = head.value;
head = head.next;
return v;
}
Object first() { return head.value; }
boolean is_empty() { return head == null; }
boolean non_empty() { return !is_empty(); }
}
class stack extends list {
void push(Object v) { add_first(v); }
Object pop() { return remove_first(); }
Object top() { return first(); }
}
class towers {
stack stacks[] = new stack[3];
int moves_done;
towers(int size) {
stack s = new stack();
for (int i = 0; i < size; i++) {
s.push(new disk(size - i));
}
stacks[0] = s;
stacks[1] = new stack();
stacks[2] = new stack();
moves_done = 0;
}
void move_stack(int from, int to, int count) {
if (count == 0) return;
int other = 3 - from - to;
move_stack(from, other, count - 1);
move_disk(from, to);
move_stack(other, to, count - 1);
}
void move_disk(int from, int to) {
disk d = (disk)stacks[from].pop();
/* BUGGY */
if (stacks[to].non_empty() &&
((disk)stacks[to].top()).id < d.id) {
/* OK
if (false) {
*/
System.out.println("pushing a disk onto a smaller disk");
System.exit(-1);
}
stacks[to].push(d);
moves_done++;
}
public static void main(String argv[]) {
int i;
towers t = null;
int size = 15;
long time, time2;
int iters = 10;
System.out.print("** Starting towers with " + size + " disks...");
System.out.flush();
time = System.currentTimeMillis();
for (i = 0; i < iters; i++) {
t = new towers(size);
t.move_stack(0, 1, size);
}
time2 = System.currentTimeMillis();
System.out.println("done. " + t.moves_done + " moves; time: "
+
((time2 - time)/iters) + " ms.");
}
}
>Fix:
Hmm, the patch I provided you with yesterday isn't quite
right. Can you please try this one instead?
Index: parse.y
===================================================================
RCS file: /cvs/cvsfiles/devo/gcc/java/parse.y,v
retrieving revision 1.110
diff -u -p -r1.110 parse.y
--- parse.y 1999/08/22 18:36:05 1.110
+++ parse.y 1999/08/24 07:30:01
@@ -7843,8 +7852,15 @@ qualify_ambiguous_name (id)
again = 1;
}
else
- name = EXPR_WFL_NODE (qual_wfl);
-
+ {
+ name = EXPR_WFL_NODE (qual_wfl);
+ if (!name)
+ {
+ qual = EXPR_WFL_QUALIFICATION (qual_wfl);
+ again = 1;
+ }
+ }
+
/* If we have a THIS (from a primary), we set the context accordingly */
if (name == this_identifier_node)
{
>Release-Note:
>Audit-Trail:
Formerly PR gcj/32
State-Changed-From-To: open->feedback
State-Changed-By: apbianco
State-Changed-When: Mon Aug 23 19:48:37 1999
State-Changed-Why:
Can you try the following patch?
Index: parse.y
===================================================================
RCS file: /cvs/egcs/egcs/gcc/java/parse.y,v
retrieving revision 1.104
diff -u -p -r1.104 parse.y
--- parse.y 1999/08/22 18:38:07 1.104
+++ parse.y 1999/08/24 02:43:35
@@ -7854,9 +7863,14 @@ qualify_ambiguous_name (id)
qual = TREE_CHAIN (qual);
qual_wfl = QUAL_WFL (qual);
again = 1;
+ }
+
+ name = EXPR_WFL_NODE (qual_wfl);
+ if (!name)
+ {
+ qual = EXPR_WFL_QUALIFICATION (qual_wfl);
+ again = 1;
}
- else
- name = EXPR_WFL_NODE (qual_wfl);
/* If we have a THIS (from a primary), we set the context accordingly */
if (name == this_identifier_node)
State-Changed-From-To: feedback->closed
State-Changed-By: apbianco
State-Changed-When: Thu Aug 26 09:56:38 1999
State-Changed-Why:
A patch has been checked in. See http://egcs.cygnus.com/ml/gcc-patches/1999-08/msg00782.html
>Unformatted:
More information about the Gcc-prs
mailing list