0N/A/*
2362N/A * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved.
0N/A * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
0N/A *
0N/A * This code is free software; you can redistribute it and/or modify it
0N/A * under the terms of the GNU General Public License version 2 only, as
2362N/A * published by the Free Software Foundation. Oracle designates this
0N/A * particular file as subject to the "Classpath" exception as provided
2362N/A * by Oracle in the LICENSE file that accompanied this code.
0N/A *
0N/A * This code is distributed in the hope that it will be useful, but WITHOUT
0N/A * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
0N/A * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
0N/A * version 2 for more details (a copy is included in the LICENSE file that
0N/A * accompanied this code).
0N/A *
0N/A * You should have received a copy of the GNU General Public License version
0N/A * 2 along with this work; if not, write to the Free Software Foundation,
0N/A * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
0N/A *
2362N/A * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
2362N/A * or visit www.oracle.com if you need additional information or have any
2362N/A * questions.
0N/A */
0N/A
0N/Apackage com.sun.jndi.ldap.pool;
0N/A
0N/A/**
0N/A * Represents a description of PooledConnection in Connections.
0N/A * Contains a PooledConnection, its state (busy, idle, expired), and idle time.
0N/A *
0N/A * Any access or update to a descriptor's state is synchronized.
0N/A *
0N/A * @author Rosanna Lee
0N/A */
0N/Afinal class ConnectionDesc {
0N/A private final static boolean debug = Pool.debug;
0N/A
0N/A // Package private because used by Pool.showStats()
0N/A static final byte BUSY = (byte)0;
0N/A static final byte IDLE = (byte)1;
0N/A static final byte EXPIRED = (byte)2;
0N/A
0N/A final private PooledConnection conn;
0N/A
0N/A private byte state = IDLE; // initial state
0N/A private long idleSince;
0N/A private long useCount = 0; // for stats & debugging only
0N/A
0N/A ConnectionDesc(PooledConnection conn) {
0N/A this.conn = conn;
0N/A }
0N/A
0N/A ConnectionDesc(PooledConnection conn, boolean use) {
0N/A this.conn = conn;
0N/A if (use) {
0N/A state = BUSY;
0N/A ++useCount;
0N/A }
0N/A }
0N/A
0N/A /**
0N/A * Two desc are equal if their PooledConnections are the same.
0N/A * This is useful when searching for a ConnectionDesc using only its
0N/A * PooledConnection.
0N/A */
0N/A public boolean equals(Object obj) {
0N/A return obj != null
0N/A && obj instanceof ConnectionDesc
0N/A && ((ConnectionDesc)obj).conn == conn;
0N/A }
0N/A
0N/A /**
0N/A * Hashcode is that of PooledConnection to facilitate
0N/A * searching for a ConnectionDesc using only its PooledConnection.
0N/A */
0N/A public int hashCode() {
0N/A return conn.hashCode();
0N/A }
0N/A
0N/A /**
0N/A * Changes the state of a ConnectionDesc from BUSY to IDLE and
0N/A * records the current time so that we will know how long it has been idle.
0N/A * @return true if state change occurred.
0N/A */
0N/A synchronized boolean release() {
0N/A d("release()");
0N/A if (state == BUSY) {
0N/A state = IDLE;
0N/A
0N/A idleSince = System.currentTimeMillis();
0N/A return true; // Connection released, ready for reuse
0N/A } else {
0N/A return false; // Connection wasn't busy to begin with
0N/A }
0N/A }
0N/A
0N/A /**
0N/A * If ConnectionDesc is IDLE, change its state to BUSY and return
0N/A * its connection.
0N/A *
0N/A * @return ConnectionDesc's PooledConnection if it was idle; null otherwise.
0N/A */
0N/A synchronized PooledConnection tryUse() {
0N/A d("tryUse()");
0N/A
0N/A if (state == IDLE) {
0N/A state = BUSY;
0N/A ++useCount;
0N/A return conn;
0N/A }
0N/A
0N/A return null;
0N/A }
0N/A
0N/A /**
0N/A * If ConnectionDesc is IDLE and has expired, close the corresponding
0N/A * PooledConnection.
0N/A *
0N/A * @param threshold a connection that has been idle before this time
0N/A * have expired.
0N/A *
0N/A * @return true if entry is idle and has expired; false otherwise.
0N/A */
0N/A synchronized boolean expire(long threshold) {
0N/A if (state == IDLE && idleSince < threshold) {
0N/A
0N/A d("expire(): expired");
0N/A
0N/A state = EXPIRED;
0N/A conn.closeConnection(); // Close real connection
0N/A
0N/A return true; // Expiration successful
0N/A } else {
0N/A d("expire(): not expired");
0N/A return false; // Expiration did not occur
0N/A }
0N/A }
0N/A
0N/A public String toString() {
0N/A return conn.toString() + " " +
0N/A (state == BUSY ? "busy" : (state == IDLE ? "idle" : "expired"));
0N/A }
0N/A
0N/A // Used by Pool.showStats()
0N/A int getState() {
0N/A return state;
0N/A }
0N/A
0N/A // Used by Pool.showStats()
0N/A long getUseCount() {
0N/A return useCount;
0N/A }
0N/A
0N/A private void d(String msg) {
0N/A if (debug) {
0N/A System.err.println("ConnectionDesc." + msg + " " + toString());
0N/A }
0N/A }
0N/A}