oops, forgot to include patches.

Salikh Zakirov wrote:
> Hi,
> 
> I have been looking to the string interning code in DRLVM recently.
> The reason I have started to do this is that the following stress
> test quickly causes OOM  (OutOfMemoryError) on DRLVM:
> ...
>From 27be6c528c73493d4a32e3d9fc0b8acf13e91c9c Mon Sep 17 00:00:00 2001
From: Salikh Zakirov <[EMAIL PROTECTED]>
Date: Tue, 18 Jul 2006 12:58:07 +0400
Subject: [PATCH] Pure java string intern()

Implemented straightforwardly by using WeakHashMap and
storing additional weak reference as the value.
Subsequently, *two* weak references are created for each
interned string.

LDC bytecode implementation now calls into java method
VM.intern() when it resolves string literals.
To avoid infinite recursion, no string literals
are allowed in VM.intern() implementation or any
functions called from there.

The method descriptor of VM.intern() method is preloaded
at the VM initialization stage.

Added stress test for interned strings, stress.Intern
It used to cause OOM before this change, and now
should pass okay.

Removed dead string_intern() code
---
 vm/tests/smoke/stress/Intern.java                  |   37 +++++++++++++
 vm/vmcore/include/environment.h                    |    5 ++
 vm/vmcore/include/vm_strings.h                     |    6 --
 vm/vmcore/src/init/vm_init.cpp                     |    4 +
 .../javasrc/org/apache/harmony/kernel/vm/VM.java   |   39 +++++++++++++---
 .../native/org_apache_harmony_kernel_vm_VM.cpp     |   13 -----
 vm/vmcore/src/util/vm_strings.cpp                  |   57 +++++++++-----------
 7 files changed, 106 insertions(+), 55 deletions(-)

