mirror of
https://github.com/maxgoedjen/secretive.git
synced 2025-04-10 17:47:19 +00:00
.
This commit is contained in:
parent
af52c60ebf
commit
80a2bd42a3
@ -12,7 +12,7 @@ public protocol SecretStore: ObservableObject, Identifiable {
|
|||||||
func sign(data: Data, with secret: SecretType, for provenance: SigningRequestProvenance) throws -> SignedData
|
func sign(data: Data, with secret: SecretType, for provenance: SigningRequestProvenance) throws -> SignedData
|
||||||
|
|
||||||
// TODO: MOVE TO SEPARATE PROTOCOL?
|
// TODO: MOVE TO SEPARATE PROTOCOL?
|
||||||
func persistAuthentication(secret: SecretType, forDuration: TimeInterval) throws
|
func persistAuthentication(secret: SecretType, forDuration duration: TimeInterval) throws
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -98,14 +98,12 @@ extension SecureEnclave {
|
|||||||
|
|
||||||
public func sign(data: Data, with secret: SecretType, for provenance: SigningRequestProvenance) throws -> SignedData {
|
public func sign(data: Data, with secret: SecretType, for provenance: SigningRequestProvenance) throws -> SignedData {
|
||||||
let context: LAContext
|
let context: LAContext
|
||||||
// TODO: RESTORE
|
|
||||||
if let existing = persistedAuthenticationContexts[secret], existing.valid {
|
if let existing = persistedAuthenticationContexts[secret], existing.valid {
|
||||||
context = existing.context
|
context = existing.context
|
||||||
} else {
|
} else {
|
||||||
let newContext = LAContext()
|
let newContext = LAContext()
|
||||||
newContext.localizedCancelTitle = "Deny"
|
newContext.localizedCancelTitle = "Deny"
|
||||||
// TODO: FIX
|
pendingAuthenticationContext = PersistentAuthenticationContext(secret: secret, context: newContext, expiration: Date(timeIntervalSinceNow: Constants.authenticationPersistenceOptInWindow))
|
||||||
pendingAuthenticationContext = PersistentAuthenticationContext(secret: secret, context: newContext, expiration: Date(timeIntervalSinceNow: 100))
|
|
||||||
context = newContext
|
context = newContext
|
||||||
}
|
}
|
||||||
context.localizedReason = "sign a request from \"\(provenance.origin.displayName)\" using secret \"\(secret.name)\""
|
context.localizedReason = "sign a request from \"\(provenance.origin.displayName)\" using secret \"\(secret.name)\""
|
||||||
@ -136,15 +134,26 @@ extension SecureEnclave {
|
|||||||
}
|
}
|
||||||
let signatureDuration = Date().timeIntervalSince(signingStartTime)
|
let signatureDuration = Date().timeIntervalSince(signingStartTime)
|
||||||
// Hack to determine if the user had to authenticate to sign.
|
// Hack to determine if the user had to authenticate to sign.
|
||||||
// Since there's now way to inspect SecAccessControl to determine.
|
// Since there's now way to inspect SecAccessControl to determine (afaict).
|
||||||
let requiredAuthentication = signatureDuration > Constants.unauthenticatedThreshold
|
let requiredAuthentication = signatureDuration > Constants.unauthenticatedThreshold
|
||||||
|
|
||||||
return SignedData(data: signature as Data, requiredAuthentication: requiredAuthentication)
|
return SignedData(data: signature as Data, requiredAuthentication: requiredAuthentication)
|
||||||
}
|
}
|
||||||
|
|
||||||
public func persistAuthentication(secret: Secret, forDuration: TimeInterval) throws {
|
public func persistAuthentication(secret: Secret, forDuration duration: TimeInterval) throws {
|
||||||
guard secret == pendingAuthenticationContext?.secret else { throw AuthenticationPersistenceError() }
|
let newContext = LAContext()
|
||||||
persistedAuthenticationContexts[secret] = pendingAuthenticationContext
|
newContext.localizedCancelTitle = "Deny"
|
||||||
|
newContext.localizedReason = "sign requests without reprompting"
|
||||||
|
newContext.evaluatePolicy(LAPolicy.deviceOwnerAuthenticationWithBiometricsOrWatch, localizedReason: newContext.localizedReason) { x, y in
|
||||||
|
print(x, y)
|
||||||
|
}
|
||||||
|
|
||||||
|
guard let pending = pendingAuthenticationContext,
|
||||||
|
secret == pending.secret,
|
||||||
|
pending.valid
|
||||||
|
else { throw AuthenticationPersistenceExpiredError() }
|
||||||
|
let rewrapped = PersistentAuthenticationContext(secret: secret, context: newContext, expiration: Date(timeIntervalSinceNow: duration))
|
||||||
|
persistedAuthenticationContexts[secret] = rewrapped
|
||||||
pendingAuthenticationContext = nil
|
pendingAuthenticationContext = nil
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -215,8 +224,7 @@ extension SecureEnclave {
|
|||||||
public let error: SecurityError?
|
public let error: SecurityError?
|
||||||
}
|
}
|
||||||
|
|
||||||
public struct AuthenticationPersistenceError: Error {
|
public struct AuthenticationPersistenceExpiredError: Error {}
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -232,6 +240,7 @@ extension SecureEnclave {
|
|||||||
static let keyTag = "com.maxgoedjen.secretive.secureenclave.key".data(using: .utf8)! as CFData
|
static let keyTag = "com.maxgoedjen.secretive.secureenclave.key".data(using: .utf8)! as CFData
|
||||||
static let keyType = kSecAttrKeyTypeECSECPrimeRandom
|
static let keyType = kSecAttrKeyTypeECSECPrimeRandom
|
||||||
static let unauthenticatedThreshold: TimeInterval = 0.05
|
static let unauthenticatedThreshold: TimeInterval = 0.05
|
||||||
|
static let authenticationPersistenceOptInWindow: TimeInterval = 30
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user