| Index: third_party/twisted_8_1/twisted/conch/ssh/connection.py
|
| diff --git a/third_party/twisted_8_1/twisted/conch/ssh/connection.py b/third_party/twisted_8_1/twisted/conch/ssh/connection.py
|
| deleted file mode 100644
|
| index bc86f02b5e0e2a1a0d2032209bbdd98613c0ed01..0000000000000000000000000000000000000000
|
| --- a/third_party/twisted_8_1/twisted/conch/ssh/connection.py
|
| +++ /dev/null
|
| @@ -1,613 +0,0 @@
|
| -# -*- test-case-name: twisted.conch.test.test_connection -*-
|
| -# Copyright (c) 2001-2007 Twisted Matrix Laboratories.
|
| -# See LICENSE for details.
|
| -
|
| -#
|
| -
|
| -"""
|
| -This module contains the implementation of the ssh-connection service, which
|
| -allows access to the shell and port-forwarding.
|
| -
|
| -Maintainer: U{Paul Swartz<mailto:z3p@twistedmatrix.com>}
|
| -"""
|
| -
|
| -import struct
|
| -
|
| -from twisted.conch.ssh import service, common
|
| -from twisted.conch import error
|
| -from twisted.internet import defer
|
| -from twisted.python import log
|
| -
|
| -class SSHConnection(service.SSHService):
|
| - """
|
| - An implementation of the 'ssh-connection' service. It is used to
|
| - multiplex multiple channels over the single SSH connection.
|
| -
|
| - @ivar localChannelID: the next number to use as a local channel ID.
|
| - @type localChannelID: C{int}
|
| - @ivar channels: a C{dict} mapping a local channel ID to C{SSHChannel}
|
| - subclasses.
|
| - @type channels: C{dict}
|
| - @ivar localToRemoteChannel: a C{dict} mapping a local channel ID to a
|
| - remote channel ID.
|
| - @type localToRemoteChannel: C{dict}
|
| - @ivar channelsToRemoteChannel: a C{dict} mapping a C{SSHChannel} subclass
|
| - to remote channel ID.
|
| - @type channelsToRemoteChannel: C{dict}
|
| - @ivar deferreds: a C{dict} mapping a local channel ID to a C{list} of
|
| - C{Deferreds} for outstanding channel requests. Also, the 'global'
|
| - key stores the C{list} of pending global request C{Deferred}s.
|
| - """
|
| - name = 'ssh-connection'
|
| -
|
| - def __init__(self):
|
| - self.localChannelID = 0 # this is the current # to use for channel ID
|
| - self.localToRemoteChannel = {} # local channel ID -> remote channel ID
|
| - self.channels = {} # local channel ID -> subclass of SSHChannel
|
| - self.channelsToRemoteChannel = {} # subclass of SSHChannel ->
|
| - # remote channel ID
|
| - self.deferreds = {} # local channel -> list of deferreds for pending
|
| - # requests or 'global' -> list of deferreds for
|
| - # global requests
|
| - self.transport = None # gets set later
|
| -
|
| - def serviceStarted(self):
|
| - if hasattr(self.transport, 'avatar'):
|
| - self.transport.avatar.conn = self
|
| -
|
| - def serviceStopped(self):
|
| - map(self.channelClosed, self.channels.values())
|
| -
|
| - # packet methods
|
| - def ssh_GLOBAL_REQUEST(self, packet):
|
| - """
|
| - The other side has made a global request. Payload::
|
| - string request type
|
| - bool want reply
|
| - <request specific data>
|
| -
|
| - This dispatches to self.gotGlobalRequest.
|
| - """
|
| - requestType, rest = common.getNS(packet)
|
| - wantReply, rest = ord(rest[0]), rest[1:]
|
| - ret = self.gotGlobalRequest(requestType, rest)
|
| - if wantReply:
|
| - reply = MSG_REQUEST_FAILURE
|
| - data = ''
|
| - if ret:
|
| - reply = MSG_REQUEST_SUCCESS
|
| - if isinstance(ret, (tuple, list)):
|
| - data = ret[1]
|
| - self.transport.sendPacket(reply, data)
|
| -
|
| - def ssh_REQUEST_SUCCESS(self, packet):
|
| - """
|
| - Our global request succeeded. Get the appropriate Deferred and call
|
| - it back with the packet we received.
|
| - """
|
| - log.msg('RS')
|
| - self.deferreds['global'].pop(0).callback(packet)
|
| -
|
| - def ssh_REQUEST_FAILURE(self, packet):
|
| - """
|
| - Our global request failed. Get the appropriate Deferred and errback
|
| - it with the packet we received.
|
| - """
|
| - log.msg('RF')
|
| - self.deferreds['global'].pop(0).errback(
|
| - error.ConchError('global request failed', packet))
|
| -
|
| - def ssh_CHANNEL_OPEN(self, packet):
|
| - """
|
| - The other side wants to get a channel. Payload::
|
| - string channel name
|
| - uint32 remote channel number
|
| - uint32 remote window size
|
| - uint32 remote maximum packet size
|
| - <channel specific data>
|
| -
|
| - We get a channel from self.getChannel(), give it a local channel number
|
| - and notify the other side. Then notify the channel by calling its
|
| - channelOpen method.
|
| - """
|
| - channelType, rest = common.getNS(packet)
|
| - senderChannel, windowSize, maxPacket = struct.unpack('>3L', rest[:12])
|
| - packet = rest[12:]
|
| - try:
|
| - channel = self.getChannel(channelType, windowSize, maxPacket,
|
| - packet)
|
| - localChannel = self.localChannelID
|
| - self.localChannelID += 1
|
| - channel.id = localChannel
|
| - self.channels[localChannel] = channel
|
| - self.channelsToRemoteChannel[channel] = senderChannel
|
| - self.localToRemoteChannel[localChannel] = senderChannel
|
| - self.transport.sendPacket(MSG_CHANNEL_OPEN_CONFIRMATION,
|
| - struct.pack('>4L', senderChannel, localChannel,
|
| - channel.localWindowSize,
|
| - channel.localMaxPacket)+channel.specificData)
|
| - log.callWithLogger(channel, channel.channelOpen, packet)
|
| - except Exception, e:
|
| - log.msg('channel open failed')
|
| - log.err(e)
|
| - if isinstance(e, error.ConchError):
|
| - textualInfo, reason = e.args
|
| - else:
|
| - reason = OPEN_CONNECT_FAILED
|
| - textualInfo = "unknown failure"
|
| - self.transport.sendPacket(MSG_CHANNEL_OPEN_FAILURE,
|
| - struct.pack('>2L', senderChannel, reason) +
|
| - common.NS(textualInfo) + common.NS(''))
|
| -
|
| - def ssh_CHANNEL_OPEN_CONFIRMATION(self, packet):
|
| - """
|
| - The other side accepted our MSG_CHANNEL_OPEN request. Payload::
|
| - uint32 local channel number
|
| - uint32 remote channel number
|
| - uint32 remote window size
|
| - uint32 remote maximum packet size
|
| - <channel specific data>
|
| -
|
| - Find the channel using the local channel number and notify its
|
| - channelOpen method.
|
| - """
|
| - (localChannel, remoteChannel, windowSize,
|
| - maxPacket) = struct.unpack('>4L', packet[: 16])
|
| - specificData = packet[16:]
|
| - channel = self.channels[localChannel]
|
| - channel.conn = self
|
| - self.localToRemoteChannel[localChannel] = remoteChannel
|
| - self.channelsToRemoteChannel[channel] = remoteChannel
|
| - channel.remoteWindowLeft = windowSize
|
| - channel.remoteMaxPacket = maxPacket
|
| - log.callWithLogger(channel, channel.channelOpen, specificData)
|
| -
|
| - def ssh_CHANNEL_OPEN_FAILURE(self, packet):
|
| - """
|
| - The other side did not accept our MSG_CHANNEL_OPEN request. Payload::
|
| - uint32 local channel number
|
| - uint32 reason code
|
| - string reason description
|
| -
|
| - Find the channel using the local channel number and notify it by
|
| - calling its openFailed() method.
|
| - """
|
| - localChannel, reasonCode = struct.unpack('>2L', packet[:8])
|
| - reasonDesc = common.getNS(packet[8:])[0]
|
| - channel = self.channels[localChannel]
|
| - del self.channels[localChannel]
|
| - channel.conn = self
|
| - reason = error.ConchError(reasonDesc, reasonCode)
|
| - log.callWithLogger(channel, channel.openFailed, reason)
|
| -
|
| - def ssh_CHANNEL_WINDOW_ADJUST(self, packet):
|
| - """
|
| - The other side is adding bytes to its window. Payload::
|
| - uint32 local channel number
|
| - uint32 bytes to add
|
| -
|
| - Call the channel's addWindowBytes() method to add new bytes to the
|
| - remote window.
|
| - """
|
| - localChannel, bytesToAdd = struct.unpack('>2L', packet[:8])
|
| - channel = self.channels[localChannel]
|
| - log.callWithLogger(channel, channel.addWindowBytes, bytesToAdd)
|
| -
|
| - def ssh_CHANNEL_DATA(self, packet):
|
| - """
|
| - The other side is sending us data. Payload::
|
| - uint32 local channel number
|
| - string data
|
| -
|
| - Check to make sure the other side hasn't sent too much data (more
|
| - than what's in the window, or more than the maximum packet size). If
|
| - they have, close the channel. Otherwise, decrease the available
|
| - window and pass the data to the channel's dataReceived().
|
| - """
|
| - localChannel, dataLength = struct.unpack('>2L', packet[:8])
|
| - channel = self.channels[localChannel]
|
| - # XXX should this move to dataReceived to put client in charge?
|
| - if (dataLength > channel.localWindowLeft or
|
| - dataLength > channel.localMaxPacket): # more data than we want
|
| - log.callWithLogger(channel, log.msg, 'too much data')
|
| - self.sendClose(channel)
|
| - return
|
| - #packet = packet[:channel.localWindowLeft+4]
|
| - data = common.getNS(packet[4:])[0]
|
| - channel.localWindowLeft -= dataLength
|
| - if channel.localWindowLeft < channel.localWindowSize / 2:
|
| - self.adjustWindow(channel, channel.localWindowSize - \
|
| - channel.localWindowLeft)
|
| - #log.msg('local window left: %s/%s' % (channel.localWindowLeft,
|
| - # channel.localWindowSize))
|
| - log.callWithLogger(channel, channel.dataReceived, data)
|
| -
|
| - def ssh_CHANNEL_EXTENDED_DATA(self, packet):
|
| - """
|
| - The other side is sending us exteneded data. Payload::
|
| - uint32 local channel number
|
| - uint32 type code
|
| - string data
|
| -
|
| - Check to make sure the other side hasn't sent too much data (more
|
| - than what's in the window, or or than the maximum packet size). If
|
| - they have, close the channel. Otherwise, decrease the available
|
| - window and pass the data and type code to the channel's
|
| - extReceived().
|
| - """
|
| - localChannel, typeCode, dataLength = struct.unpack('>3L', packet[:12])
|
| - channel = self.channels[localChannel]
|
| - if (dataLength > channel.localWindowLeft or
|
| - dataLength > channel.localMaxPacket):
|
| - log.callWithLogger(channel, log.msg, 'too much extdata')
|
| - self.sendClose(channel)
|
| - return
|
| - data = common.getNS(packet[8:])[0]
|
| - channel.localWindowLeft -= dataLength
|
| - if channel.localWindowLeft < channel.localWindowSize / 2:
|
| - self.adjustWindow(channel, channel.localWindowSize -
|
| - channel.localWindowLeft)
|
| - log.callWithLogger(channel, channel.extReceived, typeCode, data)
|
| -
|
| - def ssh_CHANNEL_EOF(self, packet):
|
| - """
|
| - The other side is not sending any more data. Payload::
|
| - uint32 local channel number
|
| -
|
| - Notify the channel by calling its eofReceived() method.
|
| - """
|
| - localChannel = struct.unpack('>L', packet[:4])[0]
|
| - channel = self.channels[localChannel]
|
| - log.callWithLogger(channel, channel.eofReceived)
|
| -
|
| - def ssh_CHANNEL_CLOSE(self, packet):
|
| - """
|
| - The other side is closing its end; it does not want to receive any
|
| - more data. Payload::
|
| - uint32 local channel number
|
| -
|
| - Notify the channnel by calling its closeReceived() method. If
|
| - the channel has also sent a close message, call self.channelClosed().
|
| - """
|
| - localChannel = struct.unpack('>L', packet[:4])[0]
|
| - channel = self.channels[localChannel]
|
| - log.callWithLogger(channel, channel.closeReceived)
|
| - channel.remoteClosed = True
|
| - if channel.localClosed and channel.remoteClosed:
|
| - self.channelClosed(channel)
|
| -
|
| - def ssh_CHANNEL_REQUEST(self, packet):
|
| - """
|
| - The other side is sending a request to a channel. Payload::
|
| - uint32 local channel number
|
| - string request name
|
| - bool want reply
|
| - <request specific data>
|
| -
|
| - Pass the message to the channel's requestReceived method. If the
|
| - other side wants a reply, add callbacks which will send the
|
| - reply.
|
| - """
|
| - localChannel = struct.unpack('>L', packet[: 4])[0]
|
| - requestType, rest = common.getNS(packet[4:])
|
| - wantReply = ord(rest[0])
|
| - channel = self.channels[localChannel]
|
| - d = defer.maybeDeferred(log.callWithLogger, channel,
|
| - channel.requestReceived, requestType, rest[1:])
|
| - if wantReply:
|
| - d.addCallback(self._cbChannelRequest, localChannel)
|
| - d.addErrback(self._ebChannelRequest, localChannel)
|
| - return d
|
| -
|
| - def _cbChannelRequest(self, result, localChannel):
|
| - """
|
| - Called back if the other side wanted a reply to a channel request. If
|
| - the result is true, send a MSG_CHANNEL_SUCCESS. Otherwise, raise
|
| - a C{error.ConchError}
|
| -
|
| - @param result: the value returned from the channel's requestReceived()
|
| - method. If it's False, the request failed.
|
| - @type result: C{bool}
|
| - @param localChannel: the local channel ID of the channel to which the
|
| - request was made.
|
| - @type localChannel: C{int}
|
| - @raises ConchError: if the result is False.
|
| - """
|
| - if not result:
|
| - raise error.ConchError('failed request')
|
| - self.transport.sendPacket(MSG_CHANNEL_SUCCESS, struct.pack('>L',
|
| - self.localToRemoteChannel[localChannel]))
|
| -
|
| - def _ebChannelRequest(self, result, localChannel):
|
| - """
|
| - Called if the other wisde wanted a reply to the channel requeset and
|
| - the channel request failed.
|
| -
|
| - @param result: a Failure, but it's not used.
|
| - @param localChannel: the local channel ID of the channel to which the
|
| - request was made.
|
| - @type localChannel: C{int}
|
| - """
|
| - self.transport.sendPacket(MSG_CHANNEL_FAILURE, struct.pack('>L',
|
| - self.localToRemoteChannel[localChannel]))
|
| -
|
| - def ssh_CHANNEL_SUCCESS(self, packet):
|
| - """
|
| - Our channel request to the other other side succeeded. Payload::
|
| - uint32 local channel number
|
| -
|
| - Get the C{Deferred} out of self.deferreds and call it back.
|
| - """
|
| - localChannel = struct.unpack('>L', packet[:4])[0]
|
| - if self.deferreds.get(localChannel):
|
| - d = self.deferreds[localChannel].pop(0)
|
| - log.callWithLogger(self.channels[localChannel],
|
| - d.callback, '')
|
| -
|
| - def ssh_CHANNEL_FAILURE(self, packet):
|
| - """
|
| - Our channel request to the other side failed. Payload::
|
| - uint32 local channel number
|
| -
|
| - Get the C{Deferred} out of self.deferreds and errback it with a
|
| - C{error.ConchError}.
|
| - """
|
| - localChannel = struct.unpack('>L', packet[:4])[0]
|
| - if self.deferreds.get(localChannel):
|
| - d = self.deferreds[localChannel].pop(0)
|
| - log.callWithLogger(self.channels[localChannel],
|
| - d.errback,
|
| - error.ConchError('channel request failed'))
|
| -
|
| - # methods for users of the connection to call
|
| -
|
| - def sendGlobalRequest(self, request, data, wantReply=0):
|
| - """
|
| - Send a global request for this connection. Current this is only used
|
| - for remote->local TCP forwarding.
|
| -
|
| - @type request: C{str}
|
| - @type data: C{str}
|
| - @type wantReply: C{bool}
|
| - @rtype C{Deferred}/C{None}
|
| - """
|
| - self.transport.sendPacket(MSG_GLOBAL_REQUEST,
|
| - common.NS(request)
|
| - + (wantReply and '\xff' or '\x00')
|
| - + data)
|
| - if wantReply:
|
| - d = defer.Deferred()
|
| - self.deferreds.setdefault('global', []).append(d)
|
| - return d
|
| -
|
| - def openChannel(self, channel, extra=''):
|
| - """
|
| - Open a new channel on this connection.
|
| -
|
| - @type channel: subclass of C{SSHChannel}
|
| - @type extra: C{str}
|
| - """
|
| - log.msg('opening channel %s with %s %s'%(self.localChannelID,
|
| - channel.localWindowSize, channel.localMaxPacket))
|
| - self.transport.sendPacket(MSG_CHANNEL_OPEN, common.NS(channel.name)
|
| - + struct.pack('>3L', self.localChannelID,
|
| - channel.localWindowSize, channel.localMaxPacket)
|
| - + extra)
|
| - channel.id = self.localChannelID
|
| - self.channels[self.localChannelID] = channel
|
| - self.localChannelID += 1
|
| -
|
| - def sendRequest(self, channel, requestType, data, wantReply=0):
|
| - """
|
| - Send a request to a channel.
|
| -
|
| - @type channel: subclass of C{SSHChannel}
|
| - @type requestType: C{str}
|
| - @type data: C{str}
|
| - @type wantReply: C{bool}
|
| - @rtype C{Deferred}/C{None}
|
| - """
|
| - if channel.localClosed:
|
| - return
|
| - log.msg('sending request %s' % requestType)
|
| - self.transport.sendPacket(MSG_CHANNEL_REQUEST, struct.pack('>L',
|
| - self.channelsToRemoteChannel[channel])
|
| - + common.NS(requestType)+chr(wantReply)
|
| - + data)
|
| - if wantReply:
|
| - d = defer.Deferred()
|
| - self.deferreds.setdefault(channel.id, []).append(d)
|
| - return d
|
| -
|
| - def adjustWindow(self, channel, bytesToAdd):
|
| - """
|
| - Tell the other side that we will receive more data. This should not
|
| - normally need to be called as it is managed automatically.
|
| -
|
| - @type channel: subclass of L{SSHChannel}
|
| - @type bytesToAdd: C{int}
|
| - """
|
| - if channel.localClosed:
|
| - return # we're already closed
|
| - self.transport.sendPacket(MSG_CHANNEL_WINDOW_ADJUST, struct.pack('>2L',
|
| - self.channelsToRemoteChannel[channel],
|
| - bytesToAdd))
|
| - log.msg('adding %i to %i in channel %i' % (bytesToAdd,
|
| - channel.localWindowLeft, channel.id))
|
| - channel.localWindowLeft += bytesToAdd
|
| -
|
| - def sendData(self, channel, data):
|
| - """
|
| - Send data to a channel. This should not normally be used: instead use
|
| - channel.write(data) as it manages the window automatically.
|
| -
|
| - @type channel: subclass of L{SSHChannel}
|
| - @type data: C{str}
|
| - """
|
| - if channel.localClosed:
|
| - return # we're already closed
|
| - self.transport.sendPacket(MSG_CHANNEL_DATA, struct.pack('>L',
|
| - self.channelsToRemoteChannel[channel]) +
|
| - common.NS(data))
|
| -
|
| - def sendExtendedData(self, channel, dataType, data):
|
| - """
|
| - Send extended data to a channel. This should not normally be used:
|
| - instead use channel.writeExtendedData(data, dataType) as it manages
|
| - the window automatically.
|
| -
|
| - @type channel: subclass of L{SSHChannel}
|
| - @type dataType: C{int}
|
| - @type data: C{str}
|
| - """
|
| - if channel.localClosed:
|
| - return # we're already closed
|
| - self.transport.sendPacket(MSG_CHANNEL_EXTENDED_DATA, struct.pack('>2L',
|
| - self.channelsToRemoteChannel[channel],dataType) \
|
| - + common.NS(data))
|
| -
|
| - def sendEOF(self, channel):
|
| - """
|
| - Send an EOF (End of File) for a channel.
|
| -
|
| - @type channel: subclass of L{SSHChannel}
|
| - """
|
| - if channel.localClosed:
|
| - return # we're already closed
|
| - log.msg('sending eof')
|
| - self.transport.sendPacket(MSG_CHANNEL_EOF, struct.pack('>L',
|
| - self.channelsToRemoteChannel[channel]))
|
| -
|
| - def sendClose(self, channel):
|
| - """
|
| - Close a channel.
|
| -
|
| - @type channel: subclass of L{SSHChannel}
|
| - """
|
| - if channel.localClosed:
|
| - return # we're already closed
|
| - log.msg('sending close %i' % channel.id)
|
| - self.transport.sendPacket(MSG_CHANNEL_CLOSE, struct.pack('>L',
|
| - self.channelsToRemoteChannel[channel]))
|
| - channel.localClosed = True
|
| - if channel.localClosed and channel.remoteClosed:
|
| - self.channelClosed(channel)
|
| -
|
| - # methods to override
|
| - def getChannel(self, channelType, windowSize, maxPacket, data):
|
| - """
|
| - The other side requested a channel of some sort.
|
| - channelType is the type of channel being requested,
|
| - windowSize is the initial size of the remote window,
|
| - maxPacket is the largest packet we should send,
|
| - data is any other packet data (often nothing).
|
| -
|
| - We return a subclass of L{SSHChannel}.
|
| -
|
| - By default, this dispatches to a method 'channel_channelType' with any
|
| - non-alphanumerics in the channelType replace with _'s. If it cannot
|
| - find a suitable method, it returns an OPEN_UNKNOWN_CHANNEL_TYPE error.
|
| - The method is called with arguments of windowSize, maxPacket, data.
|
| -
|
| - @type channelType: C{str}
|
| - @type windowSize: C{int}
|
| - @type maxPacket: C{int}
|
| - @type data: C{str}
|
| - @rtype: subclass of L{SSHChannel}/C{tuple}
|
| - """
|
| - log.msg('got channel %s request' % channelType)
|
| - if hasattr(self.transport, "avatar"): # this is a server!
|
| - chan = self.transport.avatar.lookupChannel(channelType,
|
| - windowSize,
|
| - maxPacket,
|
| - data)
|
| - else:
|
| - channelType = channelType.translate(TRANSLATE_TABLE)
|
| - f = getattr(self, 'channel_%s' % channelType, None)
|
| - if f is not None:
|
| - chan = f(windowSize, maxPacket, data)
|
| - else:
|
| - chan = None
|
| - if chan is None:
|
| - raise error.ConchError('unknown channel',
|
| - OPEN_UNKNOWN_CHANNEL_TYPE)
|
| - else:
|
| - chan.conn = self
|
| - return chan
|
| -
|
| - def gotGlobalRequest(self, requestType, data):
|
| - """
|
| - We got a global request. pretty much, this is just used by the client
|
| - to request that we forward a port from the server to the client.
|
| - Returns either:
|
| - - 1: request accepted
|
| - - 1, <data>: request accepted with request specific data
|
| - - 0: request denied
|
| -
|
| - By default, this dispatches to a method 'global_requestType' with
|
| - -'s in requestType replaced with _'s. The found method is passed data.
|
| - If this method cannot be found, this method returns 0. Otherwise, it
|
| - returns the return value of that method.
|
| -
|
| - @type requestType: C{str}
|
| - @type data: C{str}
|
| - @rtype: C{int}/C{tuple}
|
| - """
|
| - log.msg('got global %s request' % requestType)
|
| - if hasattr(self.transport, 'avatar'): # this is a server!
|
| - return self.transport.avatar.gotGlobalRequest(requestType, data)
|
| -
|
| - requestType = requestType.replace('-','_')
|
| - f = getattr(self, 'global_%s' % requestType, None)
|
| - if not f:
|
| - return 0
|
| - return f(data)
|
| -
|
| - def channelClosed(self, channel):
|
| - """
|
| - Called when a channel is closed.
|
| - It clears the local state related to the channel, and calls
|
| - channel.closed().
|
| - MAKE SURE YOU CALL THIS METHOD, even if you subclass L{SSHConnection}.
|
| - If you don't, things will break mysteriously.
|
| - """
|
| - if channel in self.channelsToRemoteChannel: # actually open
|
| - channel.localClosed = channel.remoteClosed = True
|
| - del self.localToRemoteChannel[channel.id]
|
| - del self.channels[channel.id]
|
| - del self.channelsToRemoteChannel[channel]
|
| - self.deferreds[channel.id] = []
|
| - log.callWithLogger(channel, channel.closed)
|
| -
|
| -MSG_GLOBAL_REQUEST = 80
|
| -MSG_REQUEST_SUCCESS = 81
|
| -MSG_REQUEST_FAILURE = 82
|
| -MSG_CHANNEL_OPEN = 90
|
| -MSG_CHANNEL_OPEN_CONFIRMATION = 91
|
| -MSG_CHANNEL_OPEN_FAILURE = 92
|
| -MSG_CHANNEL_WINDOW_ADJUST = 93
|
| -MSG_CHANNEL_DATA = 94
|
| -MSG_CHANNEL_EXTENDED_DATA = 95
|
| -MSG_CHANNEL_EOF = 96
|
| -MSG_CHANNEL_CLOSE = 97
|
| -MSG_CHANNEL_REQUEST = 98
|
| -MSG_CHANNEL_SUCCESS = 99
|
| -MSG_CHANNEL_FAILURE = 100
|
| -
|
| -OPEN_ADMINISTRATIVELY_PROHIBITED = 1
|
| -OPEN_CONNECT_FAILED = 2
|
| -OPEN_UNKNOWN_CHANNEL_TYPE = 3
|
| -OPEN_RESOURCE_SHORTAGE = 4
|
| -
|
| -EXTENDED_DATA_STDERR = 1
|
| -
|
| -messages = {}
|
| -for name, value in locals().copy().items():
|
| - if name[:4] == 'MSG_':
|
| - messages[value] = name # doesn't handle doubles
|
| -
|
| -import string
|
| -alphanums = string.letters + string.digits
|
| -TRANSLATE_TABLE = ''.join([chr(i) in alphanums and chr(i) or '_'
|
| - for i in range(256)])
|
| -SSHConnection.protocolMessages = messages
|
|
|