This is an automated email from the ASF dual-hosted git repository.

desruisseaux pushed a commit to branch geoapi-4.0
in repository https://gitbox.apache.org/repos/asf/sis.git

commit f75d3fb406f8aebeddaa35624c5813ededd48e5e
Author: Martin Desruisseaux <martin.desruisse...@geomatys.com>
AuthorDate: Tue Feb 6 15:50:11 2024 +0100

    Partial cleanup of compiler warnings:
    - Resolve "unchecked" warnings with an internal `Unsafe` class.
    - "ThisEscapedInObjectConstruction" replaced by "this-escape".
    - Remove a few @SuppressWarnings("null") which were too broad.
---
 .../sis/buildtools/coding/ReorganizeImports.java   |   5 +-
 .../main/org/apache/sis/console/SIS.java           |   2 +-
 .../apache/sis/feature/DefaultAttributeType.java   |   2 +-
 .../org/apache/sis/feature/DefaultFeatureType.java |   2 +-
 .../main/org/apache/sis/image/ComputedTiles.java   |   1 -
 .../org/apache/sis/index/tree/NodeIterator.java    |   1 -
 .../sis/image/processing/isoline/StepsViewer.java  |   1 -
 .../org/apache/sis/metadata/PropertyAccessor.java  |  23 +++--
 .../main/org/apache/sis/metadata/TreeNode.java     |   8 +-
 .../org/apache/sis/metadata/internal/Merger.java   |  15 +--
 .../main/org/apache/sis/xml/bind/Context.java      |   1 -
 .../apache/sis/xml/bind/lan/LocaleAndCharset.java  |   9 +-
 .../apache/sis/metadata/iso/MarshallingTest.java   |   1 -
 .../sis/profile/japan/netcdf/FactoryForUCAR.java   |   2 +
 .../referencing/gazetteer/FinalLocationType.java   |   6 +-
 .../sis/referencing/gazetteer/LocationFormat.java  |   2 +-
 .../gazetteer/ReferencingByIdentifiers.java        |   2 +-
 .../apache/sis/geometry/WraparoundInEnvelope.java  |   1 -
 .../operation/transform/ConcatenatedTransform.java |   2 +
 .../org/apache/sis/storage/geotiff/DataSubset.java |   1 +
 .../sis/storage/geotiff/ImageFileDirectory.java    |  12 +--
 .../sis/storage/geotiff/writer/TileMatrix.java     |   1 -
 .../sis/storage/netcdf/ucar/DecoderWrapper.java    |   4 +-
 .../apache/sis/storage/sql/SQLStoreProvider.java   |   7 +-
 .../sis/storage/sql/feature/FeatureIterator.java   |   1 +
 .../sis/storage/xml/stream/StaxStreamReader.java   |   3 +-
 .../sis/storage/xml/stream/StaxStreamWriter.java   |   1 -
 .../org/apache/sis/storage/StorageConnector.java   |   4 +-
 .../main/org/apache/sis/storage/folder/Store.java  |   2 +-
 .../sis/measure/FormattedCharacterIterator.java    |   7 +-
 .../main/org/apache/sis/measure/UnitDimension.java |   1 -
 .../main/org/apache/sis/measure/UnitFormat.java    |   2 +-
 .../org/apache/sis/system/OptionalDependency.java  |   1 -
 .../org/apache/sis/util/ConditionallySafe.java     |  38 ++++++++
 .../main/org/apache/sis/util/Numbers.java          |   2 -
 .../apache/sis/util/collection/WeakHashSet.java    |  43 ++++++---
 .../sis/util/internal/UnmodifiableArrayList.java   |  17 +++-
 .../main/org/apache/sis/util/internal/Unsafe.java  | 106 +++++++++++++++++++++
 .../main/org/apache/sis/util/internal/X364.java    |   2 -
 .../apache/sis/gui/controls/SyncWindowList.java    |   2 +-
 .../apache/sis/gui/controls/ValueColorMapper.java  |   1 +
 .../apache/sis/gui/coverage/CoverageCanvas.java    |   1 +
 .../apache/sis/gui/coverage/CoverageControls.java  |   6 +-
 .../apache/sis/gui/coverage/CoverageExplorer.java  |   2 +
 .../apache/sis/gui/coverage/CoverageStyling.java   |   1 -
 .../org/apache/sis/gui/coverage/GridViewSkin.java  |   1 -
 .../apache/sis/gui/coverage/IsolineRenderer.java   |   1 -
 .../org/apache/sis/gui/internal/PropertyView.java  |   1 -
 .../main/org/apache/sis/gui/map/MapCanvas.java     |  14 ++-
 .../main/org/apache/sis/gui/map/MapCanvasAWT.java  |   1 +
 .../org/apache/sis/gui/metadata/MetadataTree.java  |   4 +-
 .../sis/gui/metadata/StandardMetadataTree.java     |   1 -
 .../org/apache/sis/gui/referencing/WKTPane.java    |   1 -
 53 files changed, 278 insertions(+), 100 deletions(-)

diff --git 
a/buildSrc/src/main/java/org/apache/sis/buildtools/coding/ReorganizeImports.java
 
