mirror of
https://github.com/Thealexbarney/LibHac.git
synced 2024-11-14 10:49:41 +01:00
Skeleton AesXtsStorage
This commit is contained in:
parent
800d14f40b
commit
cd2b8edfa8
1 changed files with 115 additions and 0 deletions
115
src/LibHac/FsSystem/AesXtsStorage.cs
Normal file
115
src/LibHac/FsSystem/AesXtsStorage.cs
Normal file
|
@ -0,0 +1,115 @@
|
|||
// ReSharper disable NotAccessedField.Local
|
||||
using System;
|
||||
using System.Buffers.Binary;
|
||||
using LibHac.Common;
|
||||
using LibHac.Common.FixedArrays;
|
||||
using LibHac.Crypto;
|
||||
using LibHac.Diag;
|
||||
using LibHac.Fs;
|
||||
using LibHac.Os;
|
||||
|
||||
namespace LibHac.FsSystem;
|
||||
|
||||
/// <summary>
|
||||
/// Reads and writes to an <see cref="IStorage"/> that's encrypted with AES-XTS-128.
|
||||
/// </summary>
|
||||
/// <remarks>Based on FS 13.1.0 (nnSdk 13.4.0)</remarks>
|
||||
public class AesXtsStorage : IStorage
|
||||
{
|
||||
public static readonly int AesBlockSize = Aes.BlockSize;
|
||||
public static readonly int KeySize = Aes.KeySize128;
|
||||
public static readonly int IvSize = Aes.KeySize128;
|
||||
|
||||
private IStorage _baseStorage;
|
||||
private Array16<byte> _key1;
|
||||
private Array16<byte> _key2;
|
||||
private Array16<byte> _iv;
|
||||
private int _blockSize;
|
||||
private SdkMutexType _mutex;
|
||||
|
||||
// LibHac addition: This field goes unused if initialized with a plain IStorage.
|
||||
// The original class uses a template for both the shared and non-shared IStorage which avoids needing this field.
|
||||
private SharedRef<IStorage> _baseStorageShared;
|
||||
|
||||
public static void MakeAesXtsIv(Span<byte> outIv, long offset, int blockSize)
|
||||
{
|
||||
Assert.Equal(outIv.Length, IvSize);
|
||||
Assert.SdkRequiresGreaterEqual(offset, 0);
|
||||
Assert.SdkRequiresAligned((ulong)blockSize, AesBlockSize);
|
||||
|
||||
BinaryPrimitives.WriteInt64BigEndian(outIv.Slice(sizeof(long)), offset / blockSize);
|
||||
}
|
||||
|
||||
public AesXtsStorage(IStorage baseStorage, ReadOnlySpan<byte> key1, ReadOnlySpan<byte> key2, ReadOnlySpan<byte> iv,
|
||||
int blockSize)
|
||||
{
|
||||
_baseStorage = baseStorage;
|
||||
_blockSize = blockSize;
|
||||
_mutex = new SdkMutexType();
|
||||
|
||||
Assert.SdkRequiresEqual(KeySize, key1.Length);
|
||||
Assert.SdkRequiresEqual(KeySize, key2.Length);
|
||||
Assert.SdkRequiresEqual(IvSize, iv.Length);
|
||||
Assert.SdkRequiresAligned((ulong)blockSize, AesBlockSize);
|
||||
|
||||
key1.CopyTo(_key1.Items);
|
||||
key2.CopyTo(_key2.Items);
|
||||
iv.CopyTo(_iv.Items);
|
||||
}
|
||||
|
||||
public AesXtsStorage(ref SharedRef<IStorage> baseStorage, ReadOnlySpan<byte> key1, ReadOnlySpan<byte> key2,
|
||||
ReadOnlySpan<byte> iv, int blockSize)
|
||||
{
|
||||
_baseStorageShared = SharedRef<IStorage>.CreateMove(ref baseStorage);
|
||||
_baseStorage = _baseStorageShared.Get;
|
||||
_blockSize = blockSize;
|
||||
_mutex = new SdkMutexType();
|
||||
|
||||
Assert.SdkRequiresEqual(KeySize, key1.Length);
|
||||
Assert.SdkRequiresEqual(KeySize, key2.Length);
|
||||
Assert.SdkRequiresEqual(IvSize, iv.Length);
|
||||
Assert.SdkRequiresAligned((ulong)blockSize, AesBlockSize);
|
||||
|
||||
key1.CopyTo(_key1.Items);
|
||||
key2.CopyTo(_key2.Items);
|
||||
iv.CopyTo(_iv.Items);
|
||||
}
|
||||
|
||||
public override void Dispose()
|
||||
{
|
||||
_baseStorageShared.Destroy();
|
||||
|
||||
base.Dispose();
|
||||
}
|
||||
|
||||
public override Result Read(long offset, Span<byte> destination)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public override Result Write(long offset, ReadOnlySpan<byte> source)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public override Result Flush()
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public override Result GetSize(out long size)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public override Result SetSize(long size)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public override Result OperateRange(Span<byte> outBuffer, OperationId operationId, long offset, long size,
|
||||
ReadOnlySpan<byte> inBuffer)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue