Efficiently Storing Passwords in .NET Framework

Introduction and Background

In this article, I will discuss a few things about security in user accounts and other lockers that you might be creating in your own applications. First of all, you need to understand that security is the most essential part of every application where a user is able to share his data. A user trusts an application if he is sure that your application is safe of any external hacks and unauthorized calls to get the data. Users must be provided enough grounds to put their faith in you. 
 
I am not just talking about the users with enterprise solutions, instead I am talking about every single application. If you develop an application that provides users with access to authentication services, such as logging in. Then, you must always provide security to users. First of foremost thing to secure is the credentials that they will provide you with. Let me simply one thing for you. An authentication system is not only the one that is created using a username, an email for example, and a password, made up using alphanumeric characters. Authentication system, by definition is a system that authenticates the users. A system that tells and ensures that user indeed is the user that he/she is trying to be. For example, on C# Corner I am, "AuthorID: 201fc1". So when server wants to communicate with me. It would perform actions for my interactions using that ID. Which is then used, to show my name, Afzaal Ahmad Zeeshan, and my display picture to users for good readability purposes. On the backend it is the AuthorID that is being used (I am not sure what they call it in their database). 
 
Now think of a scenario where C# Corner has no security. Someone logs in to computer, and in the AuthorID enters my ID. C# Corner would look up for a record and work act respectively for what I am authorized to do. It may delete all of my articles, or at worse share my private information on the internet, such as passwords or other private resources stored with my account. Thank God and development team, there are security measures on C# Corner. Now, this was just a common example. There are some worse conditions and scenarios that might be raised by this security leak. 
 
That is why, it is always recommended to pay attention to security foremost!

Securing users

Securing your users is a very simple yet complex task. Many frameworks that are being used nowadays have these features already built in. ASP.NET and most specially, .NET framework have cryptography techniques already built in for you. You can use the namespaces (discussed later in this article) to secure your protected data in a way that no one can steal the data, even if they do, I repeat, even if they do, it would take a lot of time of theirs to decrypt the ciphers. 
 
Mostly, authentication systems are built using email address and password as the key/value pair for credentials. But, let me tell you one more thing. You can create your own login system using a security password and an answer
 
A sample example for a server-client communication that sets up authentication based on a question and an answer. 
 
Now, you can see that the above logic is not pretty much secure, because everyone knows (or at least ones who know me) that Eminem is my favorite rapper. Anyone can take that and authenticate themselves on the servers. For this, there is another technique known as, Hashing. I will show you what that is in a minute. First, understand the actual authentication logic. 
 
Authentication is actually just a function, feature or a program that asks the users a security question before they can continue using the service as who they are trying to say they are. For example, your username and password. Username, everyone knows. Password, only you know. Server asks you to tell them both, accurate, so that it can authenticate you on itself and allow you to work as the one you are trying to say you are. If the credentials are false, server won't authenticate you.
 
Each user has to go through this process, no matter sharing their answers to security questions or providing their passwords. 
 
Above image has a demonstration of the authentication system in websites. You do not need to be using only username and password combination anymore, there are many more functions that can be implemented to the application, just to make sure that the user is actually himself whom he is trying to claim to be. :-) 

Securing the passwords

Securing user accounts starts with the process of securing the passwords of users. A question can be shared with anyone, but the answer to that question should not be shared, even with the server. Many techniques have been introduced to store passwords and I would only talk about hashing the password.
 
The technique of hashing is to hide the underlying message, known as password, so that no one can ever get an idea of what user might be using as the secure string for his account. Passwords are similar to keys for your locks at homes. There is no purpose to lock down your house if you are going to leave the key to it unsafe, exposed or unprotected. Similarly, if you create a login system, but do not secure the passwords for users then chances are that your users are already at stake of privacy issues. 
 
