Skip to content

Commit aa4f143

Browse files
ChrisHegartyrmuir
andauthored
Avoid static dependency from TermsEnum to one of its subclasses (#15319)
Fixes a potential hang with initialisation of TermsEnum and BaseTermsEnum, by simply removing the dependency and replicating the small amount of code. Problem description: the static TermsEnum.EMPTY initialises to an implementation of BaseTermsEnum. TermsEnum is a superclass of BaseTermsEnum, so there is a clear dependency between these classes. If a subclass of BaseTermsEnum is initialising it may grab the lock on BaseTermsEnum, and prevent TermsEnum from initialising. --------- Co-authored-by: Robert Muir <[email protected]>
1 parent a71c429 commit aa4f143

File tree

2 files changed

+25
-2
lines changed

2 files changed

+25
-2
lines changed

lucene/CHANGES.txt

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -199,6 +199,8 @@ Bug Fixes
199199
removing co-planar points to do it once after all holes are removed instead of doing it for each
200200
removed hole.
201201

202+
* GITHUB#15319: Fix potential hang in initialisation of TermsEnum and BaseTermsEnum (Chris Hegarty)
203+
202204
Other
203205
---------------------
204206
* GITHUB#15237: Fix SmartChinese to only deserialize dictionary data from classpath with a native array

lucene/core/src/java/org/apache/lucene/index/TermsEnum.java

Lines changed: 23 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -196,9 +196,30 @@ public final PostingsEnum postings(PostingsEnum reuse) throws IOException {
196196
* Attributes to it. This should not be a problem, as the enum is always empty and the existence
197197
* of unused Attributes does not matter.
198198
*/
199-
@SuppressWarnings("ClassInitializationDeadlock") // FIXME: may cause hangs!
199+
// Avoid refactoring that results in a dependency on a subclass, like BaseTermsEnum.
200+
// See: https://github.com/apache/lucene/issues/15317
200201
public static final TermsEnum EMPTY =
201-
new BaseTermsEnum() {
202+
new TermsEnum() {
203+
204+
private AttributeSource atts;
205+
206+
@Override
207+
public AttributeSource attributes() {
208+
if (atts == null) {
209+
atts = new AttributeSource();
210+
}
211+
return atts;
212+
}
213+
214+
@Override
215+
public boolean seekExact(BytesRef text) {
216+
return seekCeil(text) == SeekStatus.FOUND;
217+
}
218+
219+
@Override
220+
public IOBooleanSupplier prepareSeekExact(BytesRef text) {
221+
return () -> seekExact(text);
222+
}
202223

203224
@Override
204225
public SeekStatus seekCeil(BytesRef term) {

0 commit comments

Comments
 (0)