Fixes for reloading
authorJan Vrany <jan.vrany@fit.cvut.cz>
Sat, 16 Aug 2014 08:13:09 +0100
changeset 3235 6a5d85f29c3a
parent 3234 5c9cb5b7a35b
child 3236 c8b42e8c2d6c
Fixes for reloading - when class is reloaded, all cached values in corresponding java.lang.Class object have to be invalidated. Otherwise recompilation won't help as reflective environment will still see old (invalid or incomplete) values. - correctly handle multiple version in GETFIELD/PUTFIELD
JavaClassMemberRef2.st
JavaClassRegistry.st
JavaExceptionTests.st
JavaFieldRef2.st
JavaMethodRef2.st
JavaVM.st
--- a/JavaClassMemberRef2.st	Thu Aug 14 16:00:39 2014 +0100
+++ b/JavaClassMemberRef2.st	Sat Aug 16 08:13:09 2014 +0100
@@ -133,6 +133,10 @@
     "Modified: / 12-05-2011 / 18:39:27 / Marcel Hlopko <hlopkmar@fel.cvut.cz>"
 !
 
+resolvedClass
+    ^ resolvedClass
+!
+
 selector
     ^ self nameAndType selector.
 
--- a/JavaClassRegistry.st	Thu Aug 14 16:00:39 2014 +0100
+++ b/JavaClassRegistry.st	Sat Aug 16 08:13:09 2014 +0100
@@ -331,6 +331,8 @@
                     "Class already exists, reload & reinstall"
 
                     | reloadedClass |
