RFR 8029891 : Deadlock detected in java/lang/ClassLoader/deadlock/GetResource.java
Daniel Fuchs
daniel.fuchs at oracle.com
Fri May 15 19:58:48 UTC 2015
Hi Brent,
1163 @Override
1164 public Enumeration<Object> keys() {
1165 return map.keys();
1166 }
I wonder if you should use:
public Enumeration<Object> keys() {
return Collections.enumeration(map.keySet());
}
instead.
ConcurrentHashMap.keys() returns an Enumeration which is also an
Iterator which supports removal of elements, that might have
unintended side effects WRT to concurrency & subclassing.
best regards,
-- daniel
On 15/05/15 21:09, Brent Christian wrote:
> On 5/13/15 8:53 AM, Mandy Chung wrote:
>>> On May 12, 2015, at 2:26 PM, Peter Levart <peter.levart at gmail.com>
>>> wrote:
>>> On 05/12/2015 10:49 PM, Mandy Chung wrote:
>>>>> But I think it should be pretty safe to make the
>>>>> java.util.Properties object override all Hashtable methods and
>>>>> delegate to internal CMH so that:
>>>>> - all modification methods + all bulk read methods such as
>>>>> (keySet().toArray, values.toArray) are made synchronized again
>>>>> - individual entry read methods (get, containsKey, ...) are not
>>>>> synchronized.
>>>>>
>>>>> This way we get the benefits of non-synchronized read access
>>>>> but the change is hardly observable. In particular since
>>>>> external synchronization on the Properties object makes guarded
>>>>> code atomic like it is now and individual entry read accesses
>>>>> are almost equivalent whether they are synchronized or not and
>>>>> I would be surprised if any code using Properties for the
>>>>> purpose they were designed for worked any differently.
>>>>
>>>> I agree that making read-only methods not synchronized while
>>>> keeping any method with write-access with synchronized is pretty
>>>> safe change and low compatibility risk. On the other hand, would
>>>> most of the overrridden methods be synchronized then?
>>>
>>> Yes, and that doesn't seem to be a problem. Setting properties is
>>> not very frequent operation and is usually quite localized. Reading
>>> properties is, on the other hand, a very frequent operation
>>> dispersed throughout the code (almost like logging) and therefore
>>> very prone to deadlocks like the one in this issue. I think that by
>>> having an unsynchronized get(Property), most problems with
>>> Properties will be solved - deadlock and performance (scalability)
>>> related.
>>
>> I’m keen on cleaning up the system properties but it is a bigger
>> scope as it should take other related enhancement requests into
>> account that should be something for future. I think what you
>> propose seems a good solution to fix JDK-8029891 while it doesn’t
>> completely get us off the deadlock due to user code locking the
>> Properties object.
>
> Updated webrev:
>
> http://cr.openjdk.java.net/~bchristi/8029891/webrev.1/
>
> I have restored synchronization to modification methods, and to my
> interpretation of "bulk read" operations:
>
> * forEach
> * replaceAll
> * store: (synchronized(this) in store0; also, entrySet() returns a
> synchronizedSet)
> * storeToXML: PropertiesDefaultsHandler.store() synchronizes on the
> Properties instance
> * propertyNames(): returns an Enumeration not backed by the
> Properies; calls (still synchronized) enumerate()
> * stringPropertyNames returns a Set not backed by the Properties;
> calls (still synchronized) enumerateStringProperties
>
> These continue to return a synchronized[Set|Collection]:
> * keySet
> * entrySet
> * values
>
> These methods should operate on a coherent snapshot:
> * clone
> * equals
> * hashCode
>
> I expect these two are only used for debugging. I wonder if we could
> get away with removing synchronization:
> * list
> * toString
>
> I'm still looking through the serialization code, though I suspect some
> synchronization should be added.
>
> The new webrev also has the updated test case from Peter.
>
> Thanks,
> -Brent
>
More information about the core-libs-dev
mailing list