Man in the middle attack in LAN - security

I am pretty new in this kind of things.
I have a local area network, accessed by some users via cable some and via wifi others.
I have developed a local application in php which receives only some of the LAN clients as authentic users; they can be identified by the system with an algorithm of key exchange similar to Diffie–Hellman's, to estabilish a secret key. The client then asks to be identified throug such a channel.
The problem is, MITM attack is possible in this kind of situation. I read wikipedia about how such an attack is executed: somebody listens the messages of the two, and puts himself between them creating two different secret keys for the client and server.
This attack is reality, so it must be possible; but I do not understand how it happens in a LAN:
the attacker can listen to the messages, and inject message of his own, impersoning the two subjects of the communications by forging https' IP fields if necessary...
But he can't prevent the original unforged message to reach, concurrently (but also later, because of forging process taking the attacker computer some time) with his malevolent forged one, the recipient! Especially in a wifi connection, which cannot be cut off for a single user, for example cutting his cable.
So, client and server receive two different http requests from each other, a true and a forged one; isn't this a way for them to recognize that such an attack is in progress?
Maybe this question is newby-ous; as I said, I am pretty new at this.

I think that is a scenario where you would use a digital signature (which also uses the idea that asymmetric encryption/Diffie-Hellman uses, that is "public and private key") to sign your messages.
The MITM attacker can not forge a message with a bad "from" and then sign it with the private signature of the original sender. The recipient uses the public part of the signature/certificate to validate the message. So that way he will not only know he is being attacked but also which message is genuine.

Related

Message level encryption

I’m trying to implement a message level encryption. Here is the current situation:
We have a mobile app client connects to server via oneway certificate https and we have username/password authentication and secure token for subsequent client to server invocations. So intention of message level encryption is not try to prevent 3rd part sniffing information or stealing client identity, instead to prevent the client user him/her self to something like,
1) Inspect and try to understand server - client protocol
2) Forgery request with other application than our app client
The initial idea is to use symmetric algorithm (DES, AES, or some simpler algorithm, as long as it could not be simply cracked by statistical or mathematical method without knowing the key). And the key is generated from a hash (SHA etc) from a string concatenated from a salt pre-agreed between client and server, and some information server tell client in non-encrypted content (for instance, the first call from client to server happens in non-encrypted context, and server returns a timestamp to client and also remember it for later key generating).
Does this do what I want to do for 1&2? And what is the major vulnerability if any?
There is no "secure" solution to what you try to achieve as long as you publish your software, because any key you use for the message level encryption will have to reach your software somehow. Either it is compiled into it, then a dedicated attacker can read it out of the binary, or it is transferred to the running software using the network, then the attacker can emulate the protocol your software is using to get the key.
The best you can hope for is to make it difficult for a reverse engineer to get to the key. That means you could assemble it in such a way that no complete piece of it can be found in the binary. But still if someone attaches a debugger at runtime she could still read it out of a variable trivially. In the end it remains an arms race between you and the reverse engineer.

Encrypted and authorized multicast