diff --git a/vm/tests/smoke/stress/Intern.java 
b/vm/tests/smoke/stress/Intern.java
new file mode 100644
index 0000000..84c4667
--- /dev/null
+++ b/vm/tests/smoke/stress/Intern.java
@@ -0,0 +1,37 @@
+/*
+ *  Copyright 2005-2006 The Apache Software Foundation or its licensors, as 
applicable.
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package stress;
+
+/**
+ * Tests the correctness of string interning.
+ *
+ * @keyword XXX_stress
+ */
+public class Intern {
+    public static void main(String[] args) {
+        String s = "abc";
+        for (int i = 0; i < 100000; i++) {
+            s = (s + i + s).intern();
+            if (s.length() > 65536) s = "abc" + i;
+            if (i % 1000 == 0) trace(".");
+        }
+    }
+
+    public static void trace(Object o) {
+        System.out.print(o);
+        System.out.flush();
+    }
+}
diff --git a/vm/vmcore/include/environment.h b/vm/vmcore/include/environment.h
old mode 100644
new mode 100755
index 5ae7b0d..06b8d6d
--- a/vm/vmcore/include/environment.h
+++ b/vm/vmcore/include/environment.h
@@ -93,6 +93,11 @@ struct Global_Env {
     String* InitCauseDescriptor_String;
 
     //
+    // preloaded methods
+    //
+    Method* VM_intern;
+
+    //
     // preloaded classes
     //
     Class* Boolean_Class;
diff --git a/vm/vmcore/include/vm_strings.h b/vm/vmcore/include/vm_strings.h
old mode 100644
new mode 100755
index 55eb6a1..759ee50
--- a/vm/vmcore/include/vm_strings.h
+++ b/vm/vmcore/include/vm_strings.h
@@ -36,12 +36,6 @@ #ifdef __cplusplus
 extern "C" {
 #endif
 
-/**
- * Interns a string.
- */
-VMEXPORT jstring
-string_intern(JNIEnv*, jobject string);
-
 #ifdef __cplusplus
 }
 #endif
diff --git a/vm/vmcore/src/init/vm_init.cpp b/vm/vmcore/src/init/vm_init.cpp
old mode 100644
new mode 100755
index c21befd..8d0b40c
--- a/vm/vmcore/src/init/vm_init.cpp
+++ b/vm/vmcore/src/init/vm_init.cpp
@@ -267,6 +267,10 @@ #endif // POINTER64
     env->JavaLangString_VTable = env->JavaLangString_Class->vtable;
     env->JavaLangString_allocation_handle = 
env->JavaLangString_Class->allocation_handle;
 
+    Class* VM_class = preload_class(env, "org/apache/harmony/kernel/vm/VM");
+    env->VM_intern = class_lookup_method_recursive(VM_class, "intern", 
+            "(Ljava/lang/String;)Ljava/lang/String;");
+
     TRACE2("init", "preloading exceptions");
     env->java_lang_Throwable_Class =
         preload_class(env, env->JavaLangThrowable_String);
diff --git 
a/vm/vmcore/src/kernel_classes/javasrc/org/apache/harmony/kernel/vm/VM.java 
b/vm/vmcore/src/kernel_classes/javasrc/org/apache/harmony/kernel/vm/VM.java
old mode 100644
new mode 100755
index d267cd0..0f47529
--- a/vm/vmcore/src/kernel_classes/javasrc/org/apache/harmony/kernel/vm/VM.java
+++ b/vm/vmcore/src/kernel_classes/javasrc/org/apache/harmony/kernel/vm/VM.java
@@ -20,6 +20,8 @@
 
 package org.apache.harmony.kernel.vm;
 
+import java.lang.ref.WeakReference;
+import java.util.WeakHashMap;
 import org.apache.harmony.luni.internal.net.www.protocol.jar.JarURLConnection;
 import org.apache.harmony.luni.util.DeleteOnExit;
 
@@ -123,12 +125,35 @@ public final class VM {
      *  @return String that has the same contents as 
      *    argument, but from internal pool
      */
-    public static String intern(String s) {
-        return intern0(s);
+    public static synchronized String intern(String s) {
+
+        // NB: Since this function is called for each
+        // string literal instantiaion,
+        // string literals MUST NOT be used
+        // in this function or functions called
+        // from here
+
+        // OPTIMIZEME: two weak reference object per interned string
+        // OPTIMIZEME: change get() put() to get_or_update()
+        WeakReference ref = internedStrings.get(s);
+        String interned = null;
+        if (ref != null) {
+            interned = (String)ref.get();
+        }
+        if (interned != null) {
+            return interned;
+        } else {
+            // if the string was never interned, or was reclaimed,
+            // then store the passed in string reference
+            internedStrings.put(s,new WeakReference(s));
+            return s;
+        }
+    }
+
+    private static WeakHashMap<String,WeakReference> internedStrings;
+
+    static {
+        // initialize the storage for interned strings
+        internedStrings = new WeakHashMap(32768);
     }
-    
-    /**
-     * Invokes native string interning service.
-     */
-    private static native String intern0(String s);
 }
diff --git 
a/vm/vmcore/src/kernel_classes/native/org_apache_harmony_kernel_vm_VM.cpp 
b/vm/vmcore/src/kernel_classes/native/org_apache_harmony_kernel_vm_VM.cpp
old mode 100644
new mode 100755
index 811be3d..3c9df57
--- a/vm/vmcore/src/kernel_classes/native/org_apache_harmony_kernel_vm_VM.cpp
+++ b/vm/vmcore/src/kernel_classes/native/org_apache_harmony_kernel_vm_VM.cpp
@@ -31,7 +31,7 @@ #include "org_apache_harmony_kernel_vm_V
 #include "java_lang_VMClassRegistry.h"
 
 /**
- * Implements java.lang.String.intern(..) method.
+ * Implements org.apache.harmony.kernel.vm.VM.getClassLoader() method.
  * For details see kernel classes component documentation.
  */
 JNIEXPORT jobject JNICALL Java_org_apache_harmony_kernel_vm_VM_getClassLoader
@@ -40,14 +40,3 @@ (JNIEnv *jenv, jclass, jclass clazz)
     // reuse similar method in VMClassRegistry
     return Java_java_lang_VMClassRegistry_getClassLoader(jenv, NULL, clazz);
 }
-
-/**
- * Implements org.apache.harmony.vm.VM.intern0(..) method.
- * For details see kernel classes component documentation.
- */
-JNIEXPORT jstring JNICALL
-Java_org_apache_harmony_kernel_vm_VM_intern0(JNIEnv *jenv, jclass, jstring str)
-{
-    // call corresponding VM internal function
-    return string_intern(jenv, str);
-}
diff --git a/vm/vmcore/src/util/vm_strings.cpp 
b/vm/vmcore/src/util/vm_strings.cpp
index 51268b8..4b6e66b 100755
--- a/vm/vmcore/src/util/vm_strings.cpp
+++ b/vm/vmcore/src/util/vm_strings.cpp
@@ -29,6 +29,7 @@ #include "environment.h"
 #include "vm_stats.h"
 #include "exceptions.h"
 #include "vm_arrays.h"
+#include "ini.h"
 
 /////////////////////////////////////////////////////////////
 // begin utf8 support
@@ -540,43 +541,39 @@ Java_java_lang_String *vm_instantiate_cp
         return str->ref;
     }
 
