245

Upon reviewing the Logs generated by different SIEMs (Splunk, HP Logger Trial and the AlienVault platform’s SIEM) I noticed that for some reason quite a few users tend to make the mistake of typing their passwords in the username field, either in the OS Domain logon, or within web applications. I am guessing those are people who cannot type without looking at the keyboard and in trying to do so, doing it fast, end up typing their passwords in the wrong field. This means that the password is sent in plain text everywhere in the network and end up recorded on the logs with an event that says something along the lines:

User P@$$w0rd does not exist [...]

Or

An account failed to login: P@$$w0rd [...]

(where P@$$w0rd is the actual user's password)

It becomes pretty obvious to work out to whom the passwords belong: usually the previous or very next (un)successful event on the same log file will tell you an event triggered by the same user.

Any other Analyst, looking at the logs, could get someone else’s credentials without the due owner even being aware of that; the worst case scenario is network eavesdropping, or actual log file compromise.

I am looking for a general guidance to help preventing this. I assume simply masking the username is not feasible and even if it were, this would probably eliminate a lot of the log analysis for not being able to tell who did what.

Note: There is already a post on a similar issue, but I am trying to address a way to prevent it. What's the risk if I accidently type my password into a username field (Windows logon)?


Accepted Answer: I wish I could select a few answers from the list. Unfortunately I have to stick to just one in the forum, but in practice I can combine them. Thanks very much for all the answers; I see there is no single solution. As I agree that adding 'things' add complexity which increase likelihood of security holes, I have to agree with most of the voters that @AJHenderson has the most elegant and simplest answer as a first approach. Definitely SSL and a simple code verification on the server or even at the client side. As I am looking to mitigate not against malicious users, but the distracted ones, this will do fine. Once this is in place, we can start looking at expanding the implementation to ill-intended users if appropriate. Thanks ever so much again for everyone's input.

21
  • 7
    @SparKotॐ - the problem is that if you hash the username, without a common salt, it is exceedingly difficult to identify the user. With a common salt for the username, it becomes possible to do a rainbow table attack against the logs to find any misentered passwords. Commented Mar 5, 2013 at 17:31
  • 68
    Only log if the username exists in the db? Commented Mar 5, 2013 at 18:29
  • 6
    Those of us who can type without looking at the keyboard can make that mistake too. Usually we also don't actually need to look at the screen and if one is slightly distracted such a mistake is easy to make. This is the advantage of the windows XP Home edition and later interface where it is a menu of users to pick from. Of course, not useful with more than a handful of users.
    – ewanm89
    Commented Mar 5, 2013 at 18:58
  • 7
    This used to happen to me all the time, for the following reason: typically, when I unlock my computer, it remembers that I was the last user and only the password needs to be entered. I often [ctrl]-[alt]-[del] and enter my password before power is restored to my monitor. However, if my last login was via remote desktop, the username is cleared. Following my normal routine in this scenario results in the password being entered as the username.
    – Allan
    Commented Mar 5, 2013 at 20:47
  • 8
    I suddenly feel the need to change various passwords... Also, when I have done this in the past, often times what happens is I'm typing really fast and accidentally miss the "tab" key to move to the next field. In other words... An account failed to login: MikeSP@$$W0RD
    – MikeS
    Commented Mar 6, 2013 at 15:49

18 Answers 18

365
+500

One thought is to not allow form submission if there is not a value in the password box. Generally if they accidentally entered the password in the username, then there likely isn't going to be anything in the password dialog.

It is worth noting that this does not have to be simply done client side, but could also be done on a server as long as the transport used is secure and the input is not logged until after passing a check about the password field not being empty.

6
  • 3
    A bypassed javascript control would sent the username across the wire thats where the risk applies. It would be picked by something similar to wireshark and if its ssl it still would be e.g sslstrip thoughtcrime.org/software/sslstrip
    – Saladin
    Commented Mar 5, 2013 at 19:39
  • 10
    too bad we can't convince MS to implement this for the windows login dialog. Commented Mar 5, 2013 at 20:33
  • 27
    @asadz - yeah, it isn't a prevention against an attacker doing something, the question was just about what could be done to prevent passwords from ending up in log files by users making mistakes though. Commented Mar 5, 2013 at 21:18
  • 1
    @EricG - if you are logging every forum submission's Post data, that's going to be a lot of logging. I suppose you would still have to be careful with how you set things up, but I think that you could probably work around having it get logged as long as it doesn't actually try the authentication. Granted, it may not work in all systems. Commented Mar 7, 2013 at 4:04
  • 1
    Nowadays, many login dialogs ask for the username on page one and for the password on page two. For such dialogs, this solution sadly doesn't work.
    – gerrit
    Commented Jul 25, 2022 at 15:37
38

Assuming your backend application and SIEM needs to view failed login attempts to various applications (and thus show the "User P@$$w0rd is not valid" error message) then it is not going to be trivial to stop this.

However, ensuring that all applications that send sensitive data including usernames and passwords implement HTTPS (encrypted HTTP using SSL) is a good way to ensure that network devices and anyone on the network can not obtain the password that was mistakingly entered into the username box!

6
  • 1
    I guess ssl is a workaround not a code fix. Problems should be fixed at source at best.
    – Saladin
    Commented Mar 5, 2013 at 17:35
  • @asadz: the fact that the application shows the username when it is entered incorrectly is not an application bug, it is intended functionality and does not require a fix imo.
    – fixulate
    Commented Mar 6, 2013 at 9:34
  • @devcity2012 An intended functionality perhaps but poorly thought of; there is a part of requirements analysis in software engineering; this is where these things should be sough preferably using Sequence diagram;how come there is no check for a form before submission? Input validation void ?
    – Saladin
    Commented Mar 6, 2013 at 9:48
  • 1
    If the form takes a username and a password and both are present and then the backend is configured to display the username, that is not an application error if the user mistakingly enters his/her password in the username textfield.
    – fixulate
    Commented Mar 6, 2013 at 9:50
  • I'm talking it as a problem only in a sense where a request would be submitted just based upon user-name field?
    – Saladin
    Commented Mar 6, 2013 at 9:53
22

So the problem is that you don't want analysts to see the passwords in the sensitive log files?

Caution: Even if you were to use Javascript it doesn't deal with the password data that is stored on your disk in plain text.

A better solution is to preprocess the logs before the analysts see them and redact information in the logs.

You can do this line-by-line filtering if you whitelist lines or blacklist other lines. For example:

You can whitelist usernames when they appear in a log file that

  • Have a pattern ( [az] + number) or ([az] + period + [az])
  • include a Domain Name followed by a slash "\" for AD environments
  • appear multiple times
  • Can be washed against an LDAP directory of known usernames before the analysts see it

You also identify and blacklist passwords by:

  • The password policy often follows a pattern (one symbol, upper/lower, x characters...)

You can use this knowledge to build a custom log data cleanser to protect the information you don't want analysts to see.

So what does a filtered line look like?

You can simply redact questionable usernames by hashing them, and assigning them a human ID and storing them in a secure location:

 eb574b236133e60c989c6f472f07827b   Redact1
 7e67b89a695bfbffc05b7ed2c38f927f   Redact2
 ..etc

The analysts can see if a particular entry is occurring over and over again if the hash repeats in frequency.

The exact hashing method (or encryption method) you choose is subject to risks since this "hash database" will contain high value information. And seeding will (by its nature) prevent frequency analysis which may or may not be of value to you.

1
  • 4
    +1 it's a good idea to always assume that logs contain sensitive information unless explicitly redacted or until proven otherwise. Commented Mar 6, 2013 at 6:27
21

I can only identify three problems with what you're discussing.

  1. Users aren't inputting information correctly.
  2. Analysts can discern passwords from logs.
  3. Passwords are being sent in clear-text and are susceptible to man-in-the-middle eavesdropping.

In my opinion, this is fairly simple to fix.

  1. Accept user error, grudgingly.
  2. Don't log invalid usernames, instead log failed attempts and IP.
  3. Don't send usernames in clear-text. Use technology like HTTPS or use javascript to encode the plain-text (e.g. ROT13).

Example log of a failed login and then a successful retry.

[00:00:00] An account failed to login from 192.168.1.100
[00:21:00] Successful login 'root' from 192.168.1.100

Reading over other answers, I would like to include this.

  • Validate all fields prior to submission.
  • Consider breaking up the form between multiple pages as Eric G mentioned.
5
  • 1
    I'm not sure what exactly you mean by "roll your own in javascript" but I'm pretty sure it's a bad idea. Commented Mar 10, 2013 at 18:23
  • -1 never roll your own https in javascript. If that's not what you meant please clarify. Commented Aug 24, 2013 at 14:24
  • @makerofthings7 I clarified. I never said roll https in javascript, I said OR javascript (clarified with encryption). Although not the easiest to implement correctly, there are resources for that kind of solution. It's a valid answer and I don't see why it's worth a negative point. Commented Aug 28, 2013 at 20:07
  • Javascript with crypto code delivered from the server (which is what you seem to describe) is rarely a good idea. The server can modify that JS code and expose the local private keys. Another vector is XSS/CSRF. It's a risky security design. HTTPS should be a minimum. Let me know if you're thinking of some other deployment, such as a HTML/SPA application wrapped in PhoneGap or something similar. Commented Aug 28, 2013 at 20:49
  • 1
    @makerofthings7, My thought process was not for man-in-the-middle. That is a can of worms. I was picturing eavesdropping. One of the systems I worked on encoded all form data with javascript (with a random key) so that coworkers couldn't snoop on each other. Commented Aug 28, 2013 at 21:25
14

A solution I have seen a few banks implement, at least in web apps, is to have a two page login.

  1. On the first page accept only the username
  2. On the next page in the process request the password and only echo the username back so it is not an editable field

Therefore the only input on the second page should be the password. Since the user knows they must clear the first page with a username, they know they must clear that gate, then the only option on the second page is the password.

If you can implement this workflow, it will help focus the users on what they are typing and when.


Also, considering your logging: Maybe you can change your logging to not include actual credentials?

E.g., On a successful login, use the primary key id instead of echoing back the input: "The user with id: '2342342' has attempted to logon" then "The user with id '2342342' has successfully provided a password".

If you do a lookup and the username is not there, then something like "User from IP address '192.168.0.10' attempted to logon with a non-valid user id".

This would be your app level logs. Web server logs may include query parameters, so that might be a little harder to address or maybe you can put some type of proxy filter in between the action and when the log is written to redact the log content based on certain rules. This would be platform specific, but it looks like it may be possible on Apache.

As a secondary control, limit read access to the various log files you are processing.

4
  • serial authentication? perhaps
    – Saladin
    Commented Mar 5, 2013 at 19:50
  • 10
    Two step forms are actually the one place I am most likely to trip up and throw my password in the username field on the first page!
    – Caleb
    Commented Mar 7, 2013 at 11:01
  • I would be interested to know more about the UX case, do you have any reason you think this happens? Does the site login store your username on repeat visits or not? I would imagine that would help (but could hurt) since you wouldn't even have a box to type in if it prefills your username. Let me know some more details and I'll see if I can add some additional info to my response.
    – Eric G
    Commented Mar 8, 2013 at 3:58
  • 1
    This makes me much less frustrated that one of my banks does this, thanks for this answer (hah).
    – enderland
    Commented Mar 9, 2013 at 2:17
5

From what you describe of your architecture, this is infeasible, but in my opinion the correct solution is: Don't send the username in the clear, and don't log usernames of failed login attempts. The only place the username and password should go is to the subsystem which checks the password; until that occurs, the username is unauthenticated, arbitrary data — anyone with access to the login form, which in a web application is the entire Internet, can type in anything they want however often they want — and therefore tells you very little of interest. (Unless your login form is not exposed to the Internet.)

this would probably eliminate a lot of the log analysis for not being able to tell who did what....?

Given a username without the correct password, you don't know that the request is actually from that user, so you still don't know who did the login attempt.

1
  • +1 for posing the question to me as to whether we really need to know the username or not. I tend to think that we still need to username in the logs, but could be convinced otherwise should the arguments be strong enough. One of the reasons is to use correlation engine to put together time, frequency, source and destination IPs with the username. As I said, still don't have a very conclusive opinion about it, but thanks for the thought: it put me to think even more about it.@KevinReid
    – Lex
    Commented Mar 7, 2013 at 11:40
4

Generally speaking, all client Code are Smart Enough to handle Basic Errors

  1. User ID and or Password Missing
  2. Password not matching the Guidelines

So in any case when you are still seeing these entries in the Log,

User P@$$w0rd does not exit [...]
An account failed to login: P@$$w0rd [...]

None of the Client Validation worked and the System ended up sending the unencrypted password over the network. So what was in the Password Field? Definitely not blank as the Client Validation would fail. It must me something different from password

So Make it a two pass authentication

  1. First Pass, send all encrypted details including password to the server. Verify if Password field is empty.
  2. First Pass, Verify if the Password matches the Guidelines else Error Out.
  3. First Pass, next check if the password is present in your DB. If not Error Out.
  4. Send back an RPC response to the Client and let it send the User ID and Password now.
  5. Now perform the authentication process

The whole essence of this process is to

  1. Minimize risk. Note, you cannot eliminate the risk to Zero
  2. Not trusting the Client.

And finally, get your interface reviewed by a UX Expert. It may be, your interface has some flaw causing Users to enter Password in the ID field.

1
  • Excellent suggestion. I think the majority of answers here so far put a good summary and it all makes a lot sense. +1
    – Lex
    Commented Mar 5, 2013 at 19:30
4

The general problem is password-based authentication. Every mom-and-pop shop insists on having own authentication with passwords. This is stupid.

Let some other identity provider do the hard work of keeping credentials secure. Do the same as StackOverflow does: allow authenticating with OpenID, Gmail, etc.

Your users will thank you for not needing yet another password somewhere.

3

Client side javascript seems reasonable.

Check password field is not empty, prior to submission. Check that the username is in a valid form. Especially elegant is something where the username is required to be an email address. You could additionally forbid password at your password set/change mechanism from being in the form of an email address. Then simply check that the username is in the form of a valid email address prior to submitting the form. This could be done similarly with say special characters or numbers. (E.g., numbers/special characters are required in passwords but forbidden from usernames).

Additionally, use an up-to-date library SSL for all form submissions (this should be done to prevent network eavesdroppers from listening in). Require elevated permissions to read these logs (e.g., the webserver account can write to these logs, but only root can read them). As soon as the password fails the authentication step, don't propagate the username to other systems. (Also use SSL between distinct internal systems to prevent network eavesdroppers).

3

I like the approach that my current company takes to this problem: if you type your password into the wrong box, an automated system causes your password to expire immediately. Thus the user has to change their password, and the password that is in the log is now no longer vulnerable.

Of course, this is still not ideal if the user is still using that password for another system, but hopefully being forced to change their password will make a user more cognizant of the possible security risks.

6
  • 1
    How does this work? Does it check the username against the password stored in the database, if they match, force reset? Is this web based or also at the Windows/LDAP level? If so, is this a custom or off the shelf product?
    – Eric G
    Commented Mar 6, 2013 at 5:14
  • @EricG: It's a custom system, and I didn't build it, so I don't really know how it was implemented. That said, I believe it works by hashing the username and checking the hashes against the password hashes. My understanding is that they keep a database somewhere of "passwords found under suspicious circumstances" and expire any active passwords that match that list. Commented Mar 6, 2013 at 6:23
  • 1
    @jcolebrand: Sorry, I thought I explained that: hash whatever gets entered into the username field and check the hash against the password database. Optionally use something like a Bloom filter if you have a really big password database and want to check quickly. I have no idea if this is what they actually do, though: maybe there's an even better way. Commented Mar 6, 2013 at 22:05
  • 3
    That may actually be a valid thing to do. Then the problem is I can put in 1234567 or password1 etc and invalidate a whole lotta passwords. If I think I know my buddies password, etc.
    – jcolebrand
    Commented Mar 6, 2013 at 22:21
  • 2
    I'm with EricG. I don't understand how to actually implement this in a secure way. If the password database is storing password using a salt (and using a slow password hash like bcrypt), it's not easy to verify whether an incorrect username is actually someone's password, and if so, find whose it was -- the best you can do is exhaustive search over all users in the database, which is not scalable. If the password database doesn't use a salt (or doesn't use a slow password hash), you've got more serious problems -- that's a definite no-no.
    – D.W.
    Commented Mar 7, 2013 at 8:57
2

Mostly the EASIEST answer is the right answer. Now we notice that every email address has a "@" sign in it Just before the domain name. Making "@" a NON ACCEPTABLE key in password makes the solution pretty obvious. If the username does NOT have @ and ALL USERNAMES are email addresses, then Log only those that have atleast @ in them.

Now if the username DONOT have "@", it probably might make some users angry but this is a neat solution. That is to have ONE SINGLE special character that comes BEFORE a password. Just like ALL USERNAMES that are email accounts have a format. All answers have a special character at the start or at the end, whatever. So when the user is entering a password, you let him know that he needs to type it in.

Third solution is that COLOR CODING. Make username Field Yellow and Password Field RED. Red normally catches your attention because it is used for sensitive stuff. So even if they are looking at the keyboard, the will VERY QUICKLY LEARN that passwords are red. So basically the textfield AND THE label of password is red preferably in a separate box and Username label and textfield ALL YELLOW.

1
  • 2
    Using email addresses as user names is far from universal for public apps, and is rare in in-house apps. Color coding is unlikely to help: the usual reason for using the wrong field are inattention to which field is focused (especially when the username field is usually pre-filled but for some reason isn't in one instance). Commented Mar 6, 2013 at 15:52
0

Why not just respond with this?

That username does not exist
6
  • 9
    You probably shouldn't do this, or even take a different amount of time in the response. Responses like this and sometimes the difference in the amount of time it takes to process can be abused provide a list of valid usernames, which could even be used for reasons other than just attempting to gain access to the site/service itself (e.g. they could try to send an email to that same username in gmail, etc.). Commented Mar 5, 2013 at 20:17
  • @GaryS.Weaver: <- Yes. e.g., you create an A/B test in your brute forcer and whenever you get the different conditions you know you have identified a valid username.
    – Eric G
    Commented Mar 5, 2013 at 20:22
  • @GaryS.Weaver there's no fool proof solution, but dont u think that's a little overkill? he's not running americanexpress.com Commented Mar 5, 2013 at 20:31
  • @Артём-Царионов it's up to you, him, and everyone else to implement security as they see fit. Commented Mar 5, 2013 at 21:10
  • 1
    The problem in the question is that the username ends up in log files which makes a permanent record of the username in plain text. If the server was ever compromised or an admin wasn't honest, they could access the user's account without any record in the system. The log file still needs to know what usernames are being tried, so the solution would need to somehow prevent a password from being stored in a log if it is put in the username field. Commented Mar 5, 2013 at 21:25
0

How much control do you have over the receiving server's handling of this? It seems like the solution that a user proposed above, to hash both the username and password, would be workable a couple of ways:

Method 1 (requiring JavaScript): Hash both username and password. In your database, store hashed usernames, and then do your auth lookup using that field. This would be ideal if you have some control over the way the data is treated on your server, but do not control its logging capacity.

Method 2 (not requiring JavaScript): Receive username in plaintext as usual, but convert it to a hash as in method 1 once you receive it on the server. When the attempt fails, log the hash, not the username. The logs will still be useful (slightly less useful when inspected cursorily), since each hash will still uniquely identify a user. Neither of these are as elegant as the top response here (and I would suggest using that as well), but they are more thorough.

0

A simple, yet annoying solution could be to have a on-screen keypad layout of html buttons, where users can only type their username using these buttons, this will prevent the mistake from being made, I realize how annoying this could turn out to be, but after the first login, you could use a cookie to remember the username and not require it again. Javascript will be required of course. Now its impossible to send the password in plain text by accident. Hope it helps.

1
  • true, however what about people logging into their Windows Domain from a laptop? We collect these logs too.
    – Lex
    Commented Mar 7, 2013 at 11:42
0

I have a different take... What problem are you trying to really solve?

  1. Bad passwords? I.e. when you see a person use "password" (or a variant) you want to be able to trace back to the user and correct it?

  2. Passwords being sent in the clear?

  3. Or the issue with idiots who can't type or read forms (or maybe a badly designed UI)?

Always remember that whenever you "add" to the system you are potentially adding complexity, and you are definitely adding code - both which increase the possibility you open security "holes" in your overall architecture somewhere (could be in the stack, could be via the web, could be over the net...). So in resolving any of the 3 you must measure whether the value of solving them is worth the risk of poking a hole you don't know about - the devil you know is always better than the devil you don't.

Now to each.

Resolving bad passwords should be done at the set up and change of the password via the validation rules. And only there. To add another place to do so, only means you risk getting validation rules confused or out of synch.

Passwords being sent in the clear. Who cares? Granted might "feel" unsafe, but remember this is n part authentication and if you only have 1 part it is no different than having a word in a dictionary. Maybe, just maybe if you have an active sniffer it may give them some clues, but then the intrusion already in place is your real problem, not some occasional, random, fat-fingering of passwords in the user name field. Now if you have all parts being sent in the clear, big problem.

Issue of idiots or bad UI design. Re-mediate users or UI. Simple. Provide active help on UI, have departments go through some training or something. Easy fix that requires limited, low risk coding changes (or should - be careful with the UI aspect though).

While I admire a lot of the suggestions on here, and many of them have wonderful ideas at their core. I recommend a KISS, no BS approach, always remembering that if you add to your systems you risk adding to your insecurity.

Just my 2 cents.

0
  • only allow of transmitting md5 hashes of usernames AND passwords (or similar hash), so that whatever gets logged in the log files will always look like a fixed length of random characters, which will not make anyone be able to quickly guess that it is an md5 of a password or a username.

Con: To compare with usernames in your database you have to either store two columns e.g. 'username' and 'md5(username)' OR you have to dynamically hash every time you're querying username for login.


  • create a log entry only if the username exists in the database, otherwise, log ip only.

  • only allow the user to click enter using the mouse, not the keyboard, or only allow the keyboard after 5 seconds of last entered character in either fields, which will give the user time to look at the screen and see his mistake.

  • do some restriction to allowed usernames and passwords:

    1. passwords must contain a special character like !@#$%^&*()
    2. usernames must NOT contain any special character

This way, you can do javascript to quickly identify whether the entered is username or password.

0

Biometrics are fairly inexpensive now and work at least 80% of the time. I find it great on TabletPCs and have been wanting to deploy biometric keyboards because it is faster ( at least for that 80% of the time).

I bet this was not nearly as much of a problem with Win2000, WinXP, Win2003, and WinVista because by default, the username field was already filled with the last successful username. Not exactly sure which version of ActiveDirectory or workstation changed, but the default now is for the username field to be blank which makes this problem more prevalent.

0

As a variation of Daniel Prydens answer:

One could have a minimum password length and a maximum username length. For example, passwords must be at least 16 characters long, usernames may be at most 15 characters wrong. Then, if a string of 16 characters or longer is typed into the username field, do not write it into the log file.

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .