private void Generate_Click(object sender, RoutedEventArgs e) { if (e != null && sender != null) { ((ListBoxItem)MyListView.ContainerFromElement((Button)sender)).IsSelected = true; string secret = _addAccount.GetSecret(MyListView.SelectedItem as string); lastSecret = secret; ((ListBoxItem)MyListView.ContainerFromElement((Button)sender)).IsSelected = false; } Console.WriteLine("SECRET=" + lastSecret); byte[] key; try { // Google send you base32 string you need to decode it before using it. key = Base32.Base32Encoder.Decode(lastSecret); } catch (Exception) { return; } // T = (Current Unix time - T0) / X (RFC 6238) // Here we get the current time, then we substract the unix epoch (1st January 1970) and we divide by the step // T0 is unix's epoch it's the default value // X is the step here 30 seconds. Like before we use the default value byte[] message = BitConverter.GetBytes((Int64)Math.Floor((DateTime.Now.ToUniversalTime() - new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc)).TotalSeconds / 30.0)); int remain = (int)Math.Floor((DateTime.Now.ToUniversalTime() - new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc)).TotalSeconds % 30.0); // Why ? Why is it in big endian !!! See 5.2 Description RFC 4226 message = message.Reverse().ToArray(); // We use HMAC-SHA-1 algorithm because HOTP is based on this algorithm HMACSHA1 hmac = new HMACSHA1(key); byte[] hash = hmac.ComputeHash(message); // We extract the nibble (quartet) of the last char int nibble = (hash[hash.Length - 1] & 0xf); // We extract 4 bytes from byte array and we need to set the first bit to 0 int truncatedHash = (hash[nibble] & 0x7f) << 24 | (hash[nibble + 1] & 0xff) << 16 | (hash[nibble + 2] & 0xff) << 8 | (hash[nibble + 3] & 0xff); // We get a 6 digit code string code = (truncatedHash % 1000000).ToString(); // If needed we add '0' if the code doesn't have enough digit while (code.Length < 6) { code = "0" + code; } Code.Text = code.ToString(); Progress.Value = remain; remainTimer.Start(); }