I have a server (will be noted as 'A') that transmits multicast to some end stations.
I would like only those that are privileged to see the information, to actually see it.
There is a third party server ('B') that manages unicast communications with both 'A' and the end stations and SSL with both of them.
My goal is to implement a secured multicast:
Two necessary givens:
It has to be multicast.
I want the security in the Application level (not the Network or Transport)
Questions:
Are there such implementations? I've tried searching for "secured multicast" etc. and have come across only IP Multicast security. I want an applicative implementation. If so, Could you recommend some and how to use them?
I thought about generating a special symmetric key - during the communication of 'A' and 'B' and during the conversation of 'B' and end station = to pass it (over SSL) to the end stations.
a. Is that a good idea?
b. A problem I see is that revealing the key becomes easier because of the amount of stations. I thought about replacing the key every hour. I shall inform the stations the key has changed by sending multicast messages: (sequence_number, encrypted_message) - this way every time the key changes then sequence_number++.
What do you think of the implementation? Have better ideas?
I wrote an app called UFTP (http://uftp-multicast.sourceforge.net) that does exactly this.
In terms of key management, each multicast session performs a TLS-like key exchange between the sender and each receiver, then uses the negotiated key for each receiver to send out the group key which is used to encrypt the data. By doing key negotiation for each session, this eliminates complications related to re-keying mid session.
Authentication is done via key fingerprinting, with fingerprints being communicated out-of-band. This is simpler than a certificate based system and minimizes overhead. Each sender and receiver has an RSA or ECDHA key they are identified by.
What you describe is a simple application of PKI:
Each station creates an RSA keypair and sends its public key to the server.
The server generates a random symmetric key and encrypts the multicast message using this symmetric key. New symmetric key should be generated for each message but usually it's not a big deal.
The symmetric key is encrypted using each station's public RSA key. Products of all such encryptions (i.e. encrypted session keys) are merged with encrypted data and compose the multicast packet.
Unfortunately such scheme will cause a significant extra data load on the multicast message, but this is caused by length of keys and the length can't be reduced without sacrificing security.

How long is an open, secure, TCP channel secure?

We have a web service that acts as a gateway between our clients and another service. The clients send messages to, and receive random messages from, the third-party service. The client's server opens a channel to our web server via a secure socket in order to receive the incoming messages (and not have to poll the server every few minutes).
My question is: is it safe to leave this channel open indefinitely, or should we periodically close and re-open it to obtain new credentials (session keys)? If the latter, how often (hourly, daily, weekly) would be considered "best practice"? I've found a lot of information on secure communications, but nothing to answer this specific question.
Thanks
SSL/TLS (which I'm going to assume you're talking about here) does NOT automatically refresh/renegotiate the session keys being used. There is a renegotiation procedure built-in to the protocol to allow the session keys to be changed within an active session but that procedure was found to have a significant vulnerability a few years back and the renegotiation process was changed (in RFC 5746, see here) to resolve the problem. If you do want to renegotiate the session keys for SSL/TLS, make sure you're doing it in the manner described in this RFC.
That does not, however, answer your original question of IF the session keys should be changed. The answer is...it depends on your security requirements. A good guideline to be used is that any encrypted communications can be eventually decrypted if you see enough of the encrypted data (how practical/doable this is can vary wildly). So, changing your keys every so often is a very good thing to do. If you're passing a small amount of data over a secured connection and the data isn't that sensitive, then you can get away with doing this on a not-so-regular basis (indeed, your SSL/TLS session is probably going to get broken and restablished due to timeouts on one of the two parties on a somewhat regular basis anyway...). If you've got a very sensitive dataset and you're sending alot of data, then I'd suggest rotating the keys every day or so to mitigate this risk (just do it in a secure manner).

How to resist MITM and replay attacks when sending encrypted data?

Assuming I've securely exchanged keys with another computer (using Diffie-Hellman perhaps), here's my tentative solution:
packet number + encrypted data + message authentication code (MAC)
The packet number is an incrementally-increased number starting at 0. After that is the encrypted data itself, followed by a MAC of them both. If someone attempts a MITM attack, the MAC should fail to compute. If they attempt a replay attack, the recipient will notice it has already received that packet number.
Is there any flaw in my reasoning here?
Assuming I've securely exchanged keys with another computer (using Diffie-Hellman perhaps)
This is where you face the biggest danger - if the man-in-the-middle manages to control the key exchange (for example, by establishing one key with the client and itself, and establishing another key with server and itself), then the MITM can decrypt (and re-encrypt) everything. Once you've established the secure key exchange, you should be invulnerable to the MITM attack. But the hard part is ensuring that the key exchange is truly secure.
Consult Practical Cryptography (or at Amazon) by Ferguson and Schneier for information about this.
You're not describing a man in the middle attack, but a replay attack.
With a MITM attack the key exchange is intercepted and you say that you already have exchanged keys securely - so it is not the problem.
Replay attacks are easy enough to mitigate against, you include a unique message ID and then check it for uniqueness on the receiving side. Generally each message has an expiry date and time so you don't need to keep an ever growing list of message IDs to validate.
Your approach for protecting against replay attacks seems reasonable to me. You are essentially describing a method called timestamping. Your packet number is a "virtual time" that is used by the recipient to verify that the message was not sent before.
Once the keys have been exchanged then the data cannot be intercepted or spoofed by a third party. (Except when your packet # counter loops. Hypothetically packets from the old window could be replayed as being from the new window.) The solution to this problem is timestamping (as others have mentioned.) Again, though, this can be sabotaged if the attacker is able to compromise in some way the system time. (If they are a man in the middle, they could hypothetically imitate an NTP server and in that way modify a client's system time.)
What an eavesdropper COULD do however is to insert himself between the two parties and disrupt the channel. This would likely cause a new key exchange to occur which could be observed. In order to make key exchange truly secure, you must use 3rd party validation or a pre shared key which only the two communicators know.

Is this scenario secure?

I'm using RSA to encrypt communication between a server and a client.
Lets say we have 2 Asymetric keys, key 1 and key2.
The server has key1 (Private) from the start and the client has the key1(public)
So here is the scenario:
the client generates key2
client connects to the server
sending key2(public) encrypted with key1(public)
from now on the server will send all data encrypted with the key2(public)
the client sends some random data to the server
the server sends back the same data hashed
the client verifies that the data is right
As far as I can see this should prevent a man-in-the-middle attack, or am I missing something?
At point 7 the client should know if someone is trying to give the server the wrong key to encrypt with, as no one else but the server can decrypt key2(public).
If there is anything that can be done to improve the security please tell me.
The best thing you can do to improve the security is to use an existing design and not try to reinvent the wheel. I'm not saying that what you've done is necessarily wrong, but just that many people much smarter than you and me have spent a lot of time thinking about this problem. Use TLS instead.
As long as key1 (private) has not been intercepted somehow by a third-party, your scenario looks secure.
I think I saw this somewhere in a paper actually. In it, Alice gave Bob an unlocked box (key 1 public), then Bob put a bunch of his own boxes (key 2 public) in it, locks it and sends it back to Alice. Alice then opens the box(key 1 private), and now she can securely seal the boxes that Bob just gave her.
Despite the box analogy, that's essentially what you're doing, so I'd say its secure.
I agree, just use TLS.
Also, what value do steps 5 through 7 provide? A MITM wanting to do an attack that would work after steps 1-4 (e.g. DoS of some sort by passing n transactions through and then stopping, forcing a retry from the start) could do so just as well after 5-7. What do they add?
-- MarkusQ
No, this protocol is not safe.
A man-in-the-middle can intercept the data sent by the client and send whatever it wants to the server, since you haven't specified any mechanism for the server to authenticate the client or verify the integrity of messages it receives.
Sure, you could doctor up your protocol to fix these glaring problems, but there would be others. If you ever fix them all, you'd have something that maps to TLS or SSH, so why not just start there?
#Petoj—the problem I was focusing on was that of the server trusting the messages it receives; your proposal doesn't provide any security there. However, if you are worried about confidentiality, you still have a problem, because the MITM could pass messages back and forth unaltered until he sees what wants to find because you don't have any privacy on the client messages.
Your proposal seems to be aimed at ensuring the integrity of messages from the client. You've developed the protocol to the point where the client can't distinguish between an attack and a network failure. Rather than trying to help the client determine whether the server acted on a tampered message, allow the server to verify the integrity of the message before acting on it.
I will agree with Greg that you are reinventing the wheel. What you are essentially describing is some basic form of key exchange. Incidentally, in order to ensure that it is secure against man-in-the-middle attacks you must also be certain of the server's identity, i.e. ensure that the client can know with certainty that what it believes to be public(key1) really is the server's and not the man-in-the-middle's (e.g. using a CA or having the server's public(key1) in secure storage on the client side.)
Moreover, there are additional considerations you must be aware from a systems standpoint, such as:
asymmetric key encryption is slower than symmetric key encryption, which is one of the reasons why existing solutions such as TLS will use asymmetric key encryption only to negotiate a temporary symmetric key, which is then used for channel encryption.
if traffic analysis by a third-party succeeds in cracking a temporary symmetric key, you have not compromised you asymmetric key pair. You are encouraged to re-negotiate the temporary key relatively often for this reason. Arguably, generating a new key2 in your scenario would mitigate this aspect.

Resources