Skip to content

Commit b98920e

Browse files
no races
1 parent 1199310 commit b98920e

File tree

1 file changed

+16
-5
lines changed

1 file changed

+16
-5
lines changed

server/src/main/java/org/elasticsearch/index/shard/IndexShard.java

+16-5
Original file line numberDiff line numberDiff line change
@@ -155,6 +155,8 @@
155155
import java.io.Closeable;
156156
import java.io.IOException;
157157
import java.io.PrintStream;
158+
import java.lang.invoke.MethodHandles;
159+
import java.lang.invoke.VarHandle;
158160
import java.nio.channels.ClosedByInterruptException;
159161
import java.nio.charset.StandardCharsets;
160162
import java.util.ArrayList;
@@ -1019,14 +1021,24 @@ private Engine.IndexResult applyIndexOperation(
10191021
return index(engine, operation);
10201022
}
10211023

1022-
public void setFieldInfos(FieldInfos fieldInfos) {
1023-
this.fieldInfos = fieldInfos;
1024+
private static final VarHandle FIELD_INFOS;
1025+
1026+
static {
1027+
try {
1028+
FIELD_INFOS = MethodHandles.lookup().findVarHandle(IndexShard.class, "fieldInfos", FieldInfos.class);
1029+
} catch (Exception e) {
1030+
throw new ExceptionInInitializerError(e);
1031+
}
10241032
}
10251033

10261034
public FieldInfos getFieldInfos() {
10271035
var res = fieldInfos;
10281036
if (res == null) {
1029-
return loadFieldInfos();
1037+
// don't replace field infos loaded via the refresh listener to avoid overwriting the field with an older version of the
1038+
// field infos when racing with a refresh
1039+
var read = loadFieldInfos();
1040+
var existing = (FieldInfos) FIELD_INFOS.compareAndExchange(this, null, read);
1041+
return existing == null ? read : existing;
10301042
}
10311043
return res;
10321044
}
@@ -4135,15 +4147,14 @@ public void beforeRefresh() {}
41354147
@Override
41364148
public void afterRefresh(boolean didRefresh) {
41374149
if (enableFieldHasValue && (didRefresh || fieldInfos == null)) {
4138-
loadFieldInfos();
4150+
FIELD_INFOS.setRelease(IndexShard.this, loadFieldInfos());
41394151
}
41404152
}
41414153
}
41424154

41434155
private FieldInfos loadFieldInfos() {
41444156
try (Engine.Searcher hasValueSearcher = getEngine().acquireSearcher("field_has_value")) {
41454157
var res = FieldInfos.getMergedFieldInfos(hasValueSearcher.getIndexReader());
4146-
setFieldInfos(res);
41474158
return res;
41484159
} catch (AlreadyClosedException ignore) {
41494160
// engine is closed - no update to3 FieldInfos is fine

0 commit comments

Comments
 (0)