Skip to content

Instantly share code, notes, and snippets.

@azechi
Last active October 3, 2018 19:47
Show Gist options
  • Save azechi/031ab6dd86d23c7444a8ca1085163c50 to your computer and use it in GitHub Desktop.
Save azechi/031ab6dd86d23c7444a8ca1085163c50 to your computer and use it in GitHub Desktop.
.Net Core Decrypting Legacy FormsAuthenticationTicket (mode=Framework20SP2, SHA1, AES)
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>netcoreapp1.1</TargetFramework>
<RootNamespace>App</RootNamespace>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="System.Text.Encoding.CodePages" Version="4.3.0" />
</ItemGroup>
</Project>
using System;
using System.IO;
using System.Security.Cryptography;
using System.Text;
namespace Decrypt_AuthenticationTicket
{
class Program
{
const int SHA1_KEY_SIZE = 64;
const int SHA1_HASH_SIZE = 20;
static SymmetricAlgorithm DecryptAlgorithm { get; }
static int _IVLengthDecryption { get; }
static string validationKey_sha1 = "";
static string decryptionKey_aes = "";
static Program()
{
DecryptAlgorithm = System.Security.Cryptography.Aes.Create();
DecryptAlgorithm.Key = HexToBinary(decryptionKey_aes);
DecryptAlgorithm.GenerateIV();
DecryptAlgorithm.IV = new byte[DecryptAlgorithm.IV.Length];
_IVLengthDecryption = (DecryptAlgorithm.KeySize / 8) + (((DecryptAlgorithm.KeySize & 7) != 0) ? 1 : 0);
}
static void Main(string[] args)
{
Encoding.RegisterProvider(CodePagesEncodingProvider.Instance);
var encryptedTicket = "";
for (var i = 0; i < 1; i++)
{
var bBlob = HexToBinary(encryptedTicket);
var buf = GetUnHashedData(bBlob);
byte[] paddedData;
using (var ms = new MemoryStream())
using (var cryptoTransform = DecryptAlgorithm.CreateDecryptor())
using (var cs = new CryptoStream(ms, cryptoTransform, CryptoStreamMode.Write))
{
cs.Write(buf, 0, buf.Length);
cs.FlushFinalBlock();
paddedData = ms.ToArray();
}
// strip IV
var bDataLength = paddedData.Length - _IVLengthDecryption;
var bData = new byte[bDataLength];
Buffer.BlockCopy(paddedData, _IVLengthDecryption, bData, 0, bDataLength);
//var ticketLength -= MachineKeySection.HashSize;
//var ticket = FormsAuthenticationTicketSerializer.Deserializa(bBlob, ticketLength)
using (var blobStream = new MemoryStream(bData))
{
using (var reader = new SerializingBinaryReader(blobStream))
{
var formatVersion = reader.ReadByte();
var version = reader.ReadByte();
var utcTicks = reader.ReadInt64();
var created = new DateTime(utcTicks, DateTimeKind.Utc).ToLocalTime();
var spacer = reader.ReadByte();
var expireDateTicks = reader.ReadInt64();
var expire = new DateTime(expireDateTicks, DateTimeKind.Utc).ToLocalTime();
var persistenceField = reader.ReadByte();
var name = reader.ReadString();
Console.WriteLine(name);
var userData = reader.ReadString();
var path = reader.ReadString();
var footer = reader.ReadByte();
}
}
}
}
private sealed class SerializingBinaryReader : BinaryReader
{
public SerializingBinaryReader(Stream input)
: base(input)
{
}
public override string ReadString()
{
int charCount = Read7BitEncodedInt();
byte[] bytes = ReadBytes(charCount * 2);
char[] chars = new char[charCount];
for (int i = 0; i < chars.Length; i++)
{
chars[i] = (char)(bytes[2 * i] | (bytes[2 * i + 1] << 8));
}
return new String(chars);
}
}
static byte[] GetUnHashedData(byte[] bufHashed)
{
if (!VerifyHashData(bufHashed))
{
return null;
}
var buf2 = new byte[bufHashed.Length - SHA1_HASH_SIZE];
Buffer.BlockCopy(bufHashed, 0, buf2, 0, buf2.Length);
return buf2;
}
static bool VerifyHashData(byte[] bufHashed)
{
var hasher = new HMACSHA1(HexToBinary(validationKey_sha1));
var bMac = hasher.ComputeHash(bufHashed, 0, bufHashed.Length - SHA1_HASH_SIZE);
var lastPos = bufHashed.Length - SHA1_HASH_SIZE;
var hashCheckFailed = false;
for (var iter = 0; iter < SHA1_HASH_SIZE; iter++)
{
if (bMac[iter] != bufHashed[lastPos + iter])
{
hashCheckFailed = true;
}
}
return !hashCheckFailed;
}
static int HexToInt(char h)
{
return
(h >= '0' && h <= '9') ? h - '0'
: (h >= 'a' && h <= 'f') ? h - 'a' + 10
: (h >= 'A' && h <= 'F') ? h - 'A' + 10
: -1
;
}
static byte[] HexToBinary(string data)
{
if (data == null || data.Length % 2 != 0)
{
return null;
}
var binary = new byte[data.Length / 2];
for (int i = 0; i < binary.Length; i++)
{
int highNibble = HexToInt(data[2 * i]);
int lowNibble = HexToInt(data[2 * i + 1]);
if (highNibble == -1 || lowNibble == -1)
{
return null;
}
binary[i] = (byte)((highNibble << 4) | lowNibble);
}
return binary;
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment