diff --git a/spec/integ/crypto/cross-signing.spec.ts b/spec/integ/crypto/cross-signing.spec.ts index 8a08eebdb..b81bf6f00 100644 --- a/spec/integ/crypto/cross-signing.spec.ts +++ b/spec/integ/crypto/cross-signing.spec.ts @@ -347,6 +347,67 @@ describe.each(Object.entries(CRYPTO_BACKENDS))("cross-signing (%s)", (backend: s expect(isCrossSigningReady).toBeTruthy(); }); + + it("should return false if identity is not trusted, even if the secrets are in 4S", async () => { + e2eKeyResponder.addCrossSigningData(SIGNED_CROSS_SIGNING_KEYS_DATA); + + // Complete initial sync, to get the 4S account_data events stored + mockInitialApiRequests(aliceClient.getHomeserverUrl()); + + // For this test we need to have a well-formed 4S setup. + const mockSecretInfo = { + encrypted: { + // Don't care about the actual values here, just need to be present for validation + KeyId: { + iv: "IVIVIVIVIVIVIV", + ciphertext: "CIPHERTEXTB64", + mac: "MACMACMAC", + }, + }, + }; + syncResponder.sendOrQueueSyncResponse({ + next_batch: 1, + account_data: { + events: [ + { + type: "m.secret_storage.key.KeyId", + content: { + algorithm: "m.secret_storage.v1.aes-hmac-sha2", + // iv and mac not relevant for this test + }, + }, + { + type: "m.secret_storage.default_key", + content: { + key: "KeyId", + }, + }, + { + type: "m.cross_signing.master", + content: mockSecretInfo, + }, + { + type: "m.cross_signing.user_signing", + content: mockSecretInfo, + }, + { + type: "m.cross_signing.self_signing", + content: mockSecretInfo, + }, + ], + }, + }); + await aliceClient.startClient(); + await syncPromise(aliceClient); + + // Sanity: ensure that the secrets are in 4S + const status = await aliceClient.getCrypto()!.getCrossSigningStatus(); + expect(status.privateKeysInSecretStorage).toBeTruthy(); + + const isCrossSigningReady = await aliceClient.getCrypto()!.isCrossSigningReady(); + + expect(isCrossSigningReady).toBeFalsy(); + }); }); describe("getCrossSigningKeyId", () => { diff --git a/src/rust-crypto/rust-crypto.ts b/src/rust-crypto/rust-crypto.ts index ee00aba4c..fd06d8201 100644 --- a/src/rust-crypto/rust-crypto.ts +++ b/src/rust-crypto/rust-crypto.ts @@ -610,15 +610,17 @@ export class RustCrypto extends TypedEventEmitter { - const { publicKeysOnDevice, privateKeysInSecretStorage, privateKeysCachedLocally } = - await this.getCrossSigningStatus(); + const { privateKeysInSecretStorage, privateKeysCachedLocally } = await this.getCrossSigningStatus(); const hasKeysInCache = Boolean(privateKeysCachedLocally.masterKey) && Boolean(privateKeysCachedLocally.selfSigningKey) && Boolean(privateKeysCachedLocally.userSigningKey); - // The cross signing is ready if the public and private keys are available - return publicKeysOnDevice && (hasKeysInCache || privateKeysInSecretStorage); + const identity = await this.getOwnIdentity(); + + // Cross-signing is ready if the public identity is trusted, and the private keys + // are either cached, or accessible via secret-storage. + return !!identity?.isVerified() && (hasKeysInCache || privateKeysInSecretStorage); } /**