// jTDS JDBC Driver for Microsoft SQL Server and Sybase // Copyright (C) 2004 The jTDS Project // // This library is free software; you can redistribute it and/or // modify it under the terms of the GNU Lesser General Public // License as published by the Free Software Foundation; either // version 2.1 of the License, or (at your option) any later version. // // This library is distributed in the hope that it will be useful, // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU // Lesser General Public License for more details. // // You should have received a copy of the GNU Lesser General Public // License along with this library; if not, write to the Free Software // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA // package net.sourceforge.jtds.jdbc; import java.io.BufferedInputStream; import java.io.DataInputStream; import java.io.DataOutputStream; import java.io.IOException; import java.net.UnknownHostException; import jcifs.Config; import jcifs.smb.NtlmPasswordAuthentication; import jcifs.smb.SmbNamedPipe; /** * This class implements inter-process communication (IPC) to the * database server using named pipes. * * @todo Extract abstract base class SharedIpc from <code>SharedSocket</code> and this class. * @todo Implement connection timeouts for named pipes. * * @author David D. Kilzer * @version $Id: SharedNamedPipe.java,v 1.19.2.2 2009-12-10 09:54:04 ickzon Exp $ */ public class SharedNamedPipe extends SharedSocket { /** * The shared named pipe. */ private SmbNamedPipe pipe; /** * Creates a new instance of <code>SharedNamedPipe</code>. * * @param connection * @throws IOException if the named pipe or its input or output streams do * not open * @throws UnknownHostException if host cannot be found for the named pipe */ public SharedNamedPipe(ConnectionJDBC2 connection) throws IOException { super(connection.getBufferDir(), connection.getTdsVersion(), connection.getServerType()); // apply socketTimeout as responseTimeout int timeout = connection.getSocketTimeout() * 1000; String val = String.valueOf(timeout > 0 ? timeout : Integer.MAX_VALUE); Config.setProperty("jcifs.smb.client.responseTimeout", val); Config.setProperty("jcifs.smb.client.soTimeout", val); NtlmPasswordAuthentication auth = new NtlmPasswordAuthentication( connection.getDomainName(), connection.getUser(), connection.getPassword()); StringBuffer url = new StringBuffer(32); url.append("smb://"); url.append(connection.getServerName()); url.append("/IPC$"); final String instanceName = connection.getInstanceName(); if (instanceName != null && instanceName.length() != 0) { url.append("/MSSQL$"); url.append(instanceName); } String namedPipePath = DefaultProperties.getNamedPipePath(connection.getServerType()); url.append(namedPipePath); setPipe(new SmbNamedPipe(url.toString(), SmbNamedPipe.PIPE_TYPE_RDWR, auth)); setOut(new DataOutputStream(getPipe().getNamedPipeOutputStream())); final int bufferSize = Support.calculateNamedPipeBufferSize( connection.getTdsVersion(), connection.getPacketSize()); setIn(new DataInputStream( new BufferedInputStream( getPipe().getNamedPipeInputStream(), bufferSize))); } /** * Get the connected status of this socket. * * @return true if the underlying socket is connected */ boolean isConnected() { return getPipe() != null; } /** * Close the socket (noop if in shared mode). */ void close() throws IOException { super.close(); getOut().close(); getIn().close(); //getPipe().close(); } /** * Force close the socket causing any pending reads/writes to fail. * <p/> * Used by the login timer to abort a login attempt. */ void forceClose() { try { getOut().close(); } catch (IOException e) { // Ignore } finally { setOut(null); } try { getIn().close(); } catch (IOException e) { // Ignore } finally { setIn(null); } setPipe(null); } /** * Getter for {@link SharedNamedPipe#pipe} field. * * @return {@link SmbNamedPipe} used for communication */ private SmbNamedPipe getPipe() { return pipe; } /** * Setter for {@link SharedNamedPipe#pipe} field. * * @param pipe {@link SmbNamedPipe} to be used for communication */ private void setPipe(SmbNamedPipe pipe) { this.pipe = pipe; } /** * Set the socket timeout. * <p/> * Noop for now; timeouts are not implemented for SMB named pipes. * * @param timeout timeout value in milliseconds */ protected void setTimeout(int timeout) { // FIXME - implement timeout functionality } }