5

So, I made this API which logins to the system and Used it in an android app, there was one roadblock to it, that everytime user enters a password, it has to match the password hash so I, excitingly, used password_verify($password,$passwordHash), unknowingly that it is fucking unsafe and the code is still there, and here's where it gets interesting it is not over SSL/TLS. Fuck me, any bright solutions?

Comments
  • 0
    Whats unsafe about it?
  • 0
    @trickory $password is going over no. SSL protocol and in plain text
  • 4
    @nothappy it sounds like password_verify is not the solution. How else are you supposed to verify the password? You need to set up an SSL.
  • 4
    So... the code isn’t unsafe.
    strap an SSL cert on top of the server and fix your problem.
    If your running Apache/Nginx get your self “CertBot” and the problem will go away quickly.
  • 0
    @C0D4 yes but the code it's still a patch, a hack
  • 3
    @nothappy how? If that’s the PHP7 password verifier then what’s wrong with it?

    If it’s your own incarnation of it, then there’s probably a problem.
  • 0
    @CodeMonkeyG yes obviously password_verify() isn't solution, I really don't want any major code change cos then I'll have to rewrite the whole thing in website
  • 0
    @C0D4 I don't get your point
  • 3
    @nothappy
    If you’re using this function in PHP
    http://php.net/manual/en/...

    How do you see it as hacky code?

    Your problem - from what you have described is you don’t run an SSL cert on your server containing the login api. Which is quickly fixed by adding a cert.
  • 0
    @C0D4 yes I get the point but matching password with hash is quite hacky
  • 4
    Its simple, store the password in database with something likr a salted sha512 hash, then when a user attempts to login, ypu transfer his plain text password (over tls/ssl) and hash that with the samr salted sha512 and then compare the hashes, if they match... bingo
  • 0
    @InterferenceObj but that's the thing with sha it never generates same hash for same text,
  • 0
    @nothappy then how do you suppose you are going to confirm that the plaintext version is correct against a hashed password?

    Unless you use AES or something to literally encrypt the password but you will still end up doing a comparison either way.

    I think I need a better idea on how you find this a hacky solution.

    Or are you concerned with the plaintext being shipped to the API in the first place - even if you had SSL?

    - don’t get me wrong, I’m just trying to understand what you actually mean so I can offer some reasonable advise.
  • 3
    @nothappy :/ i think your using it wrong then
  • 2
    The best solution doesn't rely on third-party solutions like SSL to obscure the cleartext password.

    Instead: One-way-hash the password on the client. Salt and re-hash on the server, then compare. This way only the client ever sees the cleartext password, so even a MITM attack will not work. SSL on top of this of course further complicates attempted attacks. Database leaks are also less helpful to attackers, since the password hashes it contains are double-hashed with salt. (This doesn't increase the difficulty of logging into your service (db leak -> bruteforce hashes -> obtain hashed password -> login), but does exponentially increase the difficulty of recovering the cleartext password, thus protecting the user from their transgression of password reuse.)

    The only clientside attack surface (minus keyloggers/etc.) here is recording all client traffic, breaking the SSL if present, then brute-forcing the intercepted hashes with the known clientside hashing algorithm -- very expensive.
  • 0
    Why exactly do you think do browsers warn when logging in over unencrypted connections?
  • 4
    @Root if you always hash the password on the client before transmitting, then effectively, that hash IS the password.
  • 1
    @Fast-Nop Correct. but it obscures the password, protecting the user from password reuse.
  • 3
    @Root but with that, we are back to square one - unencrypted effective password over an unencrypted connection which makes MITM possible. Security by obscurity is a dangerous road.

    Even with a challenge-response architecture like in the good old CHAP, the problem would remain how to initially share the secret.
  • 1
    @C0D4 Store it in plain text of course. It should be sent over SSL but stored and verified in plain text. Haven't you read the latest articles?
  • 3
    @CodeMonkeyG haha ๐Ÿ˜‚
    I’m glad I know your not being serious right now ๐Ÿ˜ or are you? ๐Ÿคจ

    @Root’s approach would work too with doing a hash at app side then shipping it to API with a rehash and stored salt (hash), granted its obscurity, but the original “plain text” password is never exposed.
  • 1
    @C0D4 if there is a MITM problem, the fact that the transmitted hash would be the same at the second time would reveal that it's effectively the password.
  • 2
    @C0D4 of course I'm kidding. I'm crazy not stupid.
  • 1
    @Root @Fast-Nop

    You can do it a little better:

    1. server generates random bits (rb) and sends it to client along with salt.

    2. client sends to server: hash( hash(psw+salt) + rb )

    3. server: hash(storedPsw + rb) == receivedPswFromClient

    Sure MITM can still bruteforce password, but that might take long time and without bruteforce it prevents reusing hash to login and hides the plaintext password.
  • 1
    My previous comment was just a comment to an ongoing discussion, and not a solution to OP's problem.

    I'm not a PHP dev, but I doubt that the function is the problem, the problem is that you are not using TLS for the connection , as stated before.
  • 1
    @sSam I know, that's about what CHAP does that I referred to above. The problem is: how does the server initially even get the hash of PW+Salt when the connection isn't encrypted?
  • 1
    @Fast-Nop yeah, my bad, I wasn't aware of CHAP, was going to read about it, but forgot.
Add Comment