[DBCP-549] Make
org.apache.commons.dbcp2.AbandonedTrace.removeTrace(AbandonedTrace)
null-safe.
diff --git a/src/changes/changes.xml b/src/changes/changes.xml
index df7d6f9..3325853 100644
--- a/src/changes/changes.xml
+++ b/src/changes/changes.xml
@@ -112,6 +112,9 @@
       <action dev="ggregory" type="update" issue="DBCP-548" due-to="Gary Gregory">
         Update Apache Commons Pool from 2.6.1 to 2.7.0.
       </action>
+      <action dev="ggregory" type="update" issue="DBCP-549" due-to="Gary Gregory">
+        Make org.apache.commons.dbcp2.AbandonedTrace.removeTrace(AbandonedTrace) null-safe.
+      </action>
     </release>
     <release version="2.6.0" date="2019-02-14" description="This is a minor release, including bug fixes and enhancements.">
       <action dev="chtompki" type="add" issue="DBCP-534" due-to="Peter Wicks">
diff --git a/src/main/java/org/apache/commons/dbcp2/AbandonedTrace.java b/src/main/java/org/apache/commons/dbcp2/AbandonedTrace.java
index 659fe76..aa55882 100644
--- a/src/main/java/org/apache/commons/dbcp2/AbandonedTrace.java
+++ b/src/main/java/org/apache/commons/dbcp2/AbandonedTrace.java
@@ -155,7 +155,7 @@
             final Iterator<WeakReference<AbandonedTrace>> iter = traceList.iterator();
             while (iter.hasNext()) {
                 final AbandonedTrace traceInList = iter.next().get();
-                if (trace.equals(traceInList)) {
+                if (trace != null && trace.equals(traceInList)) {
                     iter.remove();
                     break;
                 } else if (traceInList == null) {
@@ -165,4 +165,16 @@
             }
         }
     }
+
+    /**
+     * Removes this object the source object is tracing.
+     * 
+     * @param source The object tracing
+     * @since 2.7.0
+     */
+    protected void removeThisTrace(final Object source) {
+        if (source instanceof AbandonedTrace) {
+            AbandonedTrace.class.cast(source).removeTrace(this);
+        }
+    }
 }
diff --git a/src/main/java/org/apache/commons/dbcp2/DelegatingResultSet.java b/src/main/java/org/apache/commons/dbcp2/DelegatingResultSet.java
index 3d1483c..86e4d43 100644
--- a/src/main/java/org/apache/commons/dbcp2/DelegatingResultSet.java
+++ b/src/main/java/org/apache/commons/dbcp2/DelegatingResultSet.java
@@ -186,11 +186,11 @@
     public void close() throws SQLException {
         try {
             if (statement != null) {
-                ((AbandonedTrace) statement).removeTrace(this);
+                removeThisTrace(statement);
                 statement = null;
             }
             if (connection != null) {
-                ((AbandonedTrace) connection).removeTrace(this);
+                removeThisTrace(connection);
                 connection = null;
             }
             resultSet.close();
diff --git a/src/main/java/org/apache/commons/dbcp2/PoolableCallableStatement.java b/src/main/java/org/apache/commons/dbcp2/PoolableCallableStatement.java
index 969a7e1..717e7b2 100644
--- a/src/main/java/org/apache/commons/dbcp2/PoolableCallableStatement.java
+++ b/src/main/java/org/apache/commons/dbcp2/PoolableCallableStatement.java
@@ -67,9 +67,7 @@
 
         // Remove from trace now because this statement will be
         // added by the activate method.
-        if (getConnectionInternal() != null) {
-            getConnectionInternal().removeTrace(this);
-        }
+        removeThisTrace(getConnectionInternal());
     }
 
     /**
@@ -115,9 +113,7 @@
     @Override
     public void passivate() throws SQLException {
         setClosedInternal(true);
-        if (getConnectionInternal() != null) {
-            getConnectionInternal().removeTrace(this);
-        }
+        removeThisTrace(getConnectionInternal());
 
         // The JDBC spec requires that a statement close any open
         // ResultSet's when it is closed.
diff --git a/src/main/java/org/apache/commons/dbcp2/PoolablePreparedStatement.java b/src/main/java/org/apache/commons/dbcp2/PoolablePreparedStatement.java
index 15d933e..222de96 100644
--- a/src/main/java/org/apache/commons/dbcp2/PoolablePreparedStatement.java
+++ b/src/main/java/org/apache/commons/dbcp2/PoolablePreparedStatement.java
@@ -69,9 +69,7 @@
 
         // Remove from trace now because this statement will be
         // added by the activate method.
-        if (getConnectionInternal() != null) {
-            getConnectionInternal().removeTrace(this);
-        }
+        removeThisTrace(getConnectionInternal());
     }
 
     /**
@@ -128,9 +126,7 @@
             clearBatch();
         }
         setClosedInternal(true);
-        if (getConnectionInternal() != null) {
-            getConnectionInternal().removeTrace(this);
-        }
+        removeThisTrace(getConnectionInternal());
 
         // The JDBC spec requires that a statement closes any open
         // ResultSet's when it is closed.