Hi,

I need to replace the following call in legacy bytecode:

dataInputStream.read(buf, 0, len);

by

dataInputStream.readFully(buf, 0, len);

The original read() has the obvious flaw that it does not check for the return 
value of dataInputStream.read, which leads to problems if the implementation 
chooses to fill the buffer only partially. I want to solve this bug using 
Javassist.

I do the following:

        ExprEditor exprEditor = new ExprEditor() {

            @Override
            public void edit(MethodCall methodCall) 
                    throws CannotCompileException {
                String methodName = methodCall.getMethodName();
                if (methodName.equals("read")) {
                    methodCall.replace("$_ = $0.readFully($$);");
                    didChangesToClassfile = true;
                }
            }
        };

But the created class is broken, it is rejected by the classloader and jode 
says "Pop from empty stack".

Obviously I want to replace a method call with a return value which is being 
ignored by a void method call. I guess this is what causes the problem, but 
maybe I am wrong.

The offending bytecode is below, look around readFully in line 114:

public void (String arg1)
Code(max_stack = 4, max_locals = 9, code_length = 139)
0:    aload_0
1:    invokespecial     java.lang.Object. ()V (23)
4:    new               <java.io.DataInputStream> (2)
7:    dup
8:    aload_0
9:    invokevirtual     java.lang.Object.getClass ()Ljava/lang/Class; (24)
12:   aload_1
13:   invokevirtual     java.lang.Class.getResourceAsStream 
(Ljava/lang/String;)Ljava/io/InputStream; (22)
16:   invokespecial     java.io.DataInputStream. (Ljava/io/InputStream;)V (16)
19:   dup
20:   astore_1
21:   invokevirtual     java.io.DataInputStream.readUnsignedByte ()I (21)
24:   i2c
25:   bipush            70
27:   if_icmpeq         #31
30:   return
31:   aload_1
32:   invokevirtual     java.io.DataInputStream.readUnsignedByte ()I (21)
35:   i2c
36:   bipush            49
38:   if_icmpeq         #42
41:   return
42:   aload_0
43:   aload_1
44:   invokevirtual     java.io.DataInputStream.readByte ()B (19)
47:   putfield          ak.h I (15)
50:   aload_0
51:   aload_1
52:   invokevirtual     java.io.DataInputStream.readByte ()B (19)
55:   putfield          ak.d I (11)
58:   aload_0
59:   aload_1
60:   invokevirtual     java.io.DataInputStream.readByte ()B (19)
63:   putfield          ak.e I (12)
66:   aload_0
67:   aload_1
68:   invokevirtual     java.io.DataInputStream.readByte ()B (19)
71:   putfield          ak.f I (13)
74:   aload_0
75:   aload_1
76:   invokevirtual     java.io.DataInputStream.readByte ()B (19)
79:   putfield          ak.g I (14)
82:   aload_1
83:   invokevirtual     java.io.DataInputStream.readShort ()S (20)
86:   dup
87:   istore_2
88:   newarray          
90:   astore_3
91:   aload_1
92:   aload_3
93:   iconst_0
94:   iload_2
95:   istore            %7
97:   istore            %6
99:   astore            %5
101:  astore            %4
103:  iconst_0
104:  istore            %8
106:  aload             %4
108:  aload             %5
110:  iload             %6
112:  iload             %7
114:  invokevirtual     java.io.DataInputStream.readFully ([BII)V (116)
117:  istore            %8
119:  iload             %8
121:  pop
122:  aload_0
123:  aload_3
124:  iconst_0
125:  iload_2
126:  invokestatic      javax.microedition.lcdui.Image.createImage 
([BII)Ljavax/microedition/lcdui/Image; (34)
129:  putfield          ak.G Ljavax/microedition/lcdui/Image; (10)
132:  aload_1
133:  invokevirtual     java.io.DataInputStream.close ()V (17)
136:  return
137:  pop
138:  return

The original bytecode looks like this:

public void (String arg1)
Code(max_stack = 4, max_locals = 4, code_length = 116)
0:    aload_0
1:    invokespecial     java.lang.Object. ()V (23)
4:    new               <java.io.DataInputStream> (2)
7:    dup
8:    aload_0
9:    invokevirtual     java.lang.Object.getClass ()Ljava/lang/Class; (24)
12:   aload_1
13:   invokevirtual     java.lang.Class.getResourceAsStream 
(Ljava/lang/String;)Ljava/io/InputStream; (22)
16:   invokespecial     java.io.DataInputStream. (Ljava/io/InputStream;)V (16)
19:   dup
20:   astore_1
21:   invokevirtual     java.io.DataInputStream.readUnsignedByte ()I (21)
24:   i2c
25:   bipush            70
27:   if_icmpeq         #31
30:   return
31:   aload_1
32:   invokevirtual     java.io.DataInputStream.readUnsignedByte ()I (21)
35:   i2c
36:   bipush            49
38:   if_icmpeq         #42
41:   return
42:   aload_0
43:   aload_1
44:   invokevirtual     java.io.DataInputStream.readByte ()B (19)
47:   putfield          ak.h I (15)
50:   aload_0
51:   aload_1
52:   invokevirtual     java.io.DataInputStream.readByte ()B (19)
55:   putfield          ak.d I (11)
58:   aload_0
59:   aload_1
60:   invokevirtual     java.io.DataInputStream.readByte ()B (19)
63:   putfield          ak.e I (12)
66:   aload_0
67:   aload_1
68:   invokevirtual     java.io.DataInputStream.readByte ()B (19)
71:   putfield          ak.f I (13)
74:   aload_0
75:   aload_1
76:   invokevirtual     java.io.DataInputStream.readByte ()B (19)
79:   putfield          ak.g I (14)
82:   aload_1
83:   invokevirtual     java.io.DataInputStream.readShort ()S (20)
86:   dup
87:   istore_2
88:   newarray          
90:   astore_3
91:   aload_1
92:   aload_3
93:   iconst_0
94:   iload_2
95:   invokevirtual     java.io.DataInputStream.read ([BII)I (18)
98:   pop
99:   aload_0
100:  aload_3
101:  iconst_0
102:  iload_2
103:  invokestatic      javax.microedition.lcdui.Image.createImage 
([BII)Ljavax/microedition/lcdui/Image; (34)
106:  putfield          ak.G Ljavax/microedition/lcdui/Image; (10)
109:  aload_1
110:  invokevirtual     java.io.DataInputStream.close ()V (17)
113:  return
114:  pop
115:  return

View the original post : 
http://www.jboss.org/index.html?module=bb&op=viewtopic&p=4250792#4250792

Reply to the post : 
http://www.jboss.org/index.html?module=bb&op=posting&mode=reply&p=4250792
_______________________________________________
jboss-user mailing list
[email protected]
https://lists.jboss.org/mailman/listinfo/jboss-user

Reply via email to