fix(siteruntime): CertStoreActor — dispose listed certs + reject path-traversal thumbprints (T17)
This commit is contained in:
@@ -126,4 +126,44 @@ public class CertStoreActorTests : TestKit, IDisposable
|
||||
var ack = ExpectMsg<LocalCertOpAck>();
|
||||
ack.Success.Should().BeTrue("removing an absent cert is an idempotent no-op");
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void Write_PathTraversalThumbprint_RejectedWithoutTouchingFilesystem()
|
||||
{
|
||||
var (derBase64, _) = BuildSelfSignedCert();
|
||||
var actor = Sys.ActorOf(Props.Create(() => new CertStoreActor(_options)));
|
||||
|
||||
// A "../escape" thumbprint would otherwise resolve to "<root>/escape.der",
|
||||
// OUTSIDE the trusted-store dir, once combined into a ".der" file name.
|
||||
actor.Tell(new WriteCertToLocalStore(derBase64, "../escape"));
|
||||
var ack = ExpectMsg<LocalCertOpAck>();
|
||||
ack.Success.Should().BeFalse("a path-traversal thumbprint must be rejected");
|
||||
ack.Error.Should().Be("invalid thumbprint");
|
||||
|
||||
// No file escaped above the trusted-store dir (the shared temp root).
|
||||
var escapeRoot = Path.GetDirectoryName(_trustedDir)!;
|
||||
File.Exists(Path.Combine(escapeRoot, "escape.der")).Should().BeFalse(
|
||||
"the actor must not write outside the trusted-store directory");
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void Remove_PathTraversalThumbprint_RejectedWithoutTouchingFilesystem()
|
||||
{
|
||||
// Seed a decoy file one level up to prove the rejected remove never
|
||||
// reaches the filesystem and therefore cannot delete it.
|
||||
var escapeRoot = Path.GetDirectoryName(_trustedDir)!;
|
||||
Directory.CreateDirectory(escapeRoot);
|
||||
var decoy = Path.Combine(escapeRoot, "escape.der");
|
||||
File.WriteAllBytes(decoy, new byte[] { 0x01, 0x02, 0x03 });
|
||||
|
||||
var actor = Sys.ActorOf(Props.Create(() => new CertStoreActor(_options)));
|
||||
|
||||
actor.Tell(new RemoveCertFromLocalStore("../escape"));
|
||||
var ack = ExpectMsg<LocalCertOpAck>();
|
||||
ack.Success.Should().BeFalse("a path-traversal thumbprint must be rejected");
|
||||
ack.Error.Should().Be("invalid thumbprint");
|
||||
|
||||
File.Exists(decoy).Should().BeTrue(
|
||||
"the actor must not delete files outside the trusted-store directory");
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user