public CoinController(BoundedInbox inbox, BoundedInbox outbox, ICoinStore store, IOutpointHash hash, ILog log = null, int shardIndex = -1) { _inbox = inbox; _outbox = outbox; _store = store; _hash = hash; _log = log; _shardIndex = shardIndex; _pool = new SpanPool <byte>(PoolSizeInBytes); _mre = new ManualResetEvent(false); }
public void SetupStores(CashDBConfig config) { var secretPath = Path.Combine(config.Layer1Path, "secret.dat"); var secretStore = new MemoryMappedFileSlim(secretPath); var secretSpan = secretStore.GetSpan(0, Constants.SecretStoreFileSize); // HACK: secret initialization (would be better isolated) if (secretSpan.ToArray().All(b => b == 0)) { var rng = RandomNumberGenerator.Create(); rng.GetBytes(secretSpan); } OutpointHash = new SipHash(secretSpan); var chainPath = Path.Combine(config.Layer1Path, "chains.dat"); ChainStore = new ChainStore(new MemoryMappedFileSlim(chainPath), _log); ChainStore.Initialize(); CoinStores = new ICoinStore[Constants.CoinControllerCount]; for (var i = 0; i < Constants.CoinControllerCount; i++) { var journalPath = Path.Combine(config.Layer1Path, $"coins-journal-{i:x2}.dat"); var journalFile = new MemoryMappedFileSlim(journalPath); var layer1CoinStorePath = Path.Combine(config.Layer1Path, $"coins-1-{i:x2}.dat"); var layer1File = new MemoryMappedFileSlim(layer1CoinStorePath); var sectorCount = (int)(layer1File.FileLength / Constants.CoinStoreLayer1SectorSize); // Last layer used for key-value store. IKeyValueStore <uint> kvStore = null; if (!string.IsNullOrEmpty(config.Layer3Path)) { var layer3CoinStorePath = Path.Combine(config.Layer3Path, $"coins-3-{i:x2}.dat"); kvStore = new LightningStore <uint>(layer3CoinStorePath, "coins"); } IPackStore packStore; if (string.IsNullOrEmpty(config.Layer2Path)) { // Layer 2 is omitted packStore = new PackStore( sectorCount, new[] { Constants.CoinStoreLayer1SectorSize }, new[] { layer1File }, journalFile, kvStore, _log); } else { // Layer 2 is included var layer2CoinStorePath = Path.Combine(config.Layer2Path, $"coins-2-{i:x2}.dat"); var layer2File = new MemoryMappedFileSlim(layer2CoinStorePath); // Sector size on layer 2 is inferred from the sector count on layer 1. if (layer2File.FileLength % sectorCount != 0) { throw new InvalidOperationException("Mismatch between sector counts across layers."); } var coinStoreLayer1SectorSize = (int)(layer2File.FileLength / sectorCount); packStore = new PackStore( sectorCount, new[] { Constants.CoinStoreLayer1SectorSize, coinStoreLayer1SectorSize }, new[] { layer1File, layer2File }, journalFile, kvStore, _log); } packStore.Initialize(); CoinStores[i] = new SozuTable(packStore, OutpointHash); } _log?.Log(LogSeverity.Info, "CashDB store initialization completed successfully."); }