protected SQLException markPossiblyBroken(SQLException e) {
	    String state = e.getSQLState();
	    boolean alreadyDestroyed = false;

		ConnectionState connectionState = this.getConnectionHook() != null ? this.getConnectionHook().onMarkPossiblyBroken(this, state, e) : ConnectionState.NOP; 
		if (state == null){ // safety;
			state = "08999"; 
		}

		if (((sqlStateDBFailureCodes.contains(state) || connectionState.equals(ConnectionState.TERMINATE_ALL_CONNECTIONS)) && this.pool != null) && this.pool.getDbIsDown().compareAndSet(false, true) ){
			logger.error("Database access problem. Killing off this connection and all remaining connections in the connection pool. SQL State = " + state);
			this.pool.connectionStrategy.terminateAllConnections();
			this.pool.destroyConnection(this);
			this.logicallyClosed.set(true);
			alreadyDestroyed = true;

			for (int i=0; i < this.pool.partitionCount; i++) {
				// send a signal to try re-populating again.
				this.pool.partitions[i].getPoolWatchThreadSignalQueue().offer(new Object()); // item being pushed is not important.
			}
		}

		//case where either the connection is closed or
		//two concurrent connections loose connections with
		//the 08S01 code but one one is killed in the code
		//above give dbIsDown is set for the first connection
		if (state.equals("08003") || sqlStateDBFailureCodes.contains(state) || e.getCause() instanceof SocketException) {
		    if (!alreadyDestroyed) {
			this.pool.destroyConnection(this);
			this.logicallyClosed.set(true);
			getOriginatingPartition().getPoolWatchThreadSignalQueue().offer(new Object()); // item being pushed is not important.
		    }
		}
		
		// SQL-92 says:
		//		 Class values that begin with one of the <digit>s '5', '6', '7',
		//         '8', or '9' or one of the <simple Latin upper case letter>s 'I',
		//         'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V',
		//         'W', 'X', 'Y', or 'Z' are reserved for implementation-specified
		//         conditions.

		// FIXME: We should look into this.connection.getMetaData().getSQLStateType();
		// to determine if we have SQL:92 or X/OPEN sqlstatus codes.

		//		char firstChar = state.charAt(0);
		// if it's a communication exception, a mysql deadlock or an implementation-specific error code, flag this connection as being potentially broken.
		// state == 40001 is mysql specific triggered when a deadlock is detected
		// state == HY000 is firebird specific triggered when a connection is broken
		char firstChar = state.charAt(0);
		if (connectionState.equals(ConnectionState.CONNECTION_POSSIBLY_BROKEN) || state.equals("40001") || 
				state.equals("HY000") ||
				state.startsWith("08") ||  (firstChar >= '5' && firstChar <='9') /*|| (firstChar >='I' && firstChar <= 'Z')*/){
			this.possiblyBroken = true;
		}

		// Notify anyone who's interested
		if (this.possiblyBroken  && (this.getConnectionHook() != null)){
			this.possiblyBroken = this.getConnectionHook().onConnectionException(this, state, e);
		}

		return e;
	}
protected SQLException markPossiblyBroken ( SQLException e ) { String state = e . getSQLState ( ) ; boolean alreadyDestroyed = false ; ConnectionState connectionState = this . getConnectionHook ( ) != null ? this . getConnectionHook ( ) . onMarkPossiblyBroken ( this , state , e ) : ConnectionState . NOP ; if ( state == null ) { state = "08999" ; } if ( ( ( sqlStateDBFailureCodes . contains ( state ) || connectionState . equals ( ConnectionState . TERMINATE_ALL_CONNECTIONS ) ) && this . pool != null ) && this . pool . getDbIsDown ( ) . compareAndSet ( false , true ) ) { logger . error ( "Database access problem. Killing off this connection and all remaining connections in the connection pool. SQL State = " + state ) ; this . pool . connectionStrategy . terminateAllConnections ( ) ; this . pool . destroyConnection ( this ) ; this . logicallyClosed . set ( true ) ; alreadyDestroyed = true ; for ( int i = 0 ; i < this . pool . partitionCount ; i ++ ) { this . pool . partitions [ i ] . getPoolWatchThreadSignalQueue ( ) . offer ( new Object ( ) ) ; } } if ( state . equals ( "08003" ) || sqlStateDBFailureCodes . contains ( state ) || e . getCause ( ) instanceof SocketException ) { if ( ! alreadyDestroyed ) { this . pool . destroyConnection ( this ) ; this . logicallyClosed . set ( true ) ; getOriginatingPartition ( ) . getPoolWatchThreadSignalQueue ( ) . offer ( new Object ( ) ) ; } } char firstChar = state . charAt ( 0 ) ; if ( connectionState . equals ( ConnectionState . CONNECTION_POSSIBLY_BROKEN ) || state . equals ( "40001" ) || state . equals ( "HY000" ) || state . startsWith ( "08" ) || ( firstChar >= '5' && firstChar <= '9' ) ) { this . possiblyBroken = true ; } if ( this . possiblyBroken && ( this . getConnectionHook ( ) != null ) ) { this . possiblyBroken = this . getConnectionHook ( ) . onConnectionException ( this , state , e ) ; } return e ; }
Given an exception, flag the connection (or database) as being potentially broken. If the exception is a data-specific exception,
do nothing except throw it back to the application.

@param e SQLException e
@return SQLException for further processing