Understanding Cryptography in WindowsRT

crypto

Security runs in my blood. After extensively working on cryptography on .net platform and have developed couple of mission critical apps. I was given the other challenge for an LOB app in WinRT platform. One of the requirements of the app was of cryptography. I researched it and learned a lot about it, so thought let me share the my knowledge with the community.

WHAT PLATFORM HAS TO OFFER

Let the readers get this straight, the WinRT platform is still under evolution , hence it does not offer the same number of apis that are available under .net platform. The platform will become more mature in future and you will see more convergence between the two platforms. There are two main api’s available which does most of heavy weight lifting. They are IBuffer, which marshal out the data. I would term it as an alternative to byte array available in .net and the other one is the static class CryptographicBuffer. I shall be talking about three aspects of cryptography

  1. Hashing
  2. Random Data
  3. Symmetric Encryption

HASHING

WinRT support MD5, SHA-1,SHA-256, SHA-384 and SHA-512 hashing algorithms. The code is pretty simple.

   1: private async void BtnHashConvertTapped(object sender, TappedRoutedEventArgs e)

   2:        {

   3:            if (string.IsNullOrEmpty(this.TxtInput.Text))

   4:            {

   5:                return;

   6:            }

   7:  

   8:            // get the raw input string

   9:            var textToBeHashed = this.TxtInput.Text;

  10:                

  11:            // convert string into binary

  12:            var inputBuffer = CryptographicBuffer.ConvertStringToBinary(textToBeHashed, BinaryStringEncoding.Utf8);

  13:  

  14:            // declare sha512

  15:            var sha512Hash = HashAlgorithmProvider.OpenAlgorithm(HashAlgorithmNames.Sha512);

  16:                

  17:            // hash the binary data using SHA512 algorithm

  18:            var hashedData = sha512Hash.HashData(inputBuffer);

  19:  

  20:            // encode the hashdata to Base64 format

  21:            var encodeToBase64String = CryptographicBuffer.EncodeToBase64String(hashedData);

  22:            var msgDialog = new MessageDialog(encodeToBase64String);

  23:                

  24:            // show the output in message dialog

  25:            var msg = await msgDialog.ShowAsync();

  26:        }

After conversion of plain input string into binary, we select the algorithm that needs to be applied. The output of which is hashData which is of IBuffer type. And finally converting it back to Base64 format.

RANDOM DATA

It is quite common need of the enterprise apps to generate the random data. In WinRT platform this can be classified in two sections

  • Generating Random Number
   1: /// <summary>

   2:         /// The generate random number.

   3:         /// </summary>

   4:         /// <param name="sender">

   5:         /// The sender.

   6:         /// </param>

   7:         /// <param name="e">

   8:         /// The e.

   9:         /// </param>

  10:         private async void GenerateRandomNumber(object sender, TappedRoutedEventArgs e)

  11:         {

  12:             // generate random number and show it is message dialog.

  13:             var msgDialog = new MessageDialog(CryptographicBuffer.GenerateRandomNumber().ToString());

  14:             var msg = await msgDialog.ShowAsync();

  15:             

  16:         }

The GenerateRandomNumber method returns a 32 bit unsigned integer value.

  • Generating Random Byte Array
   1: /// <summary>

   2:         /// Generates the random byte array

   3:         /// </summary>

   4:         /// <param name="sender">The sender</param>

   5:         /// <param name="e">The EventArgs</param>

   6:         void GenerateRandomArray(object sender, TappedRoutedEventArgs e)

   7:         {

   8:             uint len;

   9:             if (uint.TryParse(this.TxtLength.Text, out len))

  10:             {

  11:                 // generate the random byte array of specified length.

  12:                 var buffer = CryptographicBuffer.GenerateRandom(len);

  13:  

  14:                 // convert the buffer (byte array) into hexadecimal format and show it in message dialog

  15:                 var msgDialog = new MessageDialog(CryptographicBuffer.EncodeToHexString(buffer));

  16:                 msgDialog.ShowAsync();

  17:             }

  18:             else

  19:             {

  20:                 // user inputted invalid number show the message and set back the focus

  21:                 new MessageDialog("Invalid number").ShowAsync();

  22:                 this.TxtLength.Focus(FocusState.Keyboard);

  23:             }

  24:         }

