You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@struts.apache.org by bu...@apache.org on 2003/02/24 06:29:58 UTC

DO NOT REPLY [Bug 17328] New: - Unsafe initialization in PropertyMessageResources

DO NOT REPLY TO THIS EMAIL, BUT PLEASE POST YOUR BUG 
RELATED COMMENTS THROUGH THE WEB INTERFACE AVAILABLE AT
<http://nagoya.apache.org/bugzilla/show_bug.cgi?id=17328>.
ANY REPLY MADE TO THIS MESSAGE WILL NOT BE COLLECTED AND 
INSERTED IN THE BUG DATABASE.

http://nagoya.apache.org/bugzilla/show_bug.cgi?id=17328

Unsafe initialization in PropertyMessageResources

           Summary: Unsafe initialization in PropertyMessageResources
           Product: Struts
           Version: 1.1 Beta 3
          Platform: All
        OS/Version: All
            Status: NEW
          Severity: Normal
          Priority: Other
         Component: Utilities
        AssignedTo: struts-dev@jakarta.apache.org
        ReportedBy: mark@fortressofgeekdom.org


This is actually against 1.1rc1, which isn't in the list of available versions yet.

I was recently troubleshooting an issue where my application would sometimes
'lose' messages loaded from a PropertyMessageResources object.  Sometimes
certain keys were not found while others were, even though both were defined in
the same .properties file.  And once a certain key was not found, it was toast
until the webapp is reloaded.

I tracked the problem down to some non-threadsafe initialization in
PropertyMessageResources.

To reproduce the problem:

1. You must have 2 or more threads attempting to access keys from a
PropertyMessageResources object at the same time, before the locales have been
loaded.  In my (probably uncommon) case, this happens all the time.

2. You must not have specified a specific messageresources.properties file for
the locale these threads are hitting-- you must let them access the default
messageresources.properties file.

Let's say that thread 1 attempts to access a message key in the en_US locale. 
The locale has not yet been loaded, so it starts to load the locale.

While that's happening, thread 2 attempts to access a message key in the en_US
locale.  It calls the loadLocale() method, which returns having done nothing,
because thread 1 is still loading.

Thread 2 then tries to look up the locale-specific message
"en_US.login.username".  It isn't found because there is no en_US-specific
properties file, so it tries to look it up in the default locale.  The message
still isn't found because Thread 1 is I/O bound and still hasn't finished
loading the messages.  So thread 2 gets "???en_US.login.username???" back as the
message.

Thread 2 then decides to cache the bogus ("???en_US.login.username???") message
back in the en_US map, to avoid having to look at the default locale in the future.

Now thread 1 finishes loading the properties file, synchronizes on the messages
map and inserts all of the messages found for the default locale.

So the message map now contains:

en_US.login.username -> ???en_US.login.username???
login.username -> 'The real text for this message'

But since all future accesses for this key will check first in the en_US locale,
this message key is in effect permanently broken.

I'm perfectly willing to do a patch for this, because I've tracked through the
current code and I know exactly where the problem is.  I haven't yet because I'd
like to get feedback on how to best fix the problem.

The simplest and most correct (I think) way would be to block any thread
attempting to access a locale until that locale has finished loading.  That way
no uninitialized data is ever returned.

That may be an unacceptable performance or reliability problem.  Any other ideas?

-- Mark Lewis (mark@fortressofgeekdom.org)

---------------------------------------------------------------------
To unsubscribe, e-mail: struts-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: struts-dev-help@jakarta.apache.org