Commit 502a9139 authored by Luna Riegel's avatar Luna Riegel
Browse files

Fix: Remove race condition in ImplicitGeometries

parent a42107d4
...@@ -28,6 +28,7 @@ public class ImplicitGeometryHolder extends Geometry { ...@@ -28,6 +28,7 @@ public class ImplicitGeometryHolder extends Geometry {
LIBRARY_OBJECT, RELATIVE_GEOMETRY LIBRARY_OBJECT, RELATIVE_GEOMETRY
} }
private ImplicitGeometry cgmlImplicitGeometry = null; private ImplicitGeometry cgmlImplicitGeometry = null;
private static ConcurrentHashMap<ImplicitGeometryHolder, ImplicitGeometry> deferredRelGeomObjects = new ConcurrentHashMap<>(); private static ConcurrentHashMap<ImplicitGeometryHolder, ImplicitGeometry> deferredRelGeomObjects = new ConcurrentHashMap<>();
private final PrototypeGeometryType type; private final PrototypeGeometryType type;
...@@ -112,6 +113,27 @@ public class ImplicitGeometryHolder extends Geometry { ...@@ -112,6 +113,27 @@ public class ImplicitGeometryHolder extends Geometry {
LibraryObject.resetObjectMap(); LibraryObject.resetObjectMap();
} }
/**
* Prepares the prototype geometries for checking and sets a lock to prevent clearing of metadata
*/
public static void preparePrototypeGeometriesForChecking(){
RelativeGeometry.preparePrototypeGeometriesForChecking();
LibraryObject.preparePrototypeGeometriesForChecking();
}
/**
* Clears metadata creating for checking of prototype geometries and releases the metadata lock
*/
public static void clearMetaDataOfPrototypeGeometries(){
RelativeGeometry.clearMetaDataOfPrototypeGeometries();
LibraryObject.clearMetaDataOfPrototypeGeometries();
}
@Override
public void accept(CheckableVisitor c) {
prototypeGeometry.accept(c);
}
@Override @Override
public boolean isValidated() { public boolean isValidated() {
return prototypeGeometry.isValidated(); return prototypeGeometry.isValidated();
......
...@@ -26,7 +26,7 @@ public class LibraryObject extends Geometry { ...@@ -26,7 +26,7 @@ public class LibraryObject extends Geometry {
private static final Logger logger = LogManager.getLogger(LibraryObject.class); private static final Logger logger = LogManager.getLogger(LibraryObject.class);
@Serial @Serial
private static final long serialVersionUID = -50293435187454911L; private static final long serialVersionUID = -50293435187454911L;
private static boolean metadataLocked = false;
private static final Map<String, LibraryObject> libraryObjects = new ConcurrentHashMap<>(); private static final Map<String, LibraryObject> libraryObjects = new ConcurrentHashMap<>();
public static LibraryObject of(Path path, ParserConfiguration config) { public static LibraryObject of(Path path, ParserConfiguration config) {
...@@ -83,4 +83,29 @@ public class LibraryObject extends Geometry { ...@@ -83,4 +83,29 @@ public class LibraryObject extends Geometry {
public static void resetObjectMap() { public static void resetObjectMap() {
libraryObjects.clear(); libraryObjects.clear();
} }
public static void preparePrototypeGeometriesForChecking() {
libraryObjects.values().forEach(LibraryObject::updateEdgesAndVertices);
metadataLocked = true;
}
public static void clearMetaDataOfPrototypeGeometries() {
metadataLocked = false;
libraryObjects.values().forEach(LibraryObject::clearMetaData);
}
@Override
public void updateEdgesAndVertices(){
if (!metadataLocked) {
super.updateEdgesAndVertices();
}
}
@Override
public void clearMetaData(){
if (!metadataLocked) {
super.clearMetaData();
}
}
} }
...@@ -15,6 +15,7 @@ public class RelativeGeometry extends Geometry { ...@@ -15,6 +15,7 @@ public class RelativeGeometry extends Geometry {
private static final long serialVersionUID = -686112245455298977L; private static final long serialVersionUID = -686112245455298977L;
private static final Map<GmlId, RelativeGeometry> relativeGeometries = new ConcurrentHashMap<>(); private static final Map<GmlId, RelativeGeometry> relativeGeometries = new ConcurrentHashMap<>();
private static boolean metadataLocked = false;
public static RelativeGeometry of(GmlId gmlId, Geometry geom) { public static RelativeGeometry of(GmlId gmlId, Geometry geom) {
if (relativeGeometries.containsKey(gmlId)) { if (relativeGeometries.containsKey(gmlId)) {
...@@ -38,4 +39,28 @@ public class RelativeGeometry extends Geometry { ...@@ -38,4 +39,28 @@ public class RelativeGeometry extends Geometry {
public static void resetObjectMap() { public static void resetObjectMap() {
relativeGeometries.clear(); relativeGeometries.clear();
} }
public static void preparePrototypeGeometriesForChecking() {
relativeGeometries.values().forEach(RelativeGeometry::updateEdgesAndVertices);
metadataLocked = true;
}
public static void clearMetaDataOfPrototypeGeometries() {
metadataLocked = false;
relativeGeometries.values().forEach(RelativeGeometry::clearMetaData);
}
@Override
public void updateEdgesAndVertices(){
if (!metadataLocked) {
super.updateEdgesAndVertices();
}
}
@Override
public void clearMetaData(){
if (!metadataLocked) {
super.clearMetaData();
}
}
} }
...@@ -33,6 +33,7 @@ import de.hft.stuttgart.citydoctor2.datastructure.CityDoctorModel; ...@@ -33,6 +33,7 @@ import de.hft.stuttgart.citydoctor2.datastructure.CityDoctorModel;
import de.hft.stuttgart.citydoctor2.datastructure.CityObject; import de.hft.stuttgart.citydoctor2.datastructure.CityObject;
import de.hft.stuttgart.citydoctor2.datastructure.FeatureType; import de.hft.stuttgart.citydoctor2.datastructure.FeatureType;
import de.hft.stuttgart.citydoctor2.datastructure.GmlId; import de.hft.stuttgart.citydoctor2.datastructure.GmlId;
import de.hft.stuttgart.citydoctor2.datastructure.ImplicitGeometryHolder;
import de.hft.stuttgart.citydoctor2.parser.CityGmlConsumer; import de.hft.stuttgart.citydoctor2.parser.CityGmlConsumer;
import de.hft.stuttgart.citydoctor2.parser.CityGmlParseException; import de.hft.stuttgart.citydoctor2.parser.CityGmlParseException;
import de.hft.stuttgart.citydoctor2.parser.CityGmlParser; import de.hft.stuttgart.citydoctor2.parser.CityGmlParser;
...@@ -669,10 +670,12 @@ public class Checker { ...@@ -669,10 +670,12 @@ public class Checker {
(threadCount, threadCount, 60L, TimeUnit.SECONDS, new LinkedBlockingQueue<>()); (threadCount, threadCount, 60L, TimeUnit.SECONDS, new LinkedBlockingQueue<>());
try{ try{
long startTime = System.nanoTime(); long startTime = System.nanoTime();
ImplicitGeometryHolder.preparePrototypeGeometriesForChecking();
List<Future<GmlId>> futures = runChecksOnFeatures(exec, cache, features, checkedCount, l); List<Future<GmlId>> futures = runChecksOnFeatures(exec, cache, features, checkedCount, l);
List<GmlId> missedFeatures = getMissedFeatures(futures); List<GmlId> missedFeatures = getMissedFeatures(futures);
ImplicitGeometryHolder.clearMetaDataOfPrototypeGeometries();
if (!missedFeatures.isEmpty()){ if (!missedFeatures.isEmpty()){
logger.error(Localization.getText("Checker.dbUnresponsive")); logger.error(Localization.getText("Checker.dbUnresponsive"));
if (logger.isDebugEnabled()){ if (logger.isDebugEnabled()){
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment