~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/transport/ssh.py

Merge from bzr.dev

Show diffs side-by-side

added added

removed removed

Lines of Context:
172
172
    signal.signal(signal.SIGINT, signal.SIG_IGN)
173
173
 
174
174
 
175
 
class LoopbackSFTP(object):
 
175
class SocketAsChannelAdapter(object):
176
176
    """Simple wrapper for a socket that pretends to be a paramiko Channel."""
177
177
 
178
178
    def __init__(self, sock):
179
179
        self.__socket = sock
180
180
 
 
181
    def get_name(self):
 
182
        return "bzr SocketAsChannelAdapter"
 
183
    
181
184
    def send(self, data):
182
185
        return self.__socket.send(data)
183
186
 
184
187
    def recv(self, n):
185
 
        return self.__socket.recv(n)
 
188
        try:
 
189
            return self.__socket.recv(n)
 
190
        except socket.error, e:
 
191
            if e.args[0] in (errno.EPIPE, errno.ECONNRESET, errno.ECONNABORTED,
 
192
                             errno.EBADF):
 
193
                # Connection has closed.  Paramiko expects an empty string in
 
194
                # this case, not an exception.
 
195
                return ''
 
196
            raise
186
197
 
187
198
    def recv_ready(self):
 
199
        # TODO: jam 20051215 this function is necessary to support the
 
200
        # pipelined() function. In reality, it probably should use
 
201
        # poll() or select() to actually return if there is data
 
202
        # available, otherwise we probably don't get any benefit
188
203
        return True
189
204
 
190
205
    def close(self):
237
252
            sock.connect((host, port))
238
253
        except socket.error, e:
239
254
            self._raise_connection_error(host, port=port, orig_error=e)
240
 
        return SFTPClient(LoopbackSFTP(sock))
 
255
        return SFTPClient(SocketAsChannelAdapter(sock))
241
256
 
242
257
register_ssh_vendor('loopback', LoopbackVendor())
243
258
 
347
362
            argv = self._get_vendor_specific_argv(username, host, port,
348
363
                                                  subsystem='sftp')
349
364
            sock = self._connect(argv)
350
 
            return SFTPClient(sock)
 
365
            return SFTPClient(SocketAsChannelAdapter(sock))
351
366
        except _sftp_connection_errors, e:
352
367
            self._raise_connection_error(host, port=port, orig_error=e)
353
368
        except (OSError, IOError), e:
601
616
    def send(self, data):
602
617
        return os.write(self.proc.stdin.fileno(), data)
603
618
 
604
 
    def recv_ready(self):
605
 
        # TODO: jam 20051215 this function is necessary to support the
606
 
        # pipelined() function. In reality, it probably should use
607
 
        # poll() or select() to actually return if there is data
608
 
        # available, otherwise we probably don't get any benefit
609
 
        return True
610
 
 
611
619
    def recv(self, count):
612
620
        return os.read(self.proc.stdout.fileno(), count)
613
621