The above code demonstrates to generate random byte array of the specified length and converts back into hexadecimal format.

SYMMETERIC ENCRYPTION

In this type of encryption we have only one key for encryption and decryption. So we should have a key before hand. Apart from the key we also require the Initialization Vector , which does the job of randomizer. In our case we will be using 1024 bit key and 16 bit for IV. Again we will be using the GenerateRandom method to generate these values. Both these binary values will be converted back to Hex format. Let us dive in code and see it in action.

   1: /// <summary>

   2:         /// Generates a random 1024 bit key

   3:         /// </summary>

   4:         /// <returns>A Hex format key</returns>

   5:         private static string GetKey()

   6:         {

   7:             // generate 1024 bits key

   8:             var buffer = CryptographicBuffer.GenerateRandom(1024);

   9:             return CryptographicBuffer.EncodeToHexString(buffer);

  10:         }

  11:  

  12:         /// <summary>

  13:         /// The get initialization vector.

  14:         /// </summary>

  15:         /// <returns>

  16:         /// The <see cref="string"/>.

  17:         /// </returns>

  18:         private static string GetInitializationVector()

  19:         {

  20:             // a 16 bit random binary value

  21:             var buffer = CryptographicBuffer.GenerateRandom(16);

  22:             return CryptographicBuffer.EncodeToHexString(buffer);

  23:         }

Code to Encrypt

   1: /// <summary>

   2:        /// The encrypt.

   3:        /// </summary>

   4:        /// <param name="sender">

   5:        /// The sender.

   6:        /// </param>

   7:        /// <param name="e">

   8:        /// The e.

   9:        /// </param>

  10:        private void Encrypt(object sender, TappedRoutedEventArgs e)

  11:        {

  12:            if (string.IsNullOrEmpty(this.TxtPlain.Text))

  13:            {

  14:                return;

  15:            }

  16:  

  17:            // convert plain text to binary

  18:            var input = CryptographicBuffer.ConvertStringToBinary(this.TxtPlain.Text, BinaryStringEncoding.Utf8);

  19:            var iv = CryptographicBuffer.DecodeFromBase64String(this.IV);

  20:  

  21:            // select the appropriate algorithm

  22:            var encryptor = SymmetricKeyAlgorithmProvider.OpenAlgorithm(SymmetricAlgorithmNames.AesCbcPkcs7);

  23:            

  24:            // get the key

  25:            var key = encryptor.CreateSymmetricKey(CryptographicBuffer.DecodeFromBase64String(this.symmetricKey));

  26:            

  27:            // do the encryption

  28:            var encryptedText = CryptographicEngine.Encrypt(key, input, iv);

  29:  

  30:            // convert the encrypted text into hex format and show it in textbox

  31:            this.TxtCipher.Text = CryptographicBuffer.EncodeToHexString(encryptedText);

  32:        }

Code to Decrypt

   1: /// <summary>

   2:         /// The decrypt.

   3:         /// </summary>

   4:         /// <param name="sender">

   5:         /// The sender.

   6:         /// </param>

   7:         /// <param name="e">

   8:         /// The e.

   9:         /// </param>

  10:         private void Decrypt(object sender, TappedRoutedEventArgs e)

  11:         {

  12:             if (!string.IsNullOrEmpty(this.TxtCipher.Text))

  13:             {

  14:                 // as the encrypted string is in hex format decode it and convert back to binary

  15:                 var input = CryptographicBuffer.DecodeFromHexString(this.TxtCipher.Text);

  16:  

  17:                 // decode the initialization vector

  18:                 var iv = CryptographicBuffer.DecodeFromBase64String(this.IV);

  19:  

  20:                 // specify the algorithm use the same one which was used with encryption

  21:                 var decryptor = SymmetricKeyAlgorithmProvider.OpenAlgorithm(SymmetricAlgorithmNames.AesCbcPkcs7);

  22:                 

  23:                 // get the key , same should be used which was used for encryption

  24:                 var key = decryptor.CreateSymmetricKey(CryptographicBuffer.DecodeFromBase64String(this.symmetricKey));

  25:  

  26:                 // Do the decryption

  27:                 var decryptedText = CryptographicEngine.Decrypt(key, input, iv);

  28:                 this.TxtPlain.Text = CryptographicBuffer.ConvertBinaryToString(BinaryStringEncoding.Utf8, decryptedText);

  29:             }

  30:             else

  31:             {

  32:                 new MessageDialog("First encrypt").ShowAsync();

  33:             }

  34:         }

CLOSURE

I talked about using the cryptography methods when you are developing a WinRT app. Apart from this operating system also has a built in support for bit locker (Only available in Pro and Enterprise versions) which helps to preserve the enterprise data and can be remotely wiped off with the Mobile Device Management Software like Windows InTune. Last but not least when your app depends on the web services it is always good practice to invoke them securely over SSL. The source code accompanying this post article is available on my GitHub account. Do share your valuable feedback.

Advertisements

What is stored for developers in Windows 8

Now that the BUILD conference comes to end. It time to reflect what were the announcements made in it. I would especially give my thoughts from the developer perspective. I will summarize it in few points that matter most to the developers.

  • SILVERLIGHT IS ALIVE AND KICKING : I think Microsoft has silent its critics who were telling that Silverlight is dead and HTML 5 and JavaScript would be native development technology for Windows 8. With new version of Silverlight about to release by this fall. Tons of new features and improvements have been done in new version and I’m looking forward to develop my first production app. Microsoft has also given importance to new trend where the competition is heading that is HTML 5 and JavaScript. The developer has the option to develop in this language also. My old friends of C++ don’t get disheartened your skills are still in demand and you can program on Windows 8. So this summarizes that there is not one technology on which you can develop apps. Folks at Microsoft has kept their promise of backward compability.

 

  • WINDOWS RUNTIME (WINRT): Welcome to this new acronym. Uptill now you must have heard about .net framework but to develop the apps for Win8 you would require to enter new arena of Windows Runtime. This still will be managed code according to the speculations it is the subset of .net framework only where MS has picked and choose the namespaces and classes which could very well gel with new platform. Tim has a great blog post mystifying the facts and speculations of new runtime. You can read it over here.

 

  •  METRO STYLE APPS : Get yourself acquainted with this new style. As windows 8 natively support touch input natively. All the apps that you would be developing should support this style. This is something that is derived from Windows Phone 7. I had always loved Metro theme, smooth and fluid. All the apps should be touch centric and chromeless. You need to get your application certified before publishing it to the store. There are guidelines available and once you follow them there are 100 % chances that your application would pass in one attempt. As mentioned above keeping the backward compability in mind you can still continue to develop the apps in traditional old style like desktop or standard web apps running in the browser. MS has committed that whatever that is running in Windows 7 will run in Windows 8. All you need is to switched to the desktop mode. You have Visual Studio 2011 IDE for doing the development of this types of apps. It comes with preinstalled templates and each template comes with lot of boiler plate code to get you quickly started. Blend 5 now support HTML authoring also.

 

  • HARDWARE AGNOSTIC : This is the perhaps the best feature I like about new platform. As windows 8 runs equally well on all the form factors (various screen sizes ranging from dual monitors to tablets). It will run on Intel based processers as well as ARM based. I was mesmerized when I saw the demo where Steven Sinofsky showing Win8 running on ATOM based processor with 1 GIG of RAM. Awesome simply awesome. Imagine here the opportunities that lies for you as a developer, your app running on laptops,desktops and now even tables or slates. You can always monetize your efforts and earn few extra bucks besides your day job. I am not saying that it will make you millionaire Smile , but opportunity is definitely there.

 

I have been in this industry now for more than decade and this is probably the best time I am having in my career span. Lot of excitement times ahead and huge opportunities for developers to seize.

So start brushing up your skills

HAPPY CODING