Just for this case, where authentication of the server isn't an issue,
and things like deployment cost are,
i'd like to propose that we on this list look again at securing
login/pass through onewayHash functions, in an otherwise non-ssl
environment.
i hate to be a critic of the community here, but isn't this insistence
on SSL a bit eh... lazy?
here's a starter for a onewayHash-based login crypto:
and think that with a proper layout of authentication architecture, one
can really secure a login system without having the administrative
overhead of installing SSL everywhere, and the monetary cost for a SSL
certificate for each domain.
I wish to code such a solution into a really-free library (so probably
LGPL or GPL + MIT) over the next 2 to 5 months.
This library would be a complete SQL, PHP & javascript package (jQuery
"plugged in"), targetted for the novice programmer.
I'm halfway (or more?) there, i think.
For my own CMS, i have taken the following approach, which i'd like to
hear your improvements on:
(For onewayHash() i have MD5 and SHA256 implementations in both JS and
PHP..)
//// SQL:
create table users (
user_id integer,
user_login_name varchar(250),
user_login_hash varchar(250),
user_password_hash varchar(250),
....other fields....
primary key (user_id)
);
create table preferences (
pref_system_hash varchar(250)
....
);
//// PHP (pseudo-code) , on system installation:
preferences.pref_system_hash = onewayHash ( randomStringLength(100) );
//// PHP , on user-create:
users[user_id].user_login_hash = onewayHash(user_login_name +
preferences.pref_system_hash);
users[user_id].user_password_hash = onewayHash ("someGooodPasswordNot"
+ preferences.pref_system_hash);
//// PHP, on request of a login form:
challenge = makeNewChallenge ();
//checks since when [browser IP] has last received a new
challenge, if < threshold : make a new challenge. else return old
challenge.
//a challenge is a random string (+ special chars) pushed through
the onewayHash function.
html = '
<form id="loginForm">
<input type="hidden" id="sh" name="sh"
value="preferences.pref_system_hash">
<input type="hidden" id="ch" name="ch" value="challenge">
<input id="plain_user" name="plain_user"/>
<input id="plain_pass" name="plain_pass"/>
<input type="hidden" id="user_hash" name="user_hash"/>
<input type="hidden" id="pass_hash" name="pass_hash"/>
</form>
';
sendHTMLtoBrowser (html);
//// Javascript: on page with login form:
jQuery('#loginForm').submit (function () {
var sh = jQuery('#sh')[0]; //same for ch, plain_user,
plain_pass, all the inputs in the html form.
....
user_hash = onewayHash ( onewayHash ( plain_user.value +
sh.value ) + challenge );
//same for pass_hash basically
plain_user.value = ''; //clear out the plain text fields so
they dont get transmitted (same for plain_pass ofcourse)
jQuery.ajax ( /* submit login form through POST, handle results
*/ )
}
//// PHP, on receiving the login form data:
// walk through all the records in users table, for each, calculate:
user_hash = onewayHash ( users[user_id].user_login_hash +
challenge );
pass_hash = onewayHash ( users[user_id].user_password_hash +
challenge );
// if they match what was sent, then it's the user we're looking
for with the right password, so their $_SESSION['authenticated_user'] =
updated.
////
If you have a completely alternative way of securing a non-ssl login
form, i'd like to hear about it too.
Michael A. Peters wrote:
Colin Guthrie wrote:
'Twas brillig, and German Geek at 15/02/09 22:32 did gyre and gimble:
Please enlighten me why it is so expensive? Is it maybe just the
hassle of
setting it up?
The whole thing is about trust. Getting a certificate is nothing if
the system is not backed up by a trust system. If a CA was setup that
gave out certificates willy nilly to all and sundry, then this
element of trust is lost.
Cheap CA's do exist. They have crappy web sites and send you all kinds
of junk mail etc. if you use them - but they do exist.
I might end up just paying godaddy - I think they charge $12.00 /
year, but since I already register through them, they already have my
address etc.
But the problem I have with FF3 is that I shouldn't have to.
I don't need to prove to the user that I am really me, and I don't
want to use a cert that some other organization has control over and
can choose to revoke at any time. I just the flipping password
encrypted by SSL so that when Betty who uses the same password for
everything (it's amazing how many people do) logs onto my server while
she has coffee at Starbucks, her uname/password isn't sniffed giving
Cracker Jack access to Betty's PayPal account.
If Cracker Jack wants to do a man in the middle attack - as long as
Betty has already connected to me before, her browser will still
inform her that the certificate doesn't match - whether or not I am
self signed, so the man in the middle attack is really not the big
deal FireFox makes it out to be.
What they should do is a simple notification telling the user they
can't verify the website is who it claims to be, and a link for more
info if the user wants more info.
But alas, that has nothing to do with php, so I apologize to the list.
Anyway, back on topic - if you want to encrypt login, use SSL.
You can self sign for free.
If you don't want the FireFox 3 issue, there are a few free and plenty
of cheap certificate authorties that FireFox recognizes.
--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php