b/buildSrc/src/main/java/org/apache/sis/buildtools/coding/ReorganizeImports.java
index 6475b372ff..d532b752e1 100644
--- 
a/buildSrc/src/main/java/org/apache/sis/buildtools/coding/ReorganizeImports.java
+++ 
b/buildSrc/src/main/java/org/apache/sis/buildtools/coding/ReorganizeImports.java
@@ -197,7 +197,6 @@ public final class ReorganizeImports extends 
SimpleFileVisitor<Path> {
      * @param  upstream  the branch which is merged in this branch.
      * @throws IOException if an error occurred while reading a file.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     private ReorganizeImports(final Path root, final ReorganizeImports 
upstream) throws IOException {
         this.root = root;
         if (upstream == null) {
@@ -619,11 +618,11 @@ public final class ReorganizeImports extends 
SimpleFileVisitor<Path> {
      * @throws IOException if an error occurred while writing a file.
      */
     private void rewrite(final String[] branchNames) throws IOException {
-        final Integer bitmask = (1 << branchNames.length) - 1;
+        final Integer allBranches = (1 << branchNames.length) - 1;
         final var lines = new ArrayList<String>();
         for (final Map.Entry<Path,Source> entry : sources.entrySet()) {
             final Path relative = entry.getKey();
-            entry.getValue().writeTo(lines, branchNames, 
branchesOfFiles.getOrDefault(relative, bitmask));
+            entry.getValue().writeTo(lines, branchNames, 
branchesOfFiles.getOrDefault(relative, allBranches));
             lines.replaceAll(ReorganizeImports::removeExtraneousSpaces);
             Files.write(root.resolve(relative), lines, 
StandardOpenOption.WRITE, StandardOpenOption.TRUNCATE_EXISTING);
             lines.clear();
diff --git 
a/endorsed/src/org.apache.sis.console/main/org/apache/sis/console/SIS.java 
b/endorsed/src/org.apache.sis.console/main/org/apache/sis/console/SIS.java
index 4e01778691..d9d333fb90 100644
--- a/endorsed/src/org.apache.sis.console/main/org/apache/sis/console/SIS.java
+++ b/endorsed/src/org.apache.sis.console/main/org/apache/sis/console/SIS.java
@@ -86,7 +86,7 @@ public final class SIS extends Static {
          * @param  value  value for the specified option.
          * @return the builder on which to perform chained method calls.
          */
-        @SuppressWarnings({"unchecked", "null"})
+        @SuppressWarnings("unchecked")
         final C set(final Option key, Object value) {
             if (key.hasValue && (value = trim(value)) == null) {
                 final String option = key.label();
diff --git 
a/endorsed/src/org.apache.sis.feature/main/org/apache/sis/feature/DefaultAttributeType.java
 
b/endorsed/src/org.apache.sis.feature/main/org/apache/sis/feature/DefaultAttributeType.java
index 3aebef67ff..619ed2cdb9 100644
--- 
a/endorsed/src/org.apache.sis.feature/main/org/apache/sis/feature/DefaultAttributeType.java
+++ 
b/endorsed/src/org.apache.sis.feature/main/org/apache/sis/feature/DefaultAttributeType.java
@@ -183,7 +183,7 @@ public class DefaultAttributeType<V> extends FieldType 
implements AttributeType<
      *
      * @see org.apache.sis.feature.builder.AttributeTypeBuilder
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")    // Okay because 
used only in package-private class.
+    @SuppressWarnings("this-escape")        // Okay because used only in 
package-private class.
     public DefaultAttributeType(final Map<String,?> identification, final 
Class<V> valueClass,
             final int minimumOccurs, final int maximumOccurs, final V 
defaultValue,
             final AttributeType<?>... characterizedBy)
diff --git 
a/endorsed/src/org.apache.sis.feature/main/org/apache/sis/feature/DefaultFeatureType.java
 
b/endorsed/src/org.apache.sis.feature/main/org/apache/sis/feature/DefaultFeatureType.java
index fa49c05e76..dd68969bbb 100644
--- 
a/endorsed/src/org.apache.sis.feature/main/org/apache/sis/feature/DefaultFeatureType.java
+++ 
b/endorsed/src/org.apache.sis.feature/main/org/apache/sis/feature/DefaultFeatureType.java
@@ -257,7 +257,7 @@ public class DefaultFeatureType extends 
AbstractIdentifiedType implements Featur
      *
      * @see org.apache.sis.feature.builder.FeatureTypeBuilder
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
+    @SuppressWarnings("this-escape")
     public DefaultFeatureType(final Map<String,?> identification, final 
boolean isAbstract,
             final FeatureType[] superTypes, final PropertyType... properties)
     {
diff --git 
a/endorsed/src/org.apache.sis.feature/main/org/apache/sis/image/ComputedTiles.java
 
b/endorsed/src/org.apache.sis.feature/main/org/apache/sis/image/ComputedTiles.java
index 3f8405530c..82778d97e1 100644
--- 
a/endorsed/src/org.apache.sis.feature/main/org/apache/sis/image/ComputedTiles.java
+++ 
b/endorsed/src/org.apache.sis.feature/main/org/apache/sis/image/ComputedTiles.java
@@ -82,7 +82,6 @@ final class ComputedTiles extends 
WeakReference<ComputedImage> implements Dispos
      * @param  image  the image for which to release tiles on 
garbage-collection.
      * @param  ws     sources to observe for changes, or {@code null} if none.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     ComputedTiles(final ComputedImage image, final WritableRenderedImage[] ws) 
{
         super(image, ReferenceQueueConsumer.QUEUE);
         cachedTiles = new HashMap<>();
diff --git 
a/endorsed/src/org.apache.sis.feature/main/org/apache/sis/index/tree/NodeIterator.java
 
b/endorsed/src/org.apache.sis.feature/main/org/apache/sis/index/tree/NodeIterator.java
index a190d1ccde..32b17fdc50 100644
--- 
a/endorsed/src/org.apache.sis.feature/main/org/apache/sis/index/tree/NodeIterator.java
+++ 
b/endorsed/src/org.apache.sis.feature/main/org/apache/sis/index/tree/NodeIterator.java
@@ -94,7 +94,6 @@ class NodeIterator<E> implements Spliterator<E>, Cloneable {
      * Creates a new iterator for the specified search region.
      * If the given region is null, then infinite bounds are assumed.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     NodeIterator(final PointTree<E> tree, final Envelope searchRegion) {
         final int n = tree.getDimension();
         bitmask = Numerics.bitmask(1 << n) - 1;
diff --git 
a/endorsed/src/org.apache.sis.feature/test/org/apache/sis/image/processing/isoline/StepsViewer.java
 
b/endorsed/src/org.apache.sis.feature/test/org/apache/sis/image/processing/isoline/StepsViewer.java
index a47d255ecd..a81b277f74 100644
--- 
a/endorsed/src/org.apache.sis.feature/test/org/apache/sis/image/processing/isoline/StepsViewer.java
+++ 
b/endorsed/src/org.apache.sis.feature/test/org/apache/sis/image/processing/isoline/StepsViewer.java
@@ -154,7 +154,6 @@ public final class StepsViewer extends JComponent 
implements BiConsumer<String,I
      * @param  data  the source of data for isolines.
      * @param  pane  the container where to add components.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     private StepsViewer(final RenderedImage data, final Container pane) {
         isolines    = new EnumMap<>(PolylineStage.class);
         stageColors = new Color[] {Color.YELLOW, Color.PINK, Color.BLUE};
diff --git 
a/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/metadata/PropertyAccessor.java
 
b/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/metadata/PropertyAccessor.java
index 5fd1314881..ebff2363fe 100644
--- 
a/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/metadata/PropertyAccessor.java
+++ 
b/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/metadata/PropertyAccessor.java
@@ -41,11 +41,12 @@ import org.apache.sis.util.ObjectConverters;
 import org.apache.sis.util.UnconvertibleObjectException;
 import org.apache.sis.util.internal.CollectionsExt;
 import org.apache.sis.util.internal.Numerics;
-import org.apache.sis.measure.ValueRange;
+import org.apache.sis.util.internal.Unsafe;
 import org.apache.sis.util.collection.CheckedContainer;
 import org.apache.sis.util.collection.BackingStoreException;
 import org.apache.sis.util.resources.Errors;
 import org.apache.sis.xml.IdentifiedObject;
+import org.apache.sis.measure.ValueRange;
 import static org.apache.sis.metadata.PropertyComparator.*;
 import static org.apache.sis.metadata.ValueExistencePolicy.isNullOrEmpty;
 import static org.apache.sis.util.internal.CollectionsExt.snapshot;
@@ -232,6 +233,7 @@ class PropertyAccessor {
      * @param  standardImpl    the implementation specified by the {@link 
MetadataStandard}, or {@code null} if none.
      *                         This is the same as {@code implementation} 
unless a custom implementation is used.
      */
+    @SuppressWarnings("LocalVariableHidesMemberVariable")
     PropertyAccessor(final Class<?> type, final Class<?> implementation, final 
Class<?> standardImpl) {
         assert type.isAssignableFrom(implementation) : implementation;
         this.type           = type;
@@ -499,6 +501,7 @@ class PropertyAccessor {
      * @return the index of the given name, or -1 if none and {@code 
mandatory} is {@code false}.
      * @throws IllegalArgumentException if the name is not found and {@code 
mandatory} is {@code true}.
      */
+    @SuppressWarnings("StringEquality")
     final int indexOf(final String name, final boolean mandatory) {
         Integer index = mapping.get(name);
         if (index == null) {
@@ -508,7 +511,7 @@ class PropertyAccessor {
              * directly the given String instance allow usage of its cached 
hash code value.
              */
             final String key = CharSequences.replace(name, " ", 
"").toString().toLowerCase(Locale.ROOT).strip();
-            if (key == name || (index = mapping.get(key)) == null) { // 
Identity comparison is okay here.
+            if (key == name || (index = mapping.get(key)) == null) {        // 
Identity comparison is okay here.
                 if (!mandatory) {
                     return -1;
                 }
@@ -622,8 +625,8 @@ class PropertyAccessor {
      */
     final boolean isCollectionOrMap(final int index) {
         if (index >= 0 && index < allCount) {
-            final Class<?> type = getters[index].getReturnType();
-            return Collection.class.isAssignableFrom(type) || 
Map.class.isAssignableFrom(type);
+            final Class<?> pt = getters[index].getReturnType();
+            return Collection.class.isAssignableFrom(pt) || 
Map.class.isAssignableFrom(pt);
         }
         return false;
     }
@@ -657,6 +660,7 @@ class PropertyAccessor {
      */
     @SuppressWarnings({"unchecked","rawtypes"})
     final synchronized ExtendedElementInformation information(final Citation 
standard, final int index) {
+        @SuppressWarnings("LocalVariableHidesMemberVariable")
         ExtendedElementInformation[] informations = this.informations;
         if (informations == null) {
             this.informations = informations = new 
PropertyInformation<?>[standardCount];
@@ -1065,8 +1069,7 @@ class PropertyAccessor {
                  * runtime. However, other implementations could use unchecked 
collection.
                  * There is not much we can do...
                  */
-                // No @SuppressWarnings because this is a real hole.
-                changed = ((Collection) addTo).addAll(elementList);
+                changed = Unsafe.addAll(addTo, elementList);
             }
         }
         /*
@@ -1090,14 +1093,14 @@ class PropertyAccessor {
     @SuppressWarnings({"unchecked","rawtypes"})
     private void convert(final Object[] elements, final Class<?> targetType) 
throws ClassCastException {
         boolean hasNewConverter = false;
-        ObjectConverter<?,?> converter = null;
+        ObjectConverter converter = null;               // Intentionally raw 
type. Checks are done below.
         for (int i=0; i<elements.length; i++) {
             final Object value = elements[i];
             if (value != null) {
                 final Class<?> sourceType = value.getClass();
                 if (!targetType.isAssignableFrom(sourceType)) try {
                     if (converter == null) {
-                        converter = lastConverter;              // Volatile 
field - read only if needed.
+                        converter = lastConverter;      // Volatile field - 
read only if needed.
                     }
                     /*
                      * Require the exact same classes, not parent or subclass,
@@ -1109,7 +1112,7 @@ class PropertyAccessor {
                         converter = ObjectConverters.find(sourceType, 
targetType);
                         hasNewConverter = true;
                     }
-                    elements[i] = ((ObjectConverter) converter).apply(value);
+                    elements[i] = converter.apply(value);
                 } catch (UnconvertibleObjectException cause) {
                     throw (ClassCastException) new 
ClassCastException(Errors.format(
                             Errors.Keys.IllegalClass_2, targetType, 
sourceType)).initCause(cause);
@@ -1117,7 +1120,7 @@ class PropertyAccessor {
             }
         }
         if (hasNewConverter) {
-            lastConverter = converter;                          // Volatile 
field - store only if needed.
+            lastConverter = converter;          // Volatile field - store only 
if needed.
         }
     }
 
diff --git 
a/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/metadata/TreeNode.java
 
b/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/metadata/TreeNode.java
index 66625ac9cb..54e6450b54 100644
--- 
a/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/metadata/TreeNode.java
+++ 
b/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/metadata/TreeNode.java
@@ -34,6 +34,7 @@ import org.apache.sis.util.CharSequences;
 import org.apache.sis.util.ArgumentChecks;
 import org.apache.sis.util.ObjectConverters;
 import org.apache.sis.util.internal.CollectionsExt;
+import org.apache.sis.util.internal.Unsafe;
 import org.apache.sis.util.iso.Types;
 import org.apache.sis.util.collection.TableColumn;
 import org.apache.sis.util.collection.TreeTable.Node;
@@ -735,8 +736,7 @@ class TreeNode implements Node {
                  * runtime. However, other implementations could use unchecked 
collection. We have
                  * done our best for converting the type above, there is not 
much more we can do...
                  */
-                // No @SuppressWarnings because this is a real hole.
-                ((List) values).set(indexInList, value);
+                Unsafe.set((List<?>) values, indexInList, value);
             } catch (IndexOutOfBoundsException e) {
                 // Same rational as in the getUserObject() method.
                 throw new ConcurrentModificationException(e);
@@ -973,6 +973,7 @@ class TreeNode implements Node {
      */
     private TreeNodeChildren getCompactChildren() {
         if (table.valuePolicy == ValueExistencePolicy.COMPACT) {
+            @SuppressWarnings("LocalVariableHidesMemberVariable")
             final Collection<Node> children = getChildren();
             if (children instanceof TreeNodeChildren) {
                 return (TreeNodeChildren) children;
@@ -1000,6 +1001,7 @@ class TreeNode implements Node {
             }
             value = name;
         } else if (column == TableColumn.TYPE) {
+            @SuppressWarnings("LocalVariableHidesMemberVariable")
             final TreeNodeChildren children = getCompactChildren();
             if (children == null || (value = children.getParentType()) == 
null) {
                 value = baseType;
@@ -1008,6 +1010,7 @@ class TreeNode implements Node {
             if (isLeaf()) {
                 value = getNonNilValue();
             } else {
+                @SuppressWarnings("LocalVariableHidesMemberVariable")
                 final TreeNodeChildren children = getCompactChildren();
                 if (children != null) {
                     value = children.getParentTitle();
@@ -1037,6 +1040,7 @@ class TreeNode implements Node {
         ArgumentChecks.ensureNonNull("column", column);
         if (column == TableColumn.VALUE) {
             ArgumentChecks.ensureNonNull("value", value);                      
 // See javadoc.
+            @SuppressWarnings("LocalVariableHidesMemberVariable")
             final TreeNodeChildren children = getCompactChildren();
             if (children == null || !(children.setParentTitle(value))) {
                 setUserObject(value);
diff --git 
a/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/metadata/internal/Merger.java
 
b/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/metadata/internal/Merger.java
index dc4f5091f8..811da3f7b0 100644
--- 
a/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/metadata/internal/Merger.java
+++ 
b/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/metadata/internal/Merger.java
@@ -31,6 +31,7 @@ import org.apache.sis.metadata.KeyNamePolicy;
 import org.apache.sis.metadata.ValueExistencePolicy;
 import org.apache.sis.util.CorruptedObjectException;
 import org.apache.sis.util.Classes;
+import org.apache.sis.util.internal.Unsafe;
 import org.apache.sis.util.resources.Errors;
 
 
@@ -181,7 +182,8 @@ public class Merger {
                                                : 
targetMap.putIfAbsent(propertyName, sourceValue);
             if (targetValue != null) {
                 if (targetValue instanceof ModifiableMetadata) {
-                    success = copy(sourceValue, (ModifiableMetadata) 
targetValue, dryRun);
+                    final var md = (ModifiableMetadata) targetValue;
+                    success = copy(sourceValue, md, dryRun);
                     if (!success) {
                         /*
                          * This exception may happen if the source is a 
subclass of the target. This is the converse
@@ -192,8 +194,7 @@ public class Merger {
                          */
                         if (dryRun) break;
                         throw new 
InvalidMetadataException(errors().getString(Errors.Keys.IllegalPropertyValueClass_3,
-                                name(target, propertyName), 
((ModifiableMetadata) targetValue).getInterface(),
-                                Classes.getClass(sourceValue)));
+                                    name(target, propertyName), 
md.getInterface(), Classes.getClass(sourceValue)));
                     }
                 } else if (targetValue instanceof Collection<?>) {
                     /*
@@ -315,11 +316,11 @@ distribute:                 while (it.hasNext()) {
                     }
                 } else {
                     /*
-                     * No @SuppressWarnings("unchecked") because this is 
really unchecked. However, since the two maps
-                     * have been fetched by calls to the same getter method on 
two org.apache.sis.metadata.iso objects,
-                     * the types should.
+                     * The two maps have been fetched by calls to the same 
getter method on the two metadata objects,
+                     * so they should have the same types declared by the 
method signature. However we cannot be sure
+                     * that the user didn't override the method with 
specialized types.
                      */
-                    ((Map) target).merge(pe.getKey(), newValue, this);
+                    Unsafe.merge(target, pe.getKey(), newValue, this);
                 }
             }
             return true;
diff --git 
a/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/xml/bind/Context.java
 
b/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/xml/bind/Context.java
index ac612f701f..d7208fc157 100644
--- 
a/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/xml/bind/Context.java
+++ 
b/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/xml/bind/Context.java
@@ -284,7 +284,6 @@ public final class Context extends MarshalContext {
      * @param  converter        the converter in use.
      * @param  logFilter        the object to inform about warnings.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     public Context(int                       bitMasks,
                    final MarshallerPool      pool,
                    final Locale              locale,
diff --git 
a/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/xml/bind/lan/LocaleAndCharset.java
 
b/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/xml/bind/lan/LocaleAndCharset.java
index 6a48a60757..5cbea92b82 100644
--- 
a/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/xml/bind/lan/LocaleAndCharset.java
+++ 
b/endorsed/src/org.apache.sis.metadata/main/org/apache/sis/xml/bind/lan/LocaleAndCharset.java
@@ -27,6 +27,7 @@ import java.util.Iterator;
 import java.nio.charset.Charset;
 import org.apache.sis.util.ArgumentChecks;
 import org.apache.sis.util.internal.Bag;
+import org.apache.sis.util.internal.Unsafe;
 import org.apache.sis.util.internal.CollectionsExt;
 import org.apache.sis.util.collection.TableColumn;
 import org.apache.sis.util.collection.TreeTable.Node;
@@ -225,11 +226,11 @@ public final class LocaleAndCharset implements Node {
         @Override public <V> void setValue(final TableColumn<V> column, V 
value) {
             if (TableColumn.VALUE.equals(column)) {
                 /*
-                 * No @SuppressWarning("unchecked") because following is a 
real hole.
-                 * We rely on Entry.setValue(Object) implementation to perform 
checks
-                 * (this is the case with SIS implementation backed by 
PropertyAccessor).
+                 * We rely on Entry.setValue(Object) implementation to perform 
type checks.
+                 * This is the case with SIS implementation backed by 
PropertyAccessor,
+                 * but we cannot guarantee that this is the case with 
user-provided map.
                  */
-                ((Map.Entry<?,V>) node.getUserObject()).setValue(value);
+                Unsafe.setValue((Map.Entry<?,?>) node.getUserObject(), value);
             } else {
                 node.setValue(column, value);
             }
diff --git 
a/endorsed/src/org.apache.sis.metadata/test/org/apache/sis/metadata/iso/MarshallingTest.java
 
b/endorsed/src/org.apache.sis.metadata/test/org/apache/sis/metadata/iso/MarshallingTest.java
index 104794c77f..03db6339a1 100644
--- 
a/endorsed/src/org.apache.sis.metadata/test/org/apache/sis/metadata/iso/MarshallingTest.java
+++ 
b/endorsed/src/org.apache.sis.metadata/test/org/apache/sis/metadata/iso/MarshallingTest.java
@@ -105,7 +105,6 @@ public final class MarshallingTest extends TestUsingFile 
implements Filter {
      *
      * @throws JAXBException if an error occurred while preparing the 
marshaller.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     public MarshallingTest() throws JAXBException {
         output     = new StringWriter();
         pool       = getMarshallerPool();
diff --git 
a/endorsed/src/org.apache.sis.profile.japan/main/org/apache/sis/profile/japan/netcdf/FactoryForUCAR.java
 
b/endorsed/src/org.apache.sis.profile.japan/main/org/apache/sis/profile/japan/netcdf/FactoryForUCAR.java
index e137255210..5a6b01eeda 100644
--- 
a/endorsed/src/org.apache.sis.profile.japan/main/org/apache/sis/profile/japan/netcdf/FactoryForUCAR.java
+++ 
b/endorsed/src/org.apache.sis.profile.japan/main/org/apache/sis/profile/japan/netcdf/FactoryForUCAR.java
@@ -74,6 +74,7 @@ public final class FactoryForUCAR implements 
CoordSystemBuilderFactory {
      * @return the coordinate system builder for the given dataset.
      */
     @Override
+    @SuppressWarnings("rawtypes")
     public CoordSystemBuilder open(NetcdfDataset.Builder dsb) {         // 
TODO: add <?> with UCAR netCDF 6.
         return new CSBuilder(dsb);
     }
@@ -107,6 +108,7 @@ public final class FactoryForUCAR implements 
CoordSystemBuilderFactory {
          * Only called for variables already identified as Coordinate Axes.
          */
         @Override
+        @SuppressWarnings("rawtypes")
         protected AxisType getAxisType(final VariableDS.Builder variable) {    
   // TODO: add <?> with UCAR netCDF 6.
             final AxisType type = super.getAxisType(variable);
             if (type == null) {
diff --git 
a/endorsed/src/org.apache.sis.referencing.gazetteer/main/org/apache/sis/referencing/gazetteer/FinalLocationType.java
 
b/endorsed/src/org.apache.sis.referencing.gazetteer/main/org/apache/sis/referencing/gazetteer/FinalLocationType.java
index 44e799fcfd..17b9f10eb7 100644
--- 
a/endorsed/src/org.apache.sis.referencing.gazetteer/main/org/apache/sis/referencing/gazetteer/FinalLocationType.java
+++ 
b/endorsed/src/org.apache.sis.referencing.gazetteer/main/org/apache/sis/referencing/gazetteer/FinalLocationType.java
@@ -112,7 +112,7 @@ final class FinalLocationType extends AbstractLocationType 
implements Serializab
      * @param rs        the reference system that comprises this location type.
      * @param existing  other {@code FinalLocationType} instances created 
before this one.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
+    @SuppressWarnings("LocalVariableHidesMemberVariable")
     private FinalLocationType(final LocationType source, final 
ReferenceSystemUsingIdentifiers rs,
             final Map<LocationType, FinalLocationType> existing)
     {
@@ -216,7 +216,9 @@ final class FinalLocationType extends AbstractLocationType 
implements Serializab
     private static <T> T unmodifiable(final Class<T> type, T metadata) {
         if (metadata instanceof ModifiableMetadata) {
             metadata = MetadataCopier.forModifiable(((ModifiableMetadata) 
metadata).getStandard()).copy(type, metadata);
-            ((ModifiableMetadata) 
metadata).transitionTo(ModifiableMetadata.State.FINAL);
+            if (metadata instanceof ModifiableMetadata) {
+                ((ModifiableMetadata) 
metadata).transitionTo(ModifiableMetadata.State.FINAL);
+            }
         }
         return metadata;
     }
diff --git 
a/endorsed/src/org.apache.sis.referencing.gazetteer/main/org/apache/sis/referencing/gazetteer/LocationFormat.java
 
b/endorsed/src/org.apache.sis.referencing.gazetteer/main/org/apache/sis/referencing/gazetteer/LocationFormat.java
index fd42702ca6..3cccc4f551 100644
--- 
a/endorsed/src/org.apache.sis.referencing.gazetteer/main/org/apache/sis/referencing/gazetteer/LocationFormat.java
+++ 
b/endorsed/src/org.apache.sis.referencing.gazetteer/main/org/apache/sis/referencing/gazetteer/LocationFormat.java
@@ -201,7 +201,7 @@ public class LocationFormat extends TabularFormat<Location> 
{
      * @throws IOException if an error occurred while writing to the given 
appendable.
      */
     @Override
-    @SuppressWarnings({"fallthrough", "null"})
+    @SuppressWarnings("fallthrough")
     public void format(final Location location, final Appendable toAppendTo) 
throws IOException {
         ArgumentChecks.ensureNonNull("location", location);
         final Locale locale = getLocale(Locale.Category.DISPLAY);
diff --git 
a/endorsed/src/org.apache.sis.referencing.gazetteer/main/org/apache/sis/referencing/gazetteer/ReferencingByIdentifiers.java
 
b/endorsed/src/org.apache.sis.referencing.gazetteer/main/org/apache/sis/referencing/gazetteer/ReferencingByIdentifiers.java
index 54b83c5af2..ea366663cc 100644
--- 
a/endorsed/src/org.apache.sis.referencing.gazetteer/main/org/apache/sis/referencing/gazetteer/ReferencingByIdentifiers.java
+++ 
b/endorsed/src/org.apache.sis.referencing.gazetteer/main/org/apache/sis/referencing/gazetteer/ReferencingByIdentifiers.java
@@ -172,7 +172,7 @@ public abstract class ReferencingByIdentifiers extends 
AbstractReferenceSystem i
      * @param properties  the properties to be given to the reference system.
      * @param types       description of location type(s) in the spatial 
reference system.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
+    @SuppressWarnings("this-escape")
     public ReferencingByIdentifiers(final Map<String,?> properties, final 
LocationType... types) {
         super(properties);
         theme = Types.toInternationalString(properties, THEME_KEY);
diff --git 
a/endorsed/src/org.apache.sis.referencing/main/org/apache/sis/geometry/WraparoundInEnvelope.java
 
b/endorsed/src/org.apache.sis.referencing/main/org/apache/sis/geometry/WraparoundInEnvelope.java
index 5e7dc58e1f..bfff4b5f29 100644
--- 
a/endorsed/src/org.apache.sis.referencing/main/org/apache/sis/geometry/WraparoundInEnvelope.java
+++ 
b/endorsed/src/org.apache.sis.referencing/main/org/apache/sis/geometry/WraparoundInEnvelope.java
@@ -180,7 +180,6 @@ final class WraparoundInEnvelope extends 
WraparoundTransform {
          * Creates a new instance using the given transform. If the given 
transform contains wraparound steps,
          * then the transform stored in the {@link #transform} will be a 
different transform chains instance.
          */
-        @SuppressWarnings("ThisEscapedInObjectConstruction")
         Controller(final MathTransform transform) {
             this.transform = replace(transform, this);
         }
diff --git 
a/endorsed/src/org.apache.sis.referencing/main/org/apache/sis/referencing/operation/transform/ConcatenatedTransform.java
 
b/endorsed/src/org.apache.sis.referencing/main/org/apache/sis/referencing/operation/transform/ConcatenatedTransform.java
index a867caf80a..7fe7306481 100644
--- 
a/endorsed/src/org.apache.sis.referencing/main/org/apache/sis/referencing/operation/transform/ConcatenatedTransform.java
+++ 
b/endorsed/src/org.apache.sis.referencing/main/org/apache/sis/referencing/operation/transform/ConcatenatedTransform.java
@@ -209,6 +209,7 @@ class ConcatenatedTransform extends AbstractMathTransform 
implements Serializabl
         boolean inverseCaseTested = false;
         if (tr1 instanceof AbstractMathTransform) {
             // TODO: after removal of the deprecated method, invoke 
`tryConcatenate(Joiner)` only once.
+            @SuppressWarnings("removal")
             final MathTransform optimized = ((AbstractMathTransform) 
tr1).tryConcatenate(false, tr2, factory);
             inverseCaseTested = true;
             if (optimized != null) {
@@ -217,6 +218,7 @@ class ConcatenatedTransform extends AbstractMathTransform 
implements Serializabl
             }
         }
         if (tr2 instanceof AbstractMathTransform) {
+            @SuppressWarnings("removal")
             final MathTransform optimized = ((AbstractMathTransform) 
tr2).tryConcatenate(true, tr1, factory);
             inverseCaseTested = true;
             if (optimized != null) {
diff --git 
a/endorsed/src/org.apache.sis.storage.geotiff/main/org/apache/sis/storage/geotiff/DataSubset.java
 
b/endorsed/src/org.apache.sis.storage.geotiff/main/org/apache/sis/storage/geotiff/DataSubset.java
index 5533d9d3af..401c0eb3f4 100644
--- 
a/endorsed/src/org.apache.sis.storage.geotiff/main/org/apache/sis/storage/geotiff/DataSubset.java
+++ 
b/endorsed/src/org.apache.sis.storage.geotiff/main/org/apache/sis/storage/geotiff/DataSubset.java
@@ -323,6 +323,7 @@ class DataSubset extends TiledGridCoverage implements 
Localized {
      *         (too many exception types to list them all).
      */
     @Override
+    @SuppressWarnings("try")
     protected final Raster[] readTiles(final AOI iterator) throws IOException, 
DataStoreException {
         /*
          * Prepare an array for all tiles to be returned. Tiles that are 
already in memory will be stored
diff --git 
a/endorsed/src/org.apache.sis.storage.geotiff/main/org/apache/sis/storage/geotiff/ImageFileDirectory.java
 
b/endorsed/src/org.apache.sis.storage.geotiff/main/org/apache/sis/storage/geotiff/ImageFileDirectory.java
index 00b0b9b3e8..67ce259321 100644
--- 
a/endorsed/src/org.apache.sis.storage.geotiff/main/org/apache/sis/storage/geotiff/ImageFileDirectory.java
+++ 
b/endorsed/src/org.apache.sis.storage.geotiff/main/org/apache/sis/storage/geotiff/ImageFileDirectory.java
@@ -960,13 +960,10 @@ final class ImageFileDirectory extends DataCube {
              */
             case TAG_PAGE_NUMBER: {
                 final Vector v = type.readAsVector(input(), count);
-                int p = 0, n = 0;
-                switch (v.size()) {
-                    default: n = v.intValue(1);     // Fall through
-                    case 1:  p = v.intValue(0);
-                    case 0:  break;
+                final int n = v.size();
+                if (n >= 1) {
+                    metadata.addPage(v.intValue(0), (n >= 2) ? v.intValue(1) : 
0);
                 }
-                metadata.addPage(p, n);
                 break;
             }
             /*
@@ -1369,6 +1366,7 @@ final class ImageFileDirectory extends DataCube {
      */
     @Override
     protected Metadata createMetadata() throws DataStoreException {
+        @SuppressWarnings("LocalVariableHidesMemberVariable")
         final ImageMetadataBuilder metadata = this.metadata;
         if (metadata == null) {
             /*
@@ -1390,6 +1388,7 @@ final class ImageFileDirectory extends DataCube {
          */
         final boolean isIndexValid = !isReducedResolution();
         metadata.newCoverage(isIndexValid && 
reader.store.customizer.isElectromagneticMeasurement(index));
+        @SuppressWarnings("LocalVariableHidesMemberVariable")
         final List<SampleDimension> sampleDimensions = getSampleDimensions();
         for (int band = 0; band < samplesPerPixel; band++) {
             metadata.addNewBand(sampleDimensions.get(band));
@@ -1406,6 +1405,7 @@ final class ImageFileDirectory extends DataCube {
          * Destination: metadata/spatialRepresentationInfo and others.
          */
         if (referencing != null) {
+            @SuppressWarnings("LocalVariableHidesMemberVariable")
             final GridGeometry gridGeometry = getGridGeometry();
             if (gridGeometry.isDefined(GridGeometry.ENVELOPE)) {
                 metadata.addExtent(gridGeometry.getEnvelope(), listeners);
diff --git 
a/endorsed/src/org.apache.sis.storage.geotiff/main/org/apache/sis/storage/geotiff/writer/TileMatrix.java
 
b/endorsed/src/org.apache.sis.storage.geotiff/main/org/apache/sis/storage/geotiff/writer/TileMatrix.java
index 48d2f83dc6..15c332f334 100644
--- 
a/endorsed/src/org.apache.sis.storage.geotiff/main/org/apache/sis/storage/geotiff/writer/TileMatrix.java
+++ 
b/endorsed/src/org.apache.sis.storage.geotiff/main/org/apache/sis/storage/geotiff/writer/TileMatrix.java
@@ -190,7 +190,6 @@ public final class TileMatrix {
      * @throws DataStoreException if the compression method is unsupported.
      * @throws IOException if an error occurred while writing to the given 
output.
      */
-    @SuppressWarnings("null")
     public void writeRasters(final ChannelDataOutput output) throws 
DataStoreException, IOException {
         ChannelDataOutput compOutput  = null;
         PixelChannel      compressor  = null;
diff --git 
a/endorsed/src/org.apache.sis.storage.netcdf/main/org/apache/sis/storage/netcdf/ucar/DecoderWrapper.java
 
b/endorsed/src/org.apache.sis.storage.netcdf/main/org/apache/sis/storage/netcdf/ucar/DecoderWrapper.java
index c72c220c55..d64e8e6023 100644
--- 
a/endorsed/src/org.apache.sis.storage.netcdf/main/org/apache/sis/storage/netcdf/ucar/DecoderWrapper.java
+++ 
b/endorsed/src/org.apache.sis.storage.netcdf/main/org/apache/sis/storage/netcdf/ucar/DecoderWrapper.java
@@ -132,7 +132,6 @@ public final class DecoderWrapper extends Decoder 
implements CancelTask {
      * @param  listeners  where to send the warnings.
      * @throws IOException if an error occurred while opening the netCDF file.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     public DecoderWrapper(final String filename, final GeometryLibrary 
geomlib, final StoreListeners listeners)
             throws IOException
     {
@@ -394,7 +393,7 @@ public final class DecoderWrapper extends Decoder 
implements CancelTask {
      * @return all variables, or an empty array if none.
      */
     @Override
-    @SuppressWarnings({"ReturnOfCollectionOrArrayField", "null"})
+    @SuppressWarnings("ReturnOfCollectionOrArrayField")
     public Variable[] getVariables() {
         if (variables == null) {
             final List<? extends ucar.nc2.Variable> all = file.getVariables();
@@ -448,6 +447,7 @@ public final class DecoderWrapper extends Decoder 
implements CancelTask {
      */
     @Override
     public DiscreteSampling[] getDiscreteSampling(final DataStore lock) throws 
IOException, DataStoreException {
+        @SuppressWarnings("LocalVariableHidesMemberVariable")
         final FeatureDataset features = getFeatureDataSet();
         if (features instanceof FeatureDatasetPoint) {
             final List<DsgFeatureCollection> fc = ((FeatureDatasetPoint) 
features).getPointFeatureCollectionList();
diff --git 
a/endorsed/src/org.apache.sis.storage.sql/main/org/apache/sis/storage/sql/SQLStoreProvider.java
 
b/endorsed/src/org.apache.sis.storage.sql/main/org/apache/sis/storage/sql/SQLStoreProvider.java
index d817f24b67..13c1187536 100644
--- 
a/endorsed/src/org.apache.sis.storage.sql/main/org/apache/sis/storage/sql/SQLStoreProvider.java
+++ 
b/endorsed/src/org.apache.sis.storage.sql/main/org/apache/sis/storage/sql/SQLStoreProvider.java
@@ -106,13 +106,15 @@ public class SQLStoreProvider extends DataStoreProvider {
      *
      * @since 1.1
      */
-    public static final ParameterDescriptor<Map> QUERIES_PARAM;
+    public static final ParameterDescriptor<Map<?,?>> QUERIES_PARAM;
 
     /**
      * The parameter descriptor to be returned by {@link #getOpenParameters()}.
      */
     private static final ParameterDescriptorGroup OPEN_DESCRIPTOR;
     static {
+        @SuppressWarnings("unchecked")
+        final Class<Map<?,?>> map = (Class) Map.class;
         final ParameterBuilder builder = new ParameterBuilder();
         SOURCE_PARAM = builder.addName(LOCATION).setRequired(true)
                               
.setDescription(Resources.formatInternational(Resources.Keys.DataSource))
@@ -122,7 +124,7 @@ public class SQLStoreProvider extends DataStoreProvider {
                               .create(GenericName[].class, null);
         QUERIES_PARAM = builder.addName(QUERIES)
                               
.setDescription(Resources.formatInternational(Resources.Keys.MappedSQLQueries))
-                              .create(Map.class, null);
+                              .create(map, null);
         OPEN_DESCRIPTOR = builder.addName(NAME).createGroup(SOURCE_PARAM, 
TABLES_PARAM, QUERIES_PARAM);
     }
 
@@ -184,6 +186,7 @@ public class SQLStoreProvider extends DataStoreProvider {
      * @throws DataStoreException if an SQL error occurred.
      */
     @Override
+    @SuppressWarnings("try")
     public ProbeResult probeContent(final StorageConnector connector) throws 
DataStoreException {
         final DataSource ds = connector.getStorageAs(DataSource.class);
         if (ds != null) {
diff --git 
a/endorsed/src/org.apache.sis.storage.sql/main/org/apache/sis/storage/sql/feature/FeatureIterator.java
 
b/endorsed/src/org.apache.sis.storage.sql/main/org/apache/sis/storage/sql/feature/FeatureIterator.java
index 83be457a0c..fee6ee9013 100644
--- 
a/endorsed/src/org.apache.sis.storage.sql/main/org/apache/sis/storage/sql/feature/FeatureIterator.java
+++ 
b/endorsed/src/org.apache.sis.storage.sql/main/org/apache/sis/storage/sql/feature/FeatureIterator.java
@@ -322,6 +322,7 @@ final class FeatureIterator implements 
Spliterator<Feature>, AutoCloseable {
      * Closes the (pooled) connection, including the statements of all 
dependencies.
      */
     @Override
+    @SuppressWarnings("try")
     public void close() throws SQLException {
         if (spatialInformation != null) {
             spatialInformation.close();
diff --git 
a/endorsed/src/org.apache.sis.storage.xml/main/org/apache/sis/storage/xml/stream/StaxStreamReader.java
 
b/endorsed/src/org.apache.sis.storage.xml/main/org/apache/sis/storage/xml/stream/StaxStreamReader.java
index ed5157fbdd..0d802ce569 100644
--- 
a/endorsed/src/org.apache.sis.storage.xml/main/org/apache/sis/storage/xml/stream/StaxStreamReader.java
+++ 
b/endorsed/src/org.apache.sis.storage.xml/main/org/apache/sis/storage/xml/stream/StaxStreamReader.java
@@ -133,10 +133,9 @@ public abstract class StaxStreamReader extends 
StaxStreamIO implements XMLStream
      * @throws IOException if an error occurred while preparing the input 
stream.
      * @throws Exception if another kind of error occurred while closing a 
previous stream.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     protected StaxStreamReader(final StaxDataStore owner) throws Exception {
         super(owner);
-        reader = owner.createReader(this);      // Okay because will not store 
the 'this' reference.
+        reader = owner.createReader(this);      // Okay because will not store 
the `this` reference.
     }
 
     /**
diff --git 
a/endorsed/src/org.apache.sis.storage.xml/main/org/apache/sis/storage/xml/stream/StaxStreamWriter.java
 
b/endorsed/src/org.apache.sis.storage.xml/main/org/apache/sis/storage/xml/stream/StaxStreamWriter.java
index d566a73c34..8b1f55a76e 100644
--- 
a/endorsed/src/org.apache.sis.storage.xml/main/org/apache/sis/storage/xml/stream/StaxStreamWriter.java
+++ 
b/endorsed/src/org.apache.sis.storage.xml/main/org/apache/sis/storage/xml/stream/StaxStreamWriter.java
@@ -110,7 +110,6 @@ public abstract class StaxStreamWriter extends StaxStreamIO 
implements Consumer<
      * @throws XMLStreamException if an error occurred while opening the XML 
file.
      * @throws IOException if an error occurred while preparing the output 
stream.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     protected StaxStreamWriter(final StaxDataStore owner, final OutputStream 
temporary)
             throws DataStoreException, XMLStreamException, IOException
     {
diff --git 
a/endorsed/src/org.apache.sis.storage/main/org/apache/sis/storage/StorageConnector.java
 
b/endorsed/src/org.apache.sis.storage/main/org/apache/sis/storage/StorageConnector.java
index 59869cd3ac..8eba8409cc 100644
--- 
a/endorsed/src/org.apache.sis.storage/main/org/apache/sis/storage/StorageConnector.java
+++ 
b/endorsed/src/org.apache.sis.storage/main/org/apache/sis/storage/StorageConnector.java
@@ -1110,6 +1110,7 @@ public class StorageConnector implements Serializable {
          * ChannelDataInput depends on ReadableByteChannel, which itself 
depends on storage
          * (potentially an InputStream). We need to remember this chain in 
`Coupled` objects.
          */
+        @SuppressWarnings("LocalVariableHidesMemberVariable")
         final String name = getStorageName();
         final ReadableByteChannel channel = factory.readable(name, null);
         addView(ReadableByteChannel.class, channel, null, factory.isCoupled() 
? CASCADE_ON_RESET : 0);
@@ -1194,7 +1195,7 @@ public class StorageConnector implements Serializable {
      * @return the byte buffer to use with {@link ChannelDataInput} or {@link 
ChannelDataOutput}.
      */
     private ByteBuffer getChannelBuffer(final ChannelFactory factory) {
-        @SuppressWarnings("deprecated")
+        @SuppressWarnings("deprecation")
         ByteBuffer buffer = getOption(OptionKey.BYTE_BUFFER);               // 
User-supplied buffer.
         if (buffer == null) {
             if (factory.suggestDirectBuffer) {
@@ -1495,6 +1496,7 @@ public class StorageConnector implements Serializable {
          * ChannelDataOutput depends on WritableByteChannel, which itself 
depends on storage
          * (potentially an OutputStream). We need to remember this chain in 
`Coupled` objects.
          */
+        @SuppressWarnings("LocalVariableHidesMemberVariable")
         final String name = getStorageName();
         final WritableByteChannel channel = factory.writable(name, null);
         addView(WritableByteChannel.class, channel, null, factory.isCoupled() 
? CASCADE_ON_RESET : 0);
diff --git 
a/endorsed/src/org.apache.sis.storage/main/org/apache/sis/storage/folder/Store.java
 
b/endorsed/src/org.apache.sis.storage/main/org/apache/sis/storage/folder/Store.java
index f6821a7fd4..ac901eb4b7 100644
--- 
a/endorsed/src/org.apache.sis.storage/main/org/apache/sis/storage/folder/Store.java
+++ 
b/endorsed/src/org.apache.sis.storage/main/org/apache/sis/storage/folder/Store.java
@@ -160,7 +160,6 @@ class Store extends DataStore implements StoreResource, 
UnstructuredAggregate, D
      * @throws DataStoreException if an error occurred while fetching the 
directory {@link Path}.
      * @throws IOException if an error occurred while using the directory 
{@code Path}.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")    // Okay because 
'children' does not escape.
     Store(final DataStoreProvider provider, final StorageConnector connector, 
final Path path, final DataStoreProvider format)
             throws DataStoreException, IOException
     {
@@ -265,6 +264,7 @@ class Store extends DataStore implements StoreResource, 
UnstructuredAggregate, D
                            configuration.getOption(OptionKey.ENCODING),
                            MetadataBuilder.Scope.RESOURCE);
 
+            @SuppressWarnings("LocalVariableHidesMemberVariable")
             final GenericName identifier = identifier(null);
             String name = null;
             if (identifier != null) {
diff --git 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/measure/FormattedCharacterIterator.java
 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/measure/FormattedCharacterIterator.java
index 07585d548a..9cf58b5762 100644
--- 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/measure/FormattedCharacterIterator.java
+++ 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/measure/FormattedCharacterIterator.java
@@ -93,7 +93,6 @@ final class FormattedCharacterIterator extends 
SimpleCharacterIterator implement
          * Creates a new entry for the given value, together with the range of 
index where
          * the field value has been formatted. See class javadoc for more 
information.
          */
-        @SuppressWarnings("ThisEscapedInObjectConstruction")
         Entry(final Attribute field, final Object value, final int start, 
final int limit,
                 final Map<Attribute,Entry> attributes)
         {
@@ -175,9 +174,9 @@ final class FormattedCharacterIterator extends 
SimpleCharacterIterator implement
                 for (final Map.Entry<Attribute,Object> entry : 
it.getAttributes().entrySet()) {
                     final Attribute attribute = entry.getKey();
                     if (it.getRunLimit(attribute) == currentRunLimit) {
-                        final Entry e = new Entry(attribute, entry.getValue(), 
 // Constructeur adds itself to the map.
-                                                  offset + 
it.getRunStart(attribute),
-                                                  offset + currentRunLimit, 
attributes);
+                        var e = new Entry(attribute, entry.getValue(),  // 
Constructeur adds itself to the map.
+                                          offset + it.getRunStart(attribute),
+                                          offset + currentRunLimit, 
attributes);
                     }
                 }
             }
diff --git 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/measure/UnitDimension.java
 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/measure/UnitDimension.java
index 46789f77db..b6afc7861d 100644
--- 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/measure/UnitDimension.java
+++ 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/measure/UnitDimension.java
@@ -90,7 +90,6 @@ final class UnitDimension implements Dimension, Serializable {
      *
      * @param  symbol  the symbol of this base dimension (not to be confused 
with unit symbol).
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")    // Safe because 
this class is final.
     UnitDimension(final char symbol) {
         this.symbol = symbol;
         components  = Map.of(this, new Fraction(1,1).unique());
diff --git 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/measure/UnitFormat.java 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/measure/UnitFormat.java
index 5b3f7f4414..2ed8106ea8 100644
--- 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/measure/UnitFormat.java
+++ 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/measure/UnitFormat.java
@@ -1110,7 +1110,7 @@ appPow: if (unit == null) {
      * @throws MeasurementParseException if a problem occurred while parsing 
the given symbols.
      */
     @Override
-    @SuppressWarnings({"null", "fallthrough"})
+    @SuppressWarnings("fallthrough")
     public Unit<?> parse(CharSequence symbols, final ParsePosition position) 
throws MeasurementParseException {
         ArgumentChecks.ensureNonNull("symbols",  symbols);
         ArgumentChecks.ensureNonNull("position", position);
diff --git 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/system/OptionalDependency.java
 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/system/OptionalDependency.java
index 78164b292f..d4a532de10 100644
--- 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/system/OptionalDependency.java
+++ 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/system/OptionalDependency.java
@@ -43,7 +43,6 @@ public abstract class OptionalDependency extends 
SystemListener {
      * @param module  a constant from the {@link Modules} class which identify 
the module that need the optional dependency.
      * @param dependency  the name of the optional module on which the 
specified {@code module} depends.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     protected OptionalDependency(final String module, final String dependency) 
{
         super(module);
         this.dependency = dependency;
diff --git 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/ConditionallySafe.java
 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/ConditionallySafe.java
new file mode 100644
index 0000000000..70fe7d327a
--- /dev/null
+++ 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/ConditionallySafe.java
@@ -0,0 +1,38 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.sis.util;
+
+import java.lang.annotation.Documented;
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+
+/**
+ * Annotates a code with parameterized types that are safe only under some 
conditions.
+ * The source code of the method typically has a {@code 
@SuppressWarnings("unchecked")}
+ * annotation despite the fact that the warning is not fully resolved. The 
Javadoc shall
+ * document the conditions that are necessary for the method to be safe.
+ *
+ * @author  Martin Desruisseaux (Geomatys)
+ */
+@Documented
+@Retention(RetentionPolicy.SOURCE)
+@Target({ElementType.METHOD, ElementType.LOCAL_VARIABLE})
+public @interface ConditionallySafe {
+}
diff --git 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/Numbers.java 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/Numbers.java
index eb993129d4..32cddf40ca 100644
--- a/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/Numbers.java
+++ b/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/Numbers.java
@@ -109,7 +109,6 @@ public final class Numbers extends Static {
     /**
      * Creates an entry for a type which is not a primitive type.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     private Numbers(final Class<?> type, final boolean isFloat, final boolean 
isInteger, final byte ordinal) {
         primitive = wrapper = type;
         this.isFloat   = isFloat;
@@ -126,7 +125,6 @@ public final class Numbers extends Static {
     /**
      * Creates a mapping between a primitive type and its wrapper.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     private Numbers(final Class<?> primitive, final Class<?> wrapper,
                     final boolean  isFloat,   final boolean  isInteger,
                     final byte     size,      final byte     ordinal,
diff --git 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/collection/WeakHashSet.java
 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/collection/WeakHashSet.java
index 2aa4d8890a..24bb09ba57 100644
--- 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/collection/WeakHashSet.java
+++ 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/collection/WeakHashSet.java
@@ -25,6 +25,7 @@ import org.apache.sis.util.Debug;
 import org.apache.sis.util.ArraysExt;
 import org.apache.sis.util.Utilities;
 import org.apache.sis.util.ArgumentChecks;
+import org.apache.sis.util.ConditionallySafe;
 import static org.apache.sis.util.collection.WeakEntry.*;
 
 
@@ -256,7 +257,7 @@ public class WeakHashSet<E> extends AbstractSet<E> 
implements CheckedContainer<E
     }
 
     /**
-     * Returns an object equals to {@code element} if such an object already 
exist in this
+     * Returns an object equals to {@code element} if such an object already 
exists in this
      * {@code WeakHashSet}. Otherwise, adds {@code element} to this {@code 
WeakHashSet}.
      * This method is functionally equivalents to the following code:
      *
@@ -272,30 +273,47 @@ public class WeakHashSet<E> extends AbstractSet<E> 
implements CheckedContainer<E
      *     return element;
      *     }
      *
-     * @param  <T>      the type of the element to get. Can be {@code null}.
-     * @param  element  the element to get or to add in the set if not already 
presents,
-     *                  or {@code null} if the given element was null.
-     * @return an element equals to the given one if already presents in the 
set,
-     *         or the given {@code object} otherwise.
+     * <h4>Requirement for type safety</h4>
+     * This method is safe only if the given {@code element} implements the 
{@link Object#equals(Object)} method
+     * in such a way that {@code T.equals(x)} can be true only if <var>x</var> 
is an instance of <var>T</var>.
+     * This requirement is true in the common case when the {@code 
equals(Object)} implementation requires that
+     * the two compared objects are of the same class, for example as below:
+     *
+     * {@snippet lang="java" :
+     *     @Override
+     *     public boolean equals(Object obj) {
+     *         if (obj == null || obj.getClass() != getClass()) {
+     *             return false;
+     *         }
+     *         // Do the comparison
+     *     }
+     *
+     * @param  <T>      the type of the element to get.
+     * @param  element  the element to get or to add in the set if not already 
presents. Can be {@code null}.
+     * @return an element equals to the given one if already presents in the 
set, or the given {@code element}
+     *         otherwise. Can be {@code null} if the given element was null.
      */
+    @ConditionallySafe
+    @SuppressWarnings("unchecked")
     public synchronized <T extends E> T unique(final T element) {
         /*
-         * There is no way to make sure that this operation is really safe.
-         * We have to trust the Object.equals(Object) method to be strict
+         * It is difficult to make sure that this operation is really safe.
+         * We have to trust the `Object.equals(Object)` method to be strict
          * about the type of compared objects.
          */
-        return (T) intern(element, INTERN);
+        return (T) intern(element, UNIQUE);
     }
 
     // Arguments for the {@link #intern} method.
     /** The "remove" operation.  */  private static final int REMOVE = -1;
     /** The "get"    operation.  */  private static final int GET    =  0;
     /** The "add"    operation.  */  private static final int ADD    = +1;
-    /** The "intern" operation.  */  private static final int INTERN = +2;
+    /** The "unique" operation.  */  private static final int UNIQUE = +2;
 
     /**
      * Implementation of the {@link #add(Object)}, {@link #remove(Object)}, 
{@link #get(Object)},
-     * {@link #contains(Object)} and {@link #unique(Object)} methods.
+     * {@link #contains(Object)} and {@link #unique(Object)} methods. Tests 
for equality are done
+     * on the given object (this is implied by the {@link #unique(Object)} 
method contract).
      */
     private E intern(final Object obj, final int operation) {
         assert isValid();
@@ -304,6 +322,7 @@ public class WeakHashSet<E> extends AbstractSet<E> 
implements CheckedContainer<E
              * Check if the object is already contained in this
              * WeakHashSet. If yes, return the existing element.
              */
+            @SuppressWarnings("LocalVariableHidesMemberVariable")
             Entry[] table = this.table;
             final int hash = (mayContainArrays ? Utilities.deepHashCode(obj) : 
obj.hashCode()) & HASH_MASK;
             int index = hash % table.length;
@@ -332,7 +351,7 @@ public class WeakHashSet<E> extends AbstractSet<E> 
implements CheckedContainer<E
                 final E element = elementType.cast(obj);
                 table[index] = new Entry(element, table[index], hash);
                 assert isValid();
-                if (operation == INTERN) {
+                if (operation == UNIQUE) {
                     return element;
                 }
             }
diff --git 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/internal/UnmodifiableArrayList.java
 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/internal/UnmodifiableArrayList.java
index 5a48ecd0a7..095d97c107 100644
--- 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/internal/UnmodifiableArrayList.java
+++ 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/internal/UnmodifiableArrayList.java
@@ -23,6 +23,7 @@ import java.util.Objects;
 import java.util.RandomAccess;
 import java.lang.reflect.Array;
 import org.apache.sis.util.ArgumentChecks;
+import org.apache.sis.util.ConditionallySafe;
 import org.apache.sis.util.collection.CheckedContainer;
 
 
@@ -39,7 +40,7 @@ import org.apache.sis.util.collection.CheckedContainer;
  *     List<?> list = Collections.unmodifiableList(Arrays.asList(array));
  *     }
  *
- * except that this class uses one less level of indirection (which may be 
significant since
+ * except that this class uses one less level of indirection (which may be 
significant because
  * unmodifiable lists are extensively used in SIS) and implements the {@link 
CheckedContainer}
  * interface.
  *
@@ -47,7 +48,7 @@ import org.apache.sis.util.collection.CheckedContainer;
  * The {@link #getElementType()} return type is {@code Class<E>}, but its 
implementation actually
  * returns {@code Class<? extends E>}. This contract violation is possible 
because Java arrays are
  * covariant (at the contrary of collections). In order to avoid such contract 
violation, callers
- * <strong>must</strong> ensure that the type of array elements in exactly 
{@code E}, not a subtype
+ * <strong>must</strong> ensure that the type of array elements is exactly 
{@code E}, not a subtype
  * of {@code E}. This class has no way to verify that condition. This class is 
not in the public API
  * for this reason.
  *
@@ -121,11 +122,11 @@ public class UnmodifiableArrayList<E> extends 
AbstractList<E> implements RandomA
      * specified sub-region of the given array shall not be modified after 
construction if the
      * returned list is intended to be immutable.
      *
-     * <p>This method does not check the validity of the given index.
+     * <p>This method does not check the validity of the given indices.
      * The check must be done by the caller.</p>
      *
      * <h4>WARNING! Type safety hole</h4>
-     * Callers <strong>must</strong> ensure that the type of array elements in 
exactly {@code E},
+     * Callers <strong>must</strong> ensure that the type of array elements is 
exactly {@code E},
      * not a subtype of {@code E}. If the caller is okay with {@code List<? 
extends E>}, then (s)he
      * should use {@link 
org.apache.sis.util.collection.Containers#unmodifiableList(Object[])} instead.
      * See class javadoc for more information.
@@ -136,6 +137,7 @@ public class UnmodifiableArrayList<E> extends 
AbstractList<E> implements RandomA
      * @param  upper  high endpoint (exclusive) of the sublist.
      * @return the given array wrapped in an unmodifiable list.
      */
+    @ConditionallySafe
     public static <E> UnmodifiableArrayList<E> wrap(final E[] array, final int 
lower, final int upper) {
         if (lower == 0 && upper == array.length) {
             return new UnmodifiableArrayList<>(array);
@@ -147,11 +149,16 @@ public class UnmodifiableArrayList<E> extends 
AbstractList<E> implements RandomA
      * Returns the element type of the wrapped array. The default 
implementation returns
      * <code>array.getClass().{@linkplain Class#getComponentType() 
getComponentType()}</code>.
      *
+     * <h4>Type safety hole</h4>
+     * The returned value is correct only if the condition documented
+     * in {@link #wrap(Object[], int, int)} has been met.
+     *
      * @return the type of elements in the list.
      */
     @Override
+    @ConditionallySafe
+    @SuppressWarnings("unchecked")
     public Class<E> getElementType() {
-        // No @SuppressWarnings because this cast is really unsafe. See class 
javadoc.
         return (Class<E>) array.getClass().getComponentType();
     }
 
diff --git 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/internal/Unsafe.java
 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/internal/Unsafe.java
new file mode 100644
index 0000000000..0011777e88
--- /dev/null
+++ 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/internal/Unsafe.java
@@ -0,0 +1,106 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.sis.util.internal;
+
+import java.util.List;
+import java.util.Collection;
+import java.util.Map;
+import java.util.function.BiFunction;
+import org.apache.sis.util.Static;
+import org.apache.sis.util.ConditionallySafe;
+
+
+/**
+ * A central place where to put unsafe methods. Those method should be invoked 
only in contexts
+ * where the warning cannot be fully resolved. The use of this class allow 
maintainers to trace
+ * the Apache SIS codes where potentially unsafe operations still exist despite
+ * {@code @SuppressWarnings("unchecked")} annotation.
+ *
+ * @author  Martin Desruisseaux (Geomatys)
+ */
+public final class Unsafe extends Static {
+    /**
+     * Do not allow instantiation of this class.
+     */
+    private Unsafe() {
+    }
+
+    /**
+     * Adds all elements from one collection to the other. This method 
bypasses the compiler type safety checks.
+     * This method should be invoked only when, while not sure, the caller 
thinks that there is reasonably good
+     * reasons to assume that the element types have been or will be verified. 
For example, it may be a context
+     * where Apache SIS uses {@linkplain 
java.util.Collections#checkedCollection checked collection} by default
+     * but cannot guarantee that the users didn't override with a non-checked 
collection.
+     *
+     * @param  target    the collection where to add elements. Should 
preferably be a checked collection.
+     * @param  elements  the elements to add.
+     * @return whether {@code target} changed as a result of this operation.
+     */
+    @ConditionallySafe
+    @SuppressWarnings("unchecked")
+    public static boolean addAll(Collection<?> target, Collection<?> elements) 
{
+        return ((Collection) target).addAll(elements);
+    }
+
+    /**
+     * Sets the element at the given index in the given list. This method 
bypasses the compiler type safety checks.
+     * This method should be invoked only when the caller has done its best 
effort for ensuring that the element is
+     * an instance of the required type, or when the target list has good 
chances to be a checked collection.
+     *
+     * @param  target   the list where to set the element. Should preferably 
be a checked collection.
+     * @param  index    index of the element to set.
+     * @param  element  the element to set in the list.
+     * @return the previous element at the given index.
+     */
+    @ConditionallySafe
+    @SuppressWarnings("unchecked")
+    public static Object set(List<?> target, int index, Object element) {
+        return ((List) target).set(index, element);
+    }
+
+    /**
+     * Merges the value associated to the given key. This method bypasses the 
compiler type safety checks.
+     * This method should be invoked only when the caller has done its best 
effort for ensuring that the
+     * value and the merge function have compatible types.
+     *
+     * @param  target  the map where to merge a value.
+     * @param  key     key of the value to merge.
+     * @param  value   value to merge.
+     * @param  remappingFunction the function to apply for merging the given 
value with the existing one.
+     * @return the new value associated to the key.
+     */
+    @ConditionallySafe
+    @SuppressWarnings("unchecked")
+    public static Object merge(Map<?,?> target, Object key, Object value, 
BiFunction<?,?,?> remappingFunction) {
+        return ((Map) target).merge(key, value, remappingFunction);
+    }
+
+    /**
+     * Sets the value of a map entry. This method bypasses the compiler type 
safety checks.
+     * This method should be invoked only when the caller has done its best 
effort for ensuring
+     * that the value is an instance of the expected type, or if the map is a 
checked collection.
+     *
+     * @param  target  the entry where to set a value. Should be an entry from 
a checked collection.
+     * @param  value   the value to set.
+     * @return the previous value.
+     */
+    @ConditionallySafe
+    @SuppressWarnings("unchecked")
+    public static Object setValue(Map.Entry<?,?> target, Object value) {
+        return ((Map.Entry) target).setValue(value);
+    }
+}
diff --git 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/internal/X364.java 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/internal/X364.java
index 1979664d30..5cf42b449b 100644
--- 
a/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/internal/X364.java
+++ 
b/endorsed/src/org.apache.sis.util/main/org/apache/sis/util/internal/X364.java
@@ -119,7 +119,6 @@ public enum X364 {
      * @param code   the X.364 numerical code.
      * @param color  the color name, or {@code null} if none.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     private X364(final byte code, final String color) {
         this.code  = code;
         this.color = color;
@@ -132,7 +131,6 @@ public enum X364 {
      *
      * @param foreground  the X.364 code for a foreground color.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     private X364(final X364 foreground) {
         this((byte) (foreground.code + 10), foreground.color);
         this.foreground = foreground;
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/controls/SyncWindowList.java
 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/controls/SyncWindowList.java
index 91fc41a7c1..a0345f3911 100644
--- 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/controls/SyncWindowList.java
+++ 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/controls/SyncWindowList.java
@@ -134,7 +134,7 @@ public final class SyncWindowList extends TabularWidget 
implements ListChangeLis
      * @param  vocabulary  localized resources, given because already known by 
the caller
      *                     (those arguments would be removed if this 
constructor was public API).
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
+    @SuppressWarnings("unchecked")
     public SyncWindowList(final WindowHandler owner, final Resources 
resources, final Vocabulary vocabulary) {
         this.owner = owner;
         table = newTable();
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/controls/ValueColorMapper.java
 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/controls/ValueColorMapper.java
index 7b1a8852a3..ef0d02f4a6 100644
--- 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/controls/ValueColorMapper.java
+++ 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/controls/ValueColorMapper.java
@@ -346,6 +346,7 @@ public final class ValueColorMapper extends TabularWidget {
      * @param  vocabulary  localized resources, given because already known by 
the caller
      *                     (this argument would be removed if this method was 
public API).
      */
+    @SuppressWarnings("unchecked")
     private void createIsolineTable(final Vocabulary vocabulary) {
         /*
          * First column containing a checkbox for choosing whether the isoline 
should be drawn or not.
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageCanvas.java
 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageCanvas.java
index 94966a92ac..3b55a99660 100644
--- 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageCanvas.java
+++ 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageCanvas.java
@@ -252,6 +252,7 @@ public class CoverageCanvas extends MapCanvasAWT {
      * @param  controls  the controls of this canvas, or {@code null} if none.
      * @param  locale    the locale to use for labels and some messages, or 
{@code null} for default.
      */
+    @SuppressWarnings("this-escape")
     CoverageCanvas(final CoverageControls controls, final Locale locale) {
         super(locale);
         this.controls         = controls;
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageControls.java
 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageControls.java
index e9086e38c6..f5ea4e2206 100644
--- 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageControls.java
+++ 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageControls.java
@@ -147,9 +147,9 @@ final class CoverageControls extends ViewAndControls {
             final ValueColorMapper mapper = new ValueColorMapper(resources, 
vocabulary);
             isolines = new IsolineRenderer(view);
             isolines.setIsolineTables(List.of(mapper.getSteps()));
-            final Region view = mapper.getView();
-            VBox.setVgrow(view, Priority.ALWAYS);
-            isolinesPane = new VBox(view);                          // TODO: 
add band selector
+            final Region style = mapper.getView();
+            VBox.setVgrow(style, Priority.ALWAYS);
+            isolinesPane = new VBox(style);                         // TODO: 
add band selector
         }
         /*
          * Synchronized windows. A synchronized windows is a window which can 
reproduce the same gestures
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageExplorer.java
 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageExplorer.java
index 0f1da54034..88486ce894 100644
--- 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageExplorer.java
+++ 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageExplorer.java
@@ -229,6 +229,7 @@ public class CoverageExplorer extends Widget {
      *
      * @since 1.2
      */
+    @SuppressWarnings("this-escape")
     public CoverageExplorer(final View type) {
         ArgumentChecks.ensureNonNull("type", type);
         views            = new EnumMap<>(View.class);
@@ -250,6 +251,7 @@ public class CoverageExplorer extends Widget {
      *
      * @since 1.2
      */
+    @SuppressWarnings("this-escape")
     public CoverageExplorer(final CoverageExplorer source) {
         this(source.getViewType());
         window = PrivateAccess.newWindowHandler.apply(source.window, this);
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageStyling.java
 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageStyling.java
index f41a557a66..6841dd17dc 100644
--- 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageStyling.java
+++ 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/CoverageStyling.java
@@ -64,7 +64,6 @@ final class CoverageStyling extends 
ColorColumnHandler<Category> implements Func
     /**
      * Creates a new styling instance.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     CoverageStyling(final CoverageCanvas canvas) {
         customizedColors = new HashMap<>();
         this.canvas = canvas;
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/GridViewSkin.java
 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/GridViewSkin.java
index 9b3dedd400..9ba58d8854 100644
--- 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/GridViewSkin.java
+++ 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/GridViewSkin.java
@@ -426,7 +426,6 @@ final class GridViewSkin extends 
VirtualContainerBase<GridView, GridRow> impleme
          * Creates a new flow for the given view. This method registers 
listeners
          * on the properties that may require a redrawn of the full view port.
          */
-        @SuppressWarnings("ThisEscapedInObjectConstruction")
         Flow(final GridView view) {
             setPannable(false);         // We will use our own pan listeners.
             getHbar().valueProperty().addListener(this);
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/IsolineRenderer.java
 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/IsolineRenderer.java
index 2a36af6e64..c9d275d4f7 100644
--- 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/IsolineRenderer.java
+++ 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/coverage/IsolineRenderer.java
@@ -152,7 +152,6 @@ final class IsolineRenderer {
          *
          * @param  steps  the list of isoline levels to render.
          */
-        @SuppressWarnings("ThisEscapedInObjectConstruction")
         Band(final ObservableList<Step> steps) {
             this.steps = steps;
             addListeners(steps);
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/internal/PropertyView.java
 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/internal/PropertyView.java
index ce6263bcbd..6774faccb5 100644
--- 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/internal/PropertyView.java
+++ 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/internal/PropertyView.java
@@ -142,7 +142,6 @@ public final class PropertyView implements Localized, 
ChangeListener<Number> {
      * @param  view        the property where to set the node showing the 
value.
      * @param  background  the image background color, or {@code null} if none.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     public PropertyView(final Locale locale, final ObjectProperty<Node> view, 
final ObjectProperty<Background> background) {
         formats = new PropertyValueFormats(locale);
         this.view = view;
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/map/MapCanvas.java 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/map/MapCanvas.java
index 1738b17ee3..d9863eacfc 100644
--- a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/map/MapCanvas.java
+++ b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/map/MapCanvas.java
@@ -46,6 +46,7 @@ import javafx.beans.value.ObservableValue;
 import javafx.beans.value.WritableValue;
 import javafx.concurrent.Task;
 import javafx.concurrent.Worker;
+import javafx.scene.Node;
 import javafx.scene.control.ContextMenu;
 import javafx.scene.control.ToggleGroup;
 import javafx.scene.transform.Affine;
@@ -351,6 +352,7 @@ public abstract class MapCanvas extends PlanarCanvas {
      *
      * @param  locale  the locale to use for labels and some messages, or 
{@code null} for default.
      */
+    @SuppressWarnings("this-escape")
     public MapCanvas(final Locale locale) {
         super(locale);
         transform        = new Affine();
@@ -719,7 +721,6 @@ public abstract class MapCanvas extends PlanarCanvas {
          * Creates and registers a new handler for showing a contextual menu 
in the enclosing canvas.
          * It is caller responsibility to ensure that this method is invoked 
only once.
          */
-        @SuppressWarnings("ThisEscapedInObjectConstruction")
         MenuHandler(final ContextMenu menu) {
             super(getDisplayCRS());
             this.menu = menu;
@@ -737,7 +738,7 @@ public abstract class MapCanvas extends PlanarCanvas {
                 hideContextMenu();
                 x = event.getX();
                 y = event.getY();
-                menu.show((Pane) event.getSource(), event.getScreenX(), 
event.getScreenY());
+                menu.show((Node) event.getSource(), event.getScreenX(), 
event.getScreenY());
                 menuShown = menu;
                 event.consume();
             }
@@ -788,8 +789,8 @@ public abstract class MapCanvas extends PlanarCanvas {
         public void propertyChange(final PropertyChangeEvent event) {
             if (OBJECTIVE_CRS_PROPERTY.equals(event.getPropertyName())) {
                 final Object value = event.getNewValue();
-                if (value instanceof CoordinateReferenceSystem) {
-                    selectedCrsProperty.set((CoordinateReferenceSystem) value);
+                if (value instanceof ReferenceSystem) {
+                    selectedCrsProperty.set((ReferenceSystem) value);
                 }
                 if (!isPositionableProjection) {
                     positionables.selectToggle(null);
@@ -804,8 +805,9 @@ public abstract class MapCanvas extends PlanarCanvas {
      *
      * @param  crs       the new Coordinate Reference System in which to 
transform all data before displaying.
      * @param  anchor    the point to keep at fixed display coordinates, or 
{@code null} for default value.
-     * @param  property  the property to reset if the operation fails.
+     * @param  property  the property to reset if the operation fails, or 
{@code null} if none.
      */
+    @SuppressWarnings("unchecked")
     private void setObjectiveCRS(final CoordinateReferenceSystem crs, 
DirectPosition anchor,
                                  final ObservableValue<? extends 
ReferenceSystem> property)
     {
@@ -826,6 +828,7 @@ public abstract class MapCanvas extends PlanarCanvas {
             requestRepaint();
         } catch (Exception e) {
             if (property instanceof WritableValue<?>) {
+                // Cast is ok because used only for properties that we defined.
                 ((WritableValue<ReferenceSystem>) property).setValue(previous);
             }
             errorOccurred(e);
@@ -1212,6 +1215,7 @@ public abstract class MapCanvas extends PlanarCanvas {
                      * Otherwise the transform is initialized to an identity 
transform (should not happen often).
                      * If a CRS is present, it is used for deciding if we need 
to swap or flip axes.
                      */
+                    @SuppressWarnings("LocalVariableHidesMemberVariable")
                     final Envelope objectiveBounds = getObjectiveBounds();
                     if (objectiveBounds != null) {
                         final MatrixSIS m;
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/map/MapCanvasAWT.java 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/map/MapCanvasAWT.java
index d27ab815ae..b72e067ba7 100644
--- 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/map/MapCanvasAWT.java
+++ 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/map/MapCanvasAWT.java
@@ -153,6 +153,7 @@ public abstract class MapCanvasAWT extends MapCanvas {
      *
      * @param  locale  the locale to use for labels and some messages, or 
{@code null} for default.
      */
+    @SuppressWarnings("this-escape")
     public MapCanvasAWT(final Locale locale) {
         super(locale);
         imageMargin = new SimpleObjectProperty<>(this, "imageMargin", 
DEFAULT_MARGIN);
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/metadata/MetadataTree.java
 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/metadata/MetadataTree.java
index a1b1af05fb..8da1947388 100644
--- 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/metadata/MetadataTree.java
+++ 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/metadata/MetadataTree.java
@@ -180,6 +180,7 @@ check:      if (data != null) {
      *
      * @param  controller  the widget to watch, or {@code null} if none.
      */
+    @SuppressWarnings("this-escape")
     public MetadataTree(final MetadataSummary controller) {
         this(controller, false);
         setRowFactory(Row::new);
@@ -192,7 +193,7 @@ check:      if (data != null) {
      * @param  controller  the widget to watch, or {@code null} if none.
      * @param  standard    {@code true} for showing standard metadata, or 
{@code false} for native metadata.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
+    @SuppressWarnings({"this-escape", "unchecked"})
     MetadataTree(final MetadataSummary controller, final boolean standard) {
         final Vocabulary vocabulary;
         if (controller != null) {
@@ -405,7 +406,6 @@ check:      if (data != null) {
         /**
          * Creates a new row for the given tree table.
          */
-        @SuppressWarnings("ThisEscapedInObjectConstruction")
         Row(final TreeTableView<TreeTable.Node> owner) {
             final MetadataTree md = (MetadataTree) owner;
             final Resources localized = Resources.forLocale(md.getLocale());
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/metadata/StandardMetadataTree.java
 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/metadata/StandardMetadataTree.java
index b40e00a40e..56b73d5c0f 100644
--- 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/metadata/StandardMetadataTree.java
+++ 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/metadata/StandardMetadataTree.java
@@ -127,7 +127,6 @@ public class StandardMetadataTree extends MetadataTree {
         /**
          * Creates a new row for the given tree table.
          */
-        @SuppressWarnings("ThisEscapedInObjectConstruction")
         Row(final TreeTableView<TreeTable.Node> view) {
             super(view);
             final StandardMetadataTree md = (StandardMetadataTree) view;
diff --git 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/referencing/WKTPane.java
 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/referencing/WKTPane.java
index 6a770d3bc5..7d9622e9ba 100644
--- 
a/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/referencing/WKTPane.java
+++ 
b/optional/src/org.apache.sis.gui/main/org/apache/sis/gui/referencing/WKTPane.java
@@ -71,7 +71,6 @@ final class WKTPane extends StringConverter<Convention> 
implements ChangeListene
     /**
      * Creates a new pane for showing CRS Well Known Text.
      */
-    @SuppressWarnings("ThisEscapedInObjectConstruction")
     WKTPane(final Locale locale) {
         final Convention[] sc = {           // Selected conventions in the 
order we want them to appear.
             Convention.WKT2_SIMPLIFIED,


Reply via email to