LibHac/libhac.Nand/Nand.cs
Alex Barney f1b660b95f Add IFileSystem interface
I don't know about this. It seems really easy to screw something up.

Allows using the same code for reading the raw nand and reading a normal file system
2018-07-11 20:03:09 -05:00

76 lines
3 KiB
C#

using System.IO;
using System.Linq;
using DiscUtils;
using DiscUtils.Fat;
using DiscUtils.Partitions;
using DiscUtils.Streams;
using libhac.XTSSharp;
namespace libhac.Nand
{
public class Nand
{
private GuidPartitionInfo ProdInfo { get; }
private GuidPartitionInfo ProdInfoF { get; }
private GuidPartitionInfo Safe { get; }
private GuidPartitionInfo System { get; }
private GuidPartitionInfo User { get; }
private Keyset Keyset { get; }
public Nand(Stream stream, Keyset keyset)
{
var disc = new GuidPartitionTable(stream, Geometry.Null);
var partitions = disc.Partitions.Select(x => (GuidPartitionInfo)x).ToArray();
ProdInfo = partitions.FirstOrDefault(x => x.Name == "PRODINFO");
ProdInfoF = partitions.FirstOrDefault(x => x.Name == "PRODINFOF");
Safe = partitions.FirstOrDefault(x => x.Name == "SAFE");
System = partitions.FirstOrDefault(x => x.Name == "SYSTEM");
User = partitions.FirstOrDefault(x => x.Name == "USER");
Keyset = keyset;
}
public Stream OpenProdInfo()
{
var encStream = ProdInfo.Open();
var xts = XtsAes128.Create(Keyset.bis_keys[0]);
var decStream = new RandomAccessSectorStream(new XtsSectorStream(encStream, xts, 0x4000, 0), true);
return decStream;
}
public NandPartition OpenProdInfoF()
{
var encStream = ProdInfoF.Open();
var xts = XtsAes128.Create(Keyset.bis_keys[0]);
var decStream = new RandomAccessSectorStream(new XtsSectorStream(encStream, xts, 0x4000, 0), true);
FatFileSystem fat = new FatFileSystem(decStream, Ownership.None);
return new NandPartition(fat);
}
public NandPartition OpenSafePartition()
{
var encStream = Safe.Open();
var xts = XtsAes128.Create(Keyset.bis_keys[1]);
var decStream = new RandomAccessSectorStream(new XtsSectorStream(encStream, xts, 0x4000, 0), true);
FatFileSystem fat = new FatFileSystem(decStream, Ownership.None);
return new NandPartition(fat);
}
public NandPartition OpenSystemPartition()
{
var encStream = System.Open();
var xts = XtsAes128.Create(Keyset.bis_keys[2]);
var decStream = new RandomAccessSectorStream(new XtsSectorStream(encStream, xts, 0x4000, 0), true);
FatFileSystem fat = new FatFileSystem(decStream, Ownership.None);
return new NandPartition(fat);
}
public NandPartition OpenUserPartition()
{
var encStream = User.Open();
var xts = XtsAes128.Create(Keyset.bis_keys[3]);
var decStream = new RandomAccessSectorStream(new XtsSectorStream(encStream, xts, 0x4000, 0), true);
FatFileSystem fat = new FatFileSystem(decStream, Ownership.None);
return new NandPartition(fat);
}
}
}