I'm developing a system where mobile applications communicate with server through HTTPS. The communication consists of two phases: at first, app "registers" at server: among other stuff, user chooses his PIN and it's being sent to server and stored there. Let's for now assume that this phase is secure and all information has been exchanged securely and no information was leaked.

The second phase of communication begins after the registration. App sends requests to server, and with each request user is requested to enter PIN which is added to the request in order to authenticate the user (it's actually just one of authentication steps as we also use client cert authentication). My question is as follows: is it possible to prevent this PIN from being exposed in case of an attacker being able to decrypt our HTTPS communication? Most solutions seem to fail because the attacker is able to enumerate PINs as they are usually about 4-6 characters long (for example passing through a hash of PIN fails because of this).

We can exchange some additional data in registration phase, as needed.


You could implement your own layer of encryption in addition to the one that TLS provides. Since you say that "we can exchange some additional data in registration phase" I think the easiest solution would be to share a symmetric encryption key (e.g. AES) during registration and then encrypt all further communication with that. (The IV will prevent brute force even if there are only a limited number of possible plain texts.)

Please do note that this rests entierly on the security of the original conection when PIN and key are exchanged. If that fails, this scheme fails. Another option would be to ship the application with your public key hard coded into it. Have the app generate a random symmetric key, encrypt it asymmetrically with your public key and send it to the server. This can be done either just once, or once per session. But now we are starting to build a complete cryptographic protocol...

This would be some work, and maybe not worth the effort. The main threat is probably not TLS breaking anyway, but the users phone being infected with malware or your server being hacked.

Instead, I would advice you to get the TLS right so that an attacker is never able to decrypt it in the first place. In the case of a mobile app, where you have control over both the client and the server, this is easier to do than for a web app. I recommend these steps:

  • Pick a small set safe cipher suits and only allow the client and server to accept those
  • Only allow TLS 1.2 (or higher)
  • Implement public key pinning
  • Yes, of course; however we're trying to be safe even in case of TLS failing. – poe123 Jun 30 '16 at 12:10
  • @poe123, TLS isn't nearly as likely to fail as the security of the machines at either end of the connection. Is it worth investing much? – John Deters Jun 30 '16 at 12:17
  • @poe123 I edited my question with a more concrete suggestion on how to do that. – Anders Jun 30 '16 at 12:18
  • @Anders Thank you, that sounds like a reasonable solution. I was thinking about using a symmetric key to encrypt just the PIN, but since we'd have to exchange the key anyway we could just as well encrypt the entire thing. – poe123 Jun 30 '16 at 12:31
  • 1
    What I was trying to say (poorly) is that instead of investing $10,000 in crypto algorithm development and testing, consider the value of investing that same $10,000 in improving your network security. I see far more problems caused by hackers than I do people dissecting encryption protocols. It's an easy trap to fall into, spending money where it's less important to the overall goals of the organization. – John Deters Jun 30 '16 at 14:51

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.