-    volatile Java_java_lang_String* lang_string = 
string_create_from_utf8(str->bytes, str->len);
-    if (!lang_string) { // if OutOfMemory
+    jobject string = oh_allocate_local_handle();
+    string->object = string_create_from_utf8(str->bytes, str->len);
+    if (!string->object) { // if OutOfMemory
         return NULL;
     }
     assert(!tmn_is_suspend_enabled());
-
-    // Atomically update the string structure since some other thread might be 
trying to make the same update.
-    // The GC won't be able to enumerate here since GC is disabled, so there 
are no race conditions with GC.
-    volatile void *result =
-        (volatile void *)apr_atomic_casptr(
-        /*destination*/ (volatile void **)&str->ref, 
-        /*exchange*/    (void *)lang_string, 
-        /*comparand*/   (void *)NULL);    
-    if (result == NULL) {
-        // Note the successful write of the object. 
-        gc_heap_write_global_slot((Managed_Object_Handle *)&str->ref, 
(Managed_Object_Handle)lang_string);
-    }
-    // Some other thread may have beaten us to the slot.
-    lang_string = str->ref;
-
-    return (Java_java_lang_String *)lang_string;
+    
+    assert(env->VM_intern);
+
+    jvalue args[1];
+    args[0].l = string;
+    vm_execute_java_method_array((jmethodID)env->VM_intern, (jvalue*)&string, 
args);
+    ASSERT(!exn_raised(), "interning resulted in exception");
+    ASSERT(string, "interning '" << str->bytes << "' returned NULL");
+    assert(string->object);
+
+    // Cache the strong reference to interned string in class pool.
+    // Many threads may run the same string interning at once,
+    // but since they get the same value from VM.intern(),
+    // the unsynchronized store looks to be safe.
+    str->ref = string->object;
+    // Note the write of the object. 
+    gc_heap_write_global_slot((Managed_Object_Handle *)&str->ref, 
+            (Managed_Object_Handle)str->ref); 
+
+    TRACE2("intern", "interning literal '" << str->bytes << "' to " 
+            << (void*)string->object);
+
+    return (Java_java_lang_String *)string->object;
 } //vm_instantiate_cp_string_resolved
 
 // Interning of strings
 
