diff --git a/src/main/java/com/alibaba/druid/pool/DruidConnectionHolder.java b/src/main/java/com/alibaba/druid/pool/DruidConnectionHolder.java index 1bf8163d40..0778659e07 100644 --- a/src/main/java/com/alibaba/druid/pool/DruidConnectionHolder.java +++ b/src/main/java/com/alibaba/druid/pool/DruidConnectionHolder.java @@ -24,6 +24,7 @@ import java.util.Date; import java.util.List; import java.util.Map; import java.util.concurrent.CopyOnWriteArrayList; +import java.util.concurrent.locks.ReentrantLock; import javax.sql.ConnectionEventListener; import javax.sql.StatementEventListener; @@ -68,6 +69,7 @@ public final class DruidConnectionHolder { protected boolean discard = false; protected final Map variables; protected final Map globleVariables; + final ReentrantLock lock = new ReentrantLock(); public DruidConnectionHolder(DruidAbstractDataSource dataSource, PhysicalConnectionInfo pyConnectInfo) throws SQLException{ @@ -191,11 +193,21 @@ public final class DruidConnectionHolder { } public void addTrace(DruidPooledStatement stmt) { - statementTrace.add(stmt); + lock.lock(); + try { + statementTrace.add(stmt); + } finally { + lock.unlock(); + } } public void removeTrace(DruidPooledStatement stmt) { - statementTrace.remove(stmt); + lock.lock(); + try { + statementTrace.remove(stmt); + } finally { + lock.unlock(); + } } public List getConnectionEventListeners() { @@ -285,11 +297,17 @@ public final class DruidConnectionHolder { connectionEventListeners.clear(); statementEventListeners.clear(); - for (Object item : statementTrace.toArray()) { - Statement stmt = (Statement) item; - JdbcUtils.close(stmt); + lock.lock(); + try { + for (Object item : statementTrace.toArray()) { + Statement stmt = (Statement) item; + JdbcUtils.close(stmt); + } + + statementTrace.clear(); + } finally { + lock.unlock(); } - statementTrace.clear(); conn.clearWarnings(); } diff --git a/src/main/java/com/alibaba/druid/pool/DruidDataSource.java b/src/main/java/com/alibaba/druid/pool/DruidDataSource.java index 376d5c2cf0..529255664d 100644 --- a/src/main/java/com/alibaba/druid/pool/DruidDataSource.java +++ b/src/main/java/com/alibaba/druid/pool/DruidDataSource.java @@ -1679,8 +1679,13 @@ public class DruidDataSource extends DruidAbstractDataSource implements DruidDat if (requireDiscard) { if (holder.statementTrace != null) { - for (Statement stmt : holder.statementTrace) { - JdbcUtils.close(stmt); + holder.lock.lock(); + try { + for (Statement stmt : holder.statementTrace) { + JdbcUtils.close(stmt); + } + } finally { + holder.lock.unlock(); } } diff --git a/src/main/java/com/alibaba/druid/pool/DruidPooledConnection.java b/src/main/java/com/alibaba/druid/pool/DruidPooledConnection.java index 7d4b36ac6a..a6b3afbda7 100644 --- a/src/main/java/com/alibaba/druid/pool/DruidPooledConnection.java +++ b/src/main/java/com/alibaba/druid/pool/DruidPooledConnection.java @@ -69,13 +69,14 @@ public class DruidPooledConnection extends PoolableWrapper implements javax.sql. private volatile boolean abandoned = false; protected StackTraceElement[] connectStackTrace; protected Throwable disableError = null; - public ReentrantLock lock = new ReentrantLock(); + final ReentrantLock lock; public DruidPooledConnection(DruidConnectionHolder holder){ super(holder.getConnection()); this.conn = holder.getConnection(); this.holder = holder; + this.lock = holder.lock; dupCloseLogEnable = holder.getDataSource().isDupCloseLogEnable(); ownerThread = Thread.currentThread(); connectedTimeMillis = System.currentTimeMillis();