Initial import to Tizen
[profile/ivi/python-twisted.git] / twisted / conch / client / direct.py
1 # Copyright (c) Twisted Matrix Laboratories.
2 # See LICENSE for details.
3
4
5 from twisted.internet import defer, protocol, reactor
6 from twisted.conch import error
7 from twisted.conch.ssh import transport
8 from twisted.python import log
9
10
11
12 class SSHClientFactory(protocol.ClientFactory):
13
14     def __init__(self, d, options, verifyHostKey, userAuthObject):
15         self.d = d
16         self.options = options
17         self.verifyHostKey = verifyHostKey
18         self.userAuthObject = userAuthObject
19
20
21     def clientConnectionLost(self, connector, reason):
22         if self.options['reconnect']:
23             connector.connect()
24
25
26     def clientConnectionFailed(self, connector, reason):
27         if self.d is None:
28             return
29         d, self.d = self.d, None
30         d.errback(reason)
31
32
33     def buildProtocol(self, addr):
34         trans = SSHClientTransport(self)
35         if self.options['ciphers']:
36             trans.supportedCiphers = self.options['ciphers']
37         if self.options['macs']:
38             trans.supportedMACs = self.options['macs']
39         if self.options['compress']:
40             trans.supportedCompressions[0:1] = ['zlib']
41         if self.options['host-key-algorithms']:
42             trans.supportedPublicKeys = self.options['host-key-algorithms']
43         return trans
44
45
46
47 class SSHClientTransport(transport.SSHClientTransport):
48
49     def __init__(self, factory):
50         self.factory = factory
51         self.unixServer = None
52
53
54     def connectionLost(self, reason):
55         if self.unixServer:
56             d = self.unixServer.stopListening()
57             self.unixServer = None
58         else:
59             d = defer.succeed(None)
60         d.addCallback(lambda x:
61             transport.SSHClientTransport.connectionLost(self, reason))
62
63
64     def receiveError(self, code, desc):
65         if self.factory.d is None:
66             return
67         d, self.factory.d = self.factory.d, None
68         d.errback(error.ConchError(desc, code))
69
70
71     def sendDisconnect(self, code, reason):
72         if self.factory.d is None:
73             return
74         d, self.factory.d = self.factory.d, None
75         transport.SSHClientTransport.sendDisconnect(self, code, reason)
76         d.errback(error.ConchError(reason, code))
77
78
79     def receiveDebug(self, alwaysDisplay, message, lang):
80         log.msg('Received Debug Message: %s' % message)
81         if alwaysDisplay: # XXX what should happen here?
82             print message
83
84
85     def verifyHostKey(self, pubKey, fingerprint):
86         return self.factory.verifyHostKey(self, self.transport.getPeer().host, pubKey,
87                                           fingerprint)
88
89
90     def setService(self, service):
91         log.msg('setting client server to %s' % service)
92         transport.SSHClientTransport.setService(self, service)
93         if service.name != 'ssh-userauth' and self.factory.d is not None:
94             d, self.factory.d = self.factory.d, None
95             d.callback(None)
96
97
98     def connectionSecure(self):
99         self.requestService(self.factory.userAuthObject)
100
101
102
103 def connect(host, port, options, verifyHostKey, userAuthObject):
104     d = defer.Deferred()
105     factory = SSHClientFactory(d, options, verifyHostKey, userAuthObject)
106     reactor.connectTCP(host, port, factory)
107     return d