Cryptography began ever since computers have been introduced, programmers have created algorithms to secure your data in the computer, so that no potential user can ever steal it without your intent or consent. Privacy issues, threats etc are the worst ones that can make your application lose users, so easily as compared to an application with bad UI or bad UX techniques.

Hashing the passwords

Enough with introduction, you need to understand what hashing process is, how it helps the programmers and how does it maintain the security. Hashing a password is key to securing the passwords in your system. A hashing algorithm is designed in a way that it is almost impossible for anyone to convert the hashed string back to the actual password string. 
 
For example, (I am not sure of the actual algorithm used, but as a sample example) I ask you to select one number from 1-100. Selected? Next, I will use 1 number (50) and multiply your number by it. Let's assume, you selected 60. The result is 3000. Similarly, storing 3000 (and the number I chose) would provide me a solution to mask your data, 60. No hacker would be able to convert 3000 back to the actual password, unless they know either one of the inputs. Either 50, or 60 is required to run the algorithm back to get the result of 3000. 
 
Above example, was a very stupid and a childish one. In real, the answers span to a hundreds of characters and the process is executed 1000s time to make sure, string is no longer able to be converted back. For real hashing processes, a special key is used as a private number. This key is used to hash the string. The hash created is an alphanumeric string. It is almost impossible to convert it back, however I will talk about a few other side effects that cause the hashed passwords to be cracked. Read the article...

Process of hashing a password; with salt.
 
It is just a security measure that makes sure that your content of passwords, is not easily accessible even if your database is exposed to hackers! 

Adding Salt

Um, ever had something to eat without masala? Possibly, you can eat your food without it. But, the purpose of salting the food is to add extra taste to it, but is not required. Similarly, adding a salt string in password before processing it in hash algorithm is not required. But, it would give very fruitful results if done. 
 
Purpose of adding a salt to password.
 
From above image it is clear as to why should one add a salt string to the password string before hashing it. The purpose is not to distinguish anything at all. 

Purpose of adding salt 

The main purpose to add a salt to the password before hashing is that there are quite a lot of procedures defined in hacking.
Rainbow Table attack
  1. Brute Force attack
  2. Dictionary attack
These attacks, try to attempt as many password strings on the server to guess the actual password as they can. Rainbow Table attack is a very common one. Rainbow attack, for example, try to enter a few most commonly used password strings and get their hashes so that server may let them in. Dictionary attack, brute force attacks are also most commonly used in this hacking technique. 
 
Adding a salt just makes it even harder for the hacker to create an algorithm to guess a password string for which the hash would be computed to a result that was stored for the user. For example, I enter password, "KingsNeverDieIsAGreatSongByEminem", and at the same time server generates another salt key, "DidYouKnow". So the password string now looks like, "DidYouKnowKingsNeverDieIsAGreatSongByEminem". The hash computed for this is way too much different for either one of them. Hacker, when attempting to create a hash for these, would not be able to create a same one. 
 
Also, it must be noted that salt must be a random string, so hacker or his tool cannot judge it. A few good techniques for salt are:
  1. It must be a new salt for every password. 
  2. For every user, a new salt must be generated.
  3. A new salt must be generated every time you need to compute hash. 
  4. Hash and salt can be stored in the database for later purposes. 
  5. Salt must be random string of alphanumeric characters.
  6. Although appending or prepending salt doesn't matter, but by convention salt is prepended to the password. 
 Following the above conditions, you can create an extra security layer over the password. In next chapter, we will learn how to hash passwords in .NET framework using C#. Remember: .NET framework and its derived frameworks, such as WPF, WinForms, ASP.NET etc all can use native cryptographic libraries of .NET framework. So, the code I would provide is applicable to ASP.NET web applications, WPF desktop apps, WinForms applications and other frameworks that run on .NET framework. 

Hashing a password in .NET

Fun part of the article, in this section I will show you a code of a few lines only, that can be used to generate hashes. I would show you many kinds of procedures that can be used to mask the passwords; hash the passwords.