Twisted Conch - Server/Client - python

I'm looking to create a Twisted Conch Server/Client SSH application similar to the below:
Client <---Key1---> Server/Client <---Key2---> Server
I guess it's like an SSH MITM or command proxier.
I have read the answers to similar Twisted related questions, such as:
Twisted server-client data sharing
and I understand the theory behind passing client/server data.
The part I am unsure of is the user authentication. I want to pass the login details from the first client, through my twisted conch application to the endpoint server.
Is there a way to do this?
Also, would it be possible to do separate SSH key negotiations but then pass all data, including credentials and any commands typed, between server and client?

Unfortunately, this is a little more complicated than it seems. SSH goes through some pains to try and avoid this kind of MITM. If you don't use the same key negotiation, the publickey authentication won't succeed because string you're signing is different on both sides of the connection (see the RFC section 7 for more).
Password authentication should still work okay, though. The easiest way to do that would be to create a twisted.conch.ssh.session.SSHSession subclass which listens for packets on the packetReceived method and forwards them to the corresponding transport.sendPacket.

Related

Only allow connections from custom clients

I'm writing a Socket Server in Python, and also a Socket Client to connect to the Server.
The Client interacts with the Server in a way that the Client sends information when an action is invoked, and the Server processes the information.
The problem I'm having, is that I am able to connect to my Server with Telnet, and probably other things that I haven't tried yet. I want to disable connection from these other Clients, and only allow connections from Python Clients. (Preferably my custom-made client, as it sends information to communicate)
Is there a way I could set up authentication on connection to differentiate Python Clients from others?
Currently there is no code, as this is a problem I want to be able to solve before getting my hands dirty.
When a new connection is made to your server, your protocol will have to specify some way for the client to authenticate. Ultimately there is nothing that the network infrastructure can do to determine what sort of process initiated the connection, so you will have to specify some exchange that allows the server to be sure that it really is talking to a valid client process.
#holdenweb has already given a good answer with basic info.
If a (terminal) software sends the bytes that your application expects as a valid identification, your app will never know whether it talks to an original client or anything else.
A possible way to test for valid clients could be, that your server sends an encrypted and authenticated question (should be different at each test!), e.g. something like "what is 18:37:12 (current date and time) plus 2 (random) hours?"
Encryption/Authentication would be another issue then.
If you keep this algorithm secret, only your clients can answer it and validate themselves successfully. It can be hacked/reverse engineered, but it is safe against basic attackers.

Client/Server role reversal with SimpleXMLRPCServer in Python

I'm working on a project to expose a set of methods from various client machines to a server for the purpose of information gathering and automation. I'm using Python at the moment, and SimpleXMLRPCServer seems to work great on a local network, where I know the addresses of the client machines, and there's no NAT or firewall.
The problem is that the client/server model is backwards for what I want to do. Rather than have an RPC server running on the client machine, exposing a service to the software client, I'd like to have a server listening for connections from clients, which connect and expose the service to the server.
I'd thought about tunneling, remote port forwarding with SSH, or a VPN, but those options don't scale well, and introduce more overhead and complexity than I'd like.
I'm thinking I could write a server and client to reverse the model, but I don't want to reinvent the wheel if it already exists. It seems to me that this would be a common enough problem that there would be a solution for it already.
I'm also just cutting my teeth on Python and networked services, so it's possible I'm asking the wrong question entirely.
What you want is probably WAMP routed RPC.
It seems to address your issue and it's very convenient once you get used to it.
The idea is to put the WAMP router (let's say) in the cloud, and both RPC caller and RPC callee are clients with outbound connections to the router.
I was also using VPN for connecting IoT devices together through the internet, but switching to this router model really simplified things up and it scales pretty well.
By the way WAMP is implemented in different languages, including Python.
Maybe Pyro can be of use? It allows for many forms of distributed computing in Python. You are not very clear in your requirements so it is hard to say if this might work for you, but I advise you to have a look at the documentation or the many examples of Pyro and see if there's something that matches what you want to do.
Pyro abstracts most of the networking intricacy away, you simply invoke a method on a (remote) python object.

is it possible to authenticate telnet automatically?

When using telnetlib I noticed some interesting variables:
AUTHENTICATION = chr(37) # Authenticate
XAUTH = chr(41) # XAUTH
PRAGMA_LOGON = chr(138) # TELOPT PRAGMA LOGON
SSPI_LOGON = chr(139) # TELOPT SSPI LOGON
Also, this page lists some RFCs which describe AUTHENTICATION option in detail.
If I understand correctly, if a telnet server supports authentication I should be receiving IAC DO AUTHENTICATION when connecting to it. However, when trying to connect to telnetd on a Linux machine I do not receive this option and so I can't send IAC WILL AUTHENTICATION.
Is my understandng correct? Is there a way I can ask the server to perform authentication? Is it even possible to authenticate telnet session automatically? (without listening to "Login:", "Username:", "Password:" and similar prompts)
Yes, you are understanding RFC 1416 correctly. The server should send DO first, if it supports authentication. You can try sending WILL anyway but that'll be against the spec and probably won't work anyway.
By Linux telnetd, you probably mean the netkit telnetd. And as far as I can see on its manpage:
-a authmode This option may be used for specifying what mode should be used for
authentication. Note that this option is only useful if telnetd has
been compiled with support for authentication, which is not available
in the current version. [...]
So I'd simply say it can't do that. I'm using the OpenBSD telnetd (telnet-bsd package in Gentoo); it seems to have some auth bits but I wasn't able to get it to work at all. I suspect it only supports Kerberos-based auth.
Looking at the authentication types list in RFC 2941, it seems that most authentication types were never even specified. Looking at those which are, DSS/DSA is mostly interesting (it is used in SSH as well) but I guess it will be really hard to find a compliant server and client. Sadly, it seems that there were no proposals for simple (plaintext) authentications there.
So, to sum up: yes, it would be possible if someone implemented it. But since telnet is practically dead, I doubt you'll find server implementations for that. And even if you did, you'd have to write the client-side yourself which won't be that easy with the supported schemes. So I doubt it's worth the effort.

UDP server to forward messages between clients

I'm starting to write an udp server to match two clients together and allow them to send/receive data to/from each other.
It's for a multiplayer game, and my goal is to create a p2p-like connection but with the intermediary server I'll make sure it will always work, even in cases where the user has a firewall, or is behind a nat.
The server should hande several matches (pairs of clients), I'm writing it in python and it's a bit harder than what I thought.
Is there any open source code for a server similar to this?
Take a look at the ZeroMq (0MQ) framework as an alternative to creating your own messaging. There's a python binding (pyzmq) for it.
This details how to write a UDP server in Python.

Secure communication between servers

I'm writing a simple control panel. It's going to be hosted on a single server, which communicates with other servers to do whatever it needs to. I need suggestions on how to do this securely, both from an authentication and an encryption standpoint. The only thing I've come up with so far is to use RSA keys to encrypt data on the master server and decrypt it on the slave, which would accomplish what I need but something seems flawed about it.
Use SSH.
See also: What is the simplest way to SSH using Python?
Stunnel is pretty handy. I like it since the code doesn't need to deal with encryption at all.
You could use SSL with client/server certificate validation.
Validate SSL certificates with Python
We are developing Versile Python, if you need object-level interaction with python objects over a secure channel you may want to have a look. You can use TLS or VTS to negotiate secure connections using RSA keys, or you can connect over SSH.
Other python object interaction frameworks you may want to consider are Pyro and RPyC.

Categories

Resources