-VMEXPORT jstring string_intern(JNIEnv *jenv, jobject jstr_obj)
-{
-    jboolean is_copy;
-    const char* val = jenv->GetStringUTFChars(jstr_obj, &is_copy);
-    String* str = VM_Global_State::loader_env->string_pool.lookup(val);
-    if (is_copy == JNI_TRUE) {
-        jenv->ReleaseStringUTFChars(jstr_obj, val);
-    }
-
-    return String_to_interned_jstring(str);
-}
-
 jstring String_to_interned_jstring(String* str)
 {
     tmn_suspend_disable();
-- 
1.4.1.g4b86

>From dbae70bf2842eaf5bf6f9d6419cf2b4c85ccbf5a Mon Sep 17 00:00:00 2001
From: Salikh Zakirov <[EMAIL PROTECTED]>
Date: Wed, 19 Jul 2006 17:10:49 +0400
Subject: [PATCH] Do not compress interned string pointers

Simplified interned strings handling by removing
the special case of compressing pointers.

The decision to use compressed pointers for strings
looks moot, and leads to code duplication without
any visible benefit. So remove it.
---
 vm/vmcore/include/String_Pool.h             |    6 --
 vm/vmcore/src/class_support/C_Interface.cpp |   18 ++----
 vm/vmcore/src/class_support/String_Pool.cpp |   81 ++++++---------------------
 vm/vmcore/src/class_support/classloader.cpp |    6 --
 vm/vmcore/src/gc/root_set_enum_common.cpp   |   24 ++------
 vm/vmcore/src/util/vm_strings.cpp           |   46 ++++-----------
 6 files changed, 44 insertions(+), 137 deletions(-)

diff --git a/vm/vmcore/include/String_Pool.h b/vm/vmcore/include/String_Pool.h
old mode 100644
new mode 100755
index e27d48e..275cd3f
--- a/vm/vmcore/include/String_Pool.h
+++ b/vm/vmcore/include/String_Pool.h
@@ -30,11 +30,7 @@ extern "C" {
 #ifdef _DEBUG
         unsigned id;                    // id for debugging
 #endif
-        // 20030507 Ref to the interned string used by 
java.lang.String.intern(). It is compressed when compressing refs.
-        union {                         
-            ManagedObject*         raw_ref;          // raw reference to 
interned string if not compressing references
-            uint32                 compressed_ref;   // equivalent compressed 
reference.
-        } intern;
+        ManagedObject* ref; // cached reference to interned string instance
         unsigned len;
         char bytes[4];
     } String;
diff --git a/vm/vmcore/src/class_support/C_Interface.cpp 
b/vm/vmcore/src/class_support/C_Interface.cpp
old mode 100644
new mode 100755
index 7f6c96b..8eca897
--- a/vm/vmcore/src/class_support/C_Interface.cpp
+++ b/vm/vmcore/src/class_support/C_Interface.cpp
@@ -753,8 +753,7 @@ const char *class_get_const_string(Class
 
 
 
-// Returns the address where the interned version of the string is stored: 
this will be the address
-// of a slot containing a Java_java_lang_String* or a uint32 compressed 
reference. Also interns the 
+// Returns the address where the interned version of the string is stored. 
Also interns the 
 // string so that the JIT can load a reference to the interned string without 
checking if it is null.
 void *class_get_const_string_intern_addr(Class_Handle cl, unsigned index)
 {
@@ -764,26 +763,19 @@ void *class_get_const_string_intern_addr
     assert(str);
 
     bool must_instantiate;
-    if (env->compress_references) {
-        must_instantiate = (str->intern.compressed_ref == 0 /*NULL*/);
-    } else {
-        must_instantiate = (str->intern.raw_ref == NULL);
-    }
+    must_instantiate = (str->ref == NULL);
 
     if (must_instantiate) {
         // vm_instantiate_cp_string_resolved assumes that GC is disabled
         tmn_suspend_disable();
-        // Discard the result. We are only interested in the side-effect of 
setting str->intern.
+        // Discard the result. We are only interested
+        // in the side-effect of setting str->ref
         vm_instantiate_cp_string_resolved(str);
         tmn_suspend_enable();
         
     }
 
-    if (env->compress_references) {
-        return &(str->intern.compressed_ref);
-    } else {
-        return &(str->intern.raw_ref);
-    }
+    return &(str->ref);
 } //class_get_const_string_intern_addr
 
 
diff --git a/vm/vmcore/src/class_support/String_Pool.cpp 
b/vm/vmcore/src/class_support/String_Pool.cpp
old mode 100644
new mode 100755
index a76f79f..d374b59
--- a/vm/vmcore/src/class_support/String_Pool.cpp
+++ b/vm/vmcore/src/class_support/String_Pool.cpp
@@ -63,11 +63,7 @@ String_Pool::_Entry::_Entry(const char *
     str.len = len;
     strncpy(str.bytes, s, len);
     str.bytes[len] = '\0';
-    // This constructor can be run very early on during VM execution--even 
before main is entered.
-    // This is before we have had a chance to process any command line 
arguments. So, initialize the 
-    // interned Java_lang_String reference to NULL in a way that will work 
whether references are compressed or not.
-    str.intern.raw_ref = NULL;
-    str.intern.raw_ref = NULL;
+    str.ref = NULL;
 } //String_Pool::_Entry::_Entry
 
 
@@ -98,11 +94,7 @@ bool String_Pool::valid_string_pool()
     unsigned short hash;
     for (hash = 0;  hash < STRING_TABLE_SIZE;  hash++) {
         for (e = _table[hash];  e != NULL;  e = e->next) {
-            if (VM_Global_State::loader_env->compress_references) {
-                jstr = (Java_java_lang_String 
*)uncompress_compressed_reference(e->intern.compressed_ref);
-            } else {
-                jstr = e->intern.raw_ref;
-            }
+            jstr = e->ref;
             if (jstr != NULL) {
                 assert(jstr->vt); // Make sure it is a valid vtable.
             }
@@ -316,23 +308,11 @@ String *String_Pool::get_next_string(Str
 
 String *String_Pool::get_first_string_intern(unsigned *cookie)
 {
-    if (VM_Global_State::loader_env->compress_references) {
-        // Examine the "compressed_ref" instead of the "raw_ref" field.
-        for (unsigned i = 0; i < STRING_TABLE_SIZE; i++) {
-            for (_Entry *e = _table[i]; e != NULL; e = e->next) {
-                if (e->str.intern.compressed_ref != 0) {
-                    *cookie = i;
-                    return &(e->str);
-                }
-            }
-        }
-    } else {
-        for (unsigned i = 0; i < STRING_TABLE_SIZE; i++) {
-            for (_Entry *e = _table[i]; e != NULL; e = e->next) {
-                if (e->str.intern.raw_ref != NULL) {
-                    *cookie = i;
-                    return &(e->str);
-                }
+    for (unsigned i = 0; i < STRING_TABLE_SIZE; i++) {
+        for (_Entry *e = _table[i]; e != NULL; e = e->next) {
+            if (e->str.ref != NULL) {
+                *cookie = i;
+                return &(e->str);
             }
         }
     }
@@ -345,45 +325,22 @@ String *String_Pool::get_next_string_int
 {
     assert(prev);
     unsigned short hash = (short)*cookie;
-    if (VM_Global_State::loader_env->compress_references) {
-        // Examine the "compressed_ref" instead of the "raw_ref" field.
-        for (_Entry *e = _table[hash]; e != NULL; e = e->next) {
-            if ((&(e->str)) == prev) {
-                for (e = e->next; e != NULL; e = e->next) {
-                    if (e->str.intern.compressed_ref) {
-                        // same cookie
-                        return &(e->str);
-                    }
-                }
-                break;
-            }
-        }
-        for (unsigned i = hash +1; i < STRING_TABLE_SIZE; i++ ) {
-            for (_Entry *e = _table[i]; e!= NULL; e= e->next) {
-                if (e->str.intern.compressed_ref) {
-                    *cookie = i;
+    for (_Entry *e = _table[hash]; e != NULL; e = e->next) {
+        if ((&(e->str)) == prev) {
+            for (e = e->next; e != NULL; e = e->next) {
+                if (e->str.ref) {
+                    // same cookie
                     return &(e->str);
                 }
             }
+            break;
         }
-    } else {
-        for (_Entry *e = _table[hash]; e != NULL; e = e->next) {
-            if ((&(e->str)) == prev) {
-                for (e = e->next; e != NULL; e = e->next) {
-                    if (e->str.intern.raw_ref) {
-                        // same cookie
-                        return &(e->str);
-                    }
-                }
-                break;
-            }
-        }
-        for (unsigned i = hash +1; i < STRING_TABLE_SIZE; i++ ) {
-            for (_Entry *e = _table[i]; e!= NULL; e= e->next) {
-                if (e->str.intern.raw_ref) {
-                    *cookie = i;
-                    return &(e->str);
-                }
+    }
+    for (unsigned i = hash +1; i < STRING_TABLE_SIZE; i++ ) {
+        for (_Entry *e = _table[i]; e!= NULL; e= e->next) {
+            if (e->str.ref) {
+                *cookie = i;
+                return &(e->str);
             }
         }
     }
diff --git a/vm/vmcore/src/class_support/classloader.cpp 
b/vm/vmcore/src/class_support/classloader.cpp
old mode 100644
new mode 100755
index eddf97d..2136524
--- a/vm/vmcore/src/class_support/classloader.cpp
+++ b/vm/vmcore/src/class_support/classloader.cpp
@@ -1656,11 +1656,7 @@ Class* UserDefinedClassLoader::LoadClass
     // can cause GC and we would like to get away with code that doesn't
     // protect references from GC.
     ManagedObject* jstr;
-    if (env->compress_references) {
-        jstr = 
uncompress_compressed_reference(class_name_with_dots->intern.compressed_ref);
-    } else {
-        jstr = class_name_with_dots->intern.raw_ref;
-    }
+    jstr = class_name_with_dots->ref;
     if (jstr != NULL) {
         ObjectHandle h = oh_allocate_local_handle();
         h->object = jstr;
diff --git a/vm/vmcore/src/gc/root_set_enum_common.cpp 
b/vm/vmcore/src/gc/root_set_enum_common.cpp
old mode 100644
new mode 100755
index 17a81b7..9677fa8
--- a/vm/vmcore/src/gc/root_set_enum_common.cpp
+++ b/vm/vmcore/src/gc/root_set_enum_common.cpp
@@ -39,25 +39,13 @@ vm_enumerate_interned_strings()
     String *ps = 
VM_Global_State::loader_env->string_pool.get_first_string_intern(&cookie);
     // 20030405 Don't enumerate references that are *unmanaged null* (i.e. 
zero/NULL)
     // since vm_enumerate_root_reference() expects to be called with slots 
containing managed refs.
-    if (VM_Global_State::loader_env->compress_references) {
-        while (ps != NULL) {
-            COMPRESSED_REFERENCE compressed_ref = ps->intern.compressed_ref;
-            assert(is_compressed_reference(compressed_ref));
-            if (compressed_ref != 0) {
-                vm_enumerate_compressed_root_reference((COMPRESSED_REFERENCE 
*)&ps->intern.compressed_ref, 
-                        VM_Global_State::loader_env->pin_interned_strings);
-            }
-            ps = 
VM_Global_State::loader_env->string_pool.get_next_string_intern(ps, &cookie);
-        }
-    } else {
-        while (ps != NULL) {
-            ManagedObject* s = ps->intern.raw_ref;
-            if (s != NULL) {
-                vm_enumerate_root_reference((void **)&(ps->intern.raw_ref), 
-                        VM_Global_State::loader_env->pin_interned_strings);
-            }
-            ps = 
VM_Global_State::loader_env->string_pool.get_next_string_intern(ps, &cookie);
+    while (ps != NULL) {
+        ManagedObject* s = ps->ref;
+        if (s != NULL) {
+            vm_enumerate_root_reference((void **)&(ps->ref), 
+                    VM_Global_State::loader_env->pin_interned_strings);
         }
+        ps = 
VM_Global_State::loader_env->string_pool.get_next_string_intern(ps, &cookie);
     }
     VM_Global_State::loader_env->string_pool.unlock_pool();
 } //vm_enumerate_interned_strings
diff --git a/vm/vmcore/src/util/vm_strings.cpp 
b/vm/vmcore/src/util/vm_strings.cpp
old mode 100644
new mode 100755
index f1fe7cb..51268b8
--- a/vm/vmcore/src/util/vm_strings.cpp
+++ b/vm/vmcore/src/util/vm_strings.cpp
@@ -536,14 +536,8 @@ Java_java_lang_String *vm_instantiate_cp
 {
     assert(!tmn_is_suspend_enabled());
     Global_Env *env = VM_Global_State::loader_env;
-    if (env->compress_references) {
-        if (str->intern.compressed_ref != 0) {
-            return uncompress_compressed_reference(str->intern.compressed_ref);
-        }
-    } else {
-        if (str->intern.raw_ref != NULL) {
-            return str->intern.raw_ref;
-        }
+    if (str->ref != NULL) {
+        return str->ref;
     }
 
     volatile Java_java_lang_String* lang_string = 
string_create_from_utf8(str->bytes, str->len);
@@ -554,33 +548,17 @@ Java_java_lang_String *vm_instantiate_cp
 
     // Atomically update the string structure since some other thread might be 
trying to make the same update.
     // The GC won't be able to enumerate here since GC is disabled, so there 
are no race conditions with GC.
-    if (env->compress_references) {
-        COMPRESSED_REFERENCE compressed_lang_string = 
(COMPRESSED_REFERENCE)((POINTER_SIZE_INT)lang_string - 
(POINTER_SIZE_INT)Class::heap_base);
-        assert(is_compressed_reference(compressed_lang_string));     
-        assert(sizeof(LONG) == sizeof(uint32));
-        uint32 result = apr_atomic_cas32(
-            /*destination*/ (volatile uint32 *)&str->intern.compressed_ref, 
-            /*exchange*/    compressed_lang_string,  
-            /*comparand*/   0);    
-        if (result == 0) {
-            // Note the successful write of the object. 
-            gc_heap_write_global_slot_compressed((COMPRESSED_REFERENCE 
*)&str->intern.compressed_ref, (Managed_Object_Handle)lang_string);
-        }
-        // Some other thread may have beaten us to the slot.
-        lang_string = (volatile Java_java_lang_String 
*)uncompress_compressed_reference(str->intern.compressed_ref);
-    } else {
-        volatile void *result =
-            (volatile void *)apr_atomic_casptr(
-            /*destination*/ (volatile void **)&str->intern.raw_ref, 
-            /*exchange*/    (void *)lang_string, 
-            /*comparand*/   (void *)NULL);    
-        if (result == NULL) {
-            // Note the successful write of the object. 
-            gc_heap_write_global_slot((Managed_Object_Handle 
*)&str->intern.raw_ref, (Managed_Object_Handle)lang_string);
-        }
-        // Some other thread may have beaten us to the slot.
-        lang_string = str->intern.raw_ref;
+    volatile void *result =
+        (volatile void *)apr_atomic_casptr(
+        /*destination*/ (volatile void **)&str->ref, 
+        /*exchange*/    (void *)lang_string, 
+        /*comparand*/   (void *)NULL);    
+    if (result == NULL) {
+        // Note the successful write of the object. 
+        gc_heap_write_global_slot((Managed_Object_Handle *)&str->ref, 
(Managed_Object_Handle)lang_string);
     }
+    // Some other thread may have beaten us to the slot.
+    lang_string = str->ref;
 
     return (Java_java_lang_String *)lang_string;
 } //vm_instantiate_cp_string_resolved
-- 
1.4.1.g4b86


---------------------------------------------------------------------
Terms of use : http://incubator.apache.org/harmony/mailing.html
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Reply via email to