Multiple hardware wallets: per-wallet devices, wallets page, Poinbase custodial account, PLEDGER item with supply-chain poisoning

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
ZHU MINCHAOandClaude Opus 5.5 committed 2026-11-03 22:58:24 +08:00
1 parent add61a6b5e
commit 783f73989d
19 files changed
+557 -199

No files matched your search

@@ -808,6 +808,42 @@ internal static class Program
Check(!ChainAddress.Valid("0x12345") && !ChainAddress.Valid("0xzzzzzzzz") && !ChainAddress.WellFormed("12345678ab"), "格式不对的地址不合法");
});
Test("被投毒的钱包:门槛以下不转,越多越快,转空", () =>
{
Check(Wallet.DrainChance(Tuning.WalletDrainMin - 1) == 0, "门槛以下不会被转走");
Check(Math.Abs(Wallet.DrainChance(Tuning.WalletDrainMin) - 1 / 7.0) < 1e-9, "刚到门槛:每晚 1/7(平均 7 天)");
Check(Wallet.DrainChance(Tuning.WalletDrainFull) == 1 && Wallet.DrainChance(Tuning.WalletDrainFull * 3) == 1, "到满额当晚就转走");
Check(Wallet.DrainChance(10000) > Wallet.DrainChance(5000), "钱越多越快");
var w = new Wallet { Address = "a" };
w.Add(Assets.PSC, 50); w.Add(Assets.CRT, 1000); w.Taint = 300; w.Basis = 900; w.Freeze(Assets.CRT, 0.5, 9);
double v = w.Drain(a => a == Assets.PSC ? 100 : 1);
Check(Math.Abs(v - 6000) < 1e-6 && w.Balances.Count == 0 && w.Frozen.Count == 0 && w.Taint == 0 && w.Basis == 0, $"全部转走(含冻结),污点和成本清零:{v}");
});
Test("多钱包:退款、出售回款、混币提回都回到原来的钱包", () =>
{
Func<string, double> price = a => a == Assets.PSC ? 100 : 1;
var a = new Wallet { Address = "0xa" }; var b = new Wallet { Address = "0xb" };
a.Add(Assets.CRT, 5000); b.Add(Assets.CRT, 5000);
Func<string, Wallet> pick = addr => addr == "0xa" ? a : b;
var mx = new Mixer();
var dep = mx.Deposit(a, Assets.CRT, 1000, 1, 1, price);
Check(dep.Wallet == "0xa", "混币存入记下钱包地址");
mx.Night(pick, 2, price, new Rng(3));
Check(mx.Pending.Count == 0 ? a.Get(Assets.CRT) > 4900 && b.Get(Assets.CRT) == 5000 : true, $"混币提回 A:A {a.Get(Assets.CRT):0},B {b.Get(Assets.CRT):0}");
var bm = new BlackMarket();
bm.RefreshOrders(5, 80, new Rng(11), _ => 300);
var seller = bm.Sellers.FindIndex(x => !x.Scam);
bm.Sellers[seller].Scam = true;
var l = bm.Catalog.First(x => x.Seller == seller);
double bBefore = b.Get(Assets.CRT);
var o = bm.Place(l, 1, PayMode.Escrow, b, Assets.CRT, 5, price);
Check(o.Wallet == "0xb" && b.Get(Assets.CRT) < bBefore, "订单记下付款钱包");
double aBefore = a.Get(Assets.CRT);
for (int d = 6; d < 30 && o.State == OrderState.Pending; d++) bm.Night(d, false, pick, new Rng((ulong)d), 0, price);
Check(o.State == OrderState.Refunded && Math.Abs(b.Get(Assets.CRT) - bBefore) < 1e-6 && a.Get(Assets.CRT) == aBefore, $"骗子托管退款回 B:{o.State}");
});
Console.WriteLine($"\n{_passed} 通过,{_failed} 失败");
return _failed == 0 ? 0 : 1;
}