[ https://issues.apache.org/jira/browse/OFBIZ-2186?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=12680015#action_12680015 ]
benoitw edited comment on OFBIZ-2186 at 3/8/09 2:17 PM: ------------------------------------------------------------- M. Jones, CacheLineTable and LRUMap do not synchronize on the same lock - CacheLineTable synchronization use the CacheLineTable instance monitor - LRUMap synchronization use the LRUMap instance monitor the LRUMap (memoryTable) can be updated concurrently by 2 differents threads - one in the CacheLineTable #put or CacheLineTable#remove - another in the CacheLineTable#get this leads to the corruption of the LRUMap which is not thread-safe the CacheLineTable#get should be synchronized or the LRUMap should be replaced by a thead safe collection Benoit Wiart www.ubik-ingenierie.com was (Author: benoitw): M. Jones, CacheLineTable and LRUMap do not synchronize on the same lock - CacheLineTable synchronization use the CacheLineTable instance monitor - LRUMap synchronization use the LRUMap instance monitor the LRUMap (memoryTable) can be updated concurrently by 2 differents threads (or more than 2) - one in the CacheLineTable #put or CacheLineTable#remove - another in the CacheLineTable#get this leads to the corruption of the LRUMap which is not thread-safe the CacheLineTable#get should be synchronized or the LRUMap should be replaced by a thead safe collection Benoit Wiart www.ubik-ingenierie.com > OutOfMemory provoked by Cache overflow > -------------------------------------- > > Key: OFBIZ-2186 > URL: https://issues.apache.org/jira/browse/OFBIZ-2186 > Project: OFBiz > Issue Type: Bug > Components: framework > Affects Versions: SVN trunk, Release Branch 4.0 > Environment: Linux, JDK 1.5_15, Xmx set to 1156Mo > Reporter: Philippe Mouawad > Priority: Critical > Attachments: CacheLineTable-patch.txt, OfbizBug.zip > > > In our production system, we had an OutOfMemoryError. > I analyzed the generated Heap Dump and found the following: > The cache entitycache.entity-list.default.ProductCategoryMember retains a > heap of 369314128 Bytes. > The LRUMap hold by this object is occupying this space (369314128) and this > object has a stange state: > - maxSize is set to 5000 (as set in the cache.properties) > - size is 128930 => PROBLEM > IN cache.properties: > entitycache.entity-list.default.ProductCategoryMember.expireTime=3600000 > entitycache.entity-list.default.ProductCategoryMember.useSoftReference=true > entitycache.entity-list.default.ProductCategoryMember.maxInMemory=5000 > entitycache.entity-list.default.ProductCategoryMember.maxSize=7500 > I analyzed the code of LRUMap and its usage in CacheLineTable and IMHO the > bug is a missing synchonized in get(): > public CacheLine<V> get(Object key) { > if (key == null) { > if (Debug.verboseOn()) Debug.logVerbose("In CacheLineTable tried > to get with null key, using NullObject" + this.cacheName, module); > } > return getNoCheck(key); > } > Since LRUMap extends LinkedHashMap, if you look at get method, it changes the > state of the Map by calling e.recordAccess(this): > public V get(Object key) { > Entry<K,V> e = (Entry<K,V>)getEntry(key); > if (e == null) > return null; > e.recordAccess(this); > return e.value; > } > So the default of synchronization corrupts the state of LRUMap which grows > indefinitely > I will submit a patch for this on the trunk. > Philippe > www.ubik-ingenierie.com -- This message is automatically generated by JIRA. - You can reply to this email to add a comment to the issue online.