I'm pretty sure there's just one string intern pool, as described in
String.intern(). Classes may contain additional references to the strings which are referenced in the intern pool, but that doesn't change that there's just one intern pool.
There are, however, several other pools which are referenced in the specs. These include a
constant pool which is part of the class file structure, and a
runtime constant pool, which is an in-memory representation of the same information (after a class is loaded). These pools are
not the same as the intern pool described in String.intern() and elsewhere. The contant pools contain
all compile-time constants for a class (not just Strings),and there's one pool per class. (Well, one constant pool per class file, and one runtime constant pool per loaded class.) The String intern pool contains only Strings, and there should be only one intern pool in the whole JVM. As far as I've been able to determine, anyway.
EFH, when you say earlier references were unclear about this, is it possible this was confusion between the different types of pools? Or was there something else which suggested there might be multiple intern pools? There are, of course, various parts of the specs that can be ambiguous; the JLS and JVMS are not perfect. But is there something specific about this issue which is (or was) ambiguous?
[EFH]: But unless you're doing something fancy with multiple class loaders, every literal "Hello" in a program definitely refers to the same single String object -- and they may still even if you are. Based on past discussions here, plus
testing, it seems that the only case that we have found where two identical literals can refer to different instances is this one: if you use different classloaders to load
and unload classes, you can create a situation in which a literal refers to one instance, and then later, an identical literal refers to a different instance. This is only possible if the literals (or rather, the classes that contain them)
are never in the JVM at the same time. Once you unload a class, the intern pool does not prevent GC, so it's possible to forget the old reference. In which case an identical literal may later refer to a different instance. Which is mostly academic, as there are very few ways to compare the identities of two instances which are not in memory at the same time, and usually no reason to do so. Except for the occasional discussion such as this one...