+
+                    self registerClassRedefined: oldClass.  
                     reloadedClass := JavaClassReloader reload: oldClass with: newClass.
                     "/OK, full reload, not just method dictionary update"
                     reloadedClass ~~ oldClass ifTrue:[
@@ -377,7 +379,7 @@
 
     "Created: / 23-10-2011 / 11:53:58 / Jan Vrany <jan.vrany@fit.cvut.cz>"
     "Modified: / 02-11-2011 / 18:40:52 / Marcel Hlopko <hlopkmar@fel.cvut.cz>"
-    "Modified: / 11-08-2014 / 01:41:33 / Jan Vrany <jan.vrany@fit.cvut.cz>"
+    "Modified: / 15-08-2014 / 15:19:36 / Jan Vrany <jan.vrany@fit.cvut.cz>"
 !
 
 registerClasses: classes
@@ -545,6 +547,23 @@
     "Modified: / 08-10-2013 / 19:27:42 / Jan Vrany <jan.vrany@fit.cvut.cz>"
 !
 
+registerClassRedefined: class
+    "Class has been redefined, so we have to invalidate
+     caches in coresponding java.lang.Class. Luckily enough,
+     thee seem to be support for this - all we have to is to
+     increase class redefinition count."
+
+    | classObject classObjectRedefinitionCountIndex classObjectRedefinitionCount |
+
+    classObject := JavaVM reflection javaClassObjectForClass: class.
+    classObjectRedefinitionCountIndex := classObject class instVarIndexFor: #classRedefinedCount.
+    classObjectRedefinitionCount := classObject instVarAt:classObjectRedefinitionCountIndex.
+    classObjectRedefinitionCount := classObjectRedefinitionCount + 1.
+    classObject instVarAt:classObjectRedefinitionCountIndex put: classObjectRedefinitionCount.
+
+    "Created: / 15-08-2014 / 15:09:41 / Jan Vrany <jan.vrany@fit.cvut.cz>"
+!
+
 unregisterClassInClassLoader: class
     "Unregisters class from it's classloader"
 
--- a/JavaExceptionTests.st	Thu Aug 14 16:00:39 2014 +0100
+++ b/JavaExceptionTests.st	Sat Aug 16 08:13:09 2014 +0100
@@ -65,7 +65,6 @@
     "Created: / 30-03-2012 / 13:38:08 / Jan Vrany <jan.vrany@fit.cvut.cz>"
 ! !
 
-
 !JavaExceptionTests methodsFor:'callbacks'!
 
 call: trhower with: aBoolean 
--- a/JavaFieldRef2.st	Thu Aug 14 16:00:39 2014 +0100
+++ b/JavaFieldRef2.st	Sat Aug 16 08:13:09 2014 +0100
@@ -102,6 +102,19 @@
     "Modified: / 05-10-2013 / 23:57:03 / Jan Vrany <jan.vrany@fit.cvut.cz>"
 ! !
 
+!JavaFieldRef2 methodsFor:'printing & storing'!
+
+printOn:aStream
+    super printOn: aStream. 
+    aStream nextPut: $(.
+    self classRef javaClassName printOn: aStream.
+    aStream nextPut:$#.
+    aStream nextPutAll: self nameAndType name.  
+    aStream nextPut: $).
+
+    "Modified: / 15-08-2014 / 15:30:02 / Jan Vrany <jan.vrany@fit.cvut.cz>"
+! !
+
 !JavaFieldRef2 methodsFor:'private - resolving'!
 
 findInstOffset
--- a/JavaMethodRef2.st	Thu Aug 14 16:00:39 2014 +0100
+++ b/JavaMethodRef2.st	Sat Aug 16 08:13:09 2014 +0100
@@ -78,6 +78,16 @@
 "
 ! !
 
+!JavaMethodRef2 methodsFor:'printing'!
+
+displayString
+    "superclass JavaRef2 says that I am responsible to implement this method"
+
+    ^ self classRef displayString , '.' , self name , self descriptor
+
+    "Created: / 15-08-2014 / 13:43:55 / Jan Vrany <jan.vrany@fit.cvut.cz>"
+! !
+
 !JavaMethodRef2 methodsFor:'printing & storing'!
 
 printOn:aStream
--- a/JavaVM.st	Thu Aug 14 16:00:39 2014 +0100
+++ b/JavaVM.st	Sat Aug 16 08:13:09 2014 +0100
@@ -5253,14 +5253,25 @@
 _GETFIELD_R: fieldRef _: obj
     "Called by jitted code for GETFIELD insn iff fieldref is not yet resolved"
 
+    | class offset |
+
     obj isNil ifTrue:[
         ^self throwNullPointerException.
     ].
-    fieldRef resolve.
-    ^ obj instVarAt: fieldRef resolvedOffset.
+    class := fieldRef classRef resolve; javaClass.
+    class hasMultipleVersions ifTrue:[
+        fieldRef classRef resolveForVersionOf: obj or: nil.
+        fieldRef resolve.
+        offset := fieldRef resolvedOffset.
+        fieldRef invalidate.
+    ] ifFalse:[
+        fieldRef resolve.
+        offset := fieldRef resolvedOffset.
+    ].
+    ^ obj instVarAt: offset.
 
     "Created: / 20-01-2014 / 14:56:11 / Jan Vrany <jan.vrany@fit.cvut.cz>"
-    "Modified: / 31-01-2014 / 09:15:52 / Jan Vrany <jan.vrany@fit.cvut.cz>"
+    "Modified: / 16-08-2014 / 07:55:48 / Jan Vrany <jan.vrany@fit.cvut.cz>"
 !
 
 _GETSTATIC_R: fieldRef
@@ -6955,15 +6966,28 @@
 _PUTFIELD_R: fieldRef _: obj _: value
     "Called by jitted code for PUTFIELD insn iff fieldref is not yet resolved"
 
+    | class offset |
+
+    obj isNil ifTrue:[
+        ^self throwNullPointerException.
+    ].
     obj isNil ifTrue:[
         ^self throwNullPointerException.
     ].
-
-    fieldRef resolve.
-    ^ obj instVarAt: fieldRef resolvedOffset put: value
+    class := fieldRef classRef resolve; javaClass.
+    class hasMultipleVersions ifTrue:[
+        fieldRef classRef resolveForVersionOf: obj or: nil.
+        fieldRef resolve.
+        offset := fieldRef resolvedOffset.
+        fieldRef invalidate.
+    ] ifFalse:[
+        fieldRef resolve.
+        offset := fieldRef resolvedOffset.
+    ].   
+    obj instVarAt: offset put: value
 
     "Created: / 20-01-2014 / 15:01:24 / Jan Vrany <jan.vrany@fit.cvut.cz>"
-    "Modified: / 31-01-2014 / 09:15:58 / Jan Vrany <jan.vrany@fit.cvut.cz>"
+    "Modified: / 16-08-2014 / 07:57:40 / Jan Vrany <jan.vrany@fit.cvut.cz>"
 !
 
 _PUTSTATIC_R: fieldRef _: value