diff --git a/FirebaseAuth/CHANGELOG.md b/FirebaseAuth/CHANGELOG.md index 01349d8f334..62a5762a5cd 100644 --- a/FirebaseAuth/CHANGELOG.md +++ b/FirebaseAuth/CHANGELOG.md @@ -1,3 +1,6 @@ +# Unreleased +- [fixed] Replaced unsafe uses of `os_unfair_lock` (#14548). + # 11.9.0 - [changed] Using reCAPTCHA Enterprise and Firebase Auth requires reCAPTCHA Enterprise 18.7.0 or later. diff --git a/FirebaseAuth/Sources/Swift/Auth/AuthComponent.swift b/FirebaseAuth/Sources/Swift/Auth/AuthComponent.swift index 649d274c294..355373104d4 100644 --- a/FirebaseAuth/Sources/Swift/Auth/AuthComponent.swift +++ b/FirebaseAuth/Sources/Swift/Auth/AuthComponent.swift @@ -33,7 +33,7 @@ class AuthComponent: NSObject, Library, ComponentLifecycleMaintainer { private var instances: [String: Auth] = [:] /// Lock to manage access to the instances array to avoid race conditions. - private var instancesLock: os_unfair_lock = .init() + private let instancesLock = OSAllocatedUnfairLock() // MARK: - Initializers @@ -58,10 +58,10 @@ class AuthComponent: NSObject, Library, ComponentLifecycleMaintainer { // MARK: - AuthProvider conformance @discardableResult func auth() -> Auth { - os_unfair_lock_lock(&instancesLock) + instancesLock.lock() // Unlock before the function returns. - defer { os_unfair_lock_unlock(&instancesLock) } + defer { instancesLock.unlock() } if let instance = instances[app.name] { return instance diff --git a/FirebaseFunctions/CHANGELOG.md b/FirebaseFunctions/CHANGELOG.md index 89a663ec718..58cf04f7a58 100644 --- a/FirebaseFunctions/CHANGELOG.md +++ b/FirebaseFunctions/CHANGELOG.md @@ -1,3 +1,6 @@ +# Unreleased +- [fixed] Replaced unsafe uses of `os_unfair_lock` (#14548). + # 11.9.0 - [fixed] Fixed App Check token reporting to enable differentiating outdated (`MISSING`) and inauthentic (`INVALID`) clients; see [Monitor App Check diff --git a/FirebaseFunctions/Sources/Functions.swift b/FirebaseFunctions/Sources/Functions.swift index ce189579c87..59ad8ce52d2 100644 --- a/FirebaseFunctions/Sources/Functions.swift +++ b/FirebaseFunctions/Sources/Functions.swift @@ -56,7 +56,7 @@ enum FunctionsConstants { private static var instances: [String: [Functions]] = [:] /// Lock to manage access to the instances array to avoid race conditions. - private static var instancesLock: os_unfair_lock = .init() + private static let instancesLock = OSAllocatedUnfairLock() /// The custom domain to use for all functions references (optional). let customDomain: String? @@ -304,10 +304,10 @@ enum FunctionsConstants { guard let app else { fatalError("`FirebaseApp.configure()` needs to be called before using Functions.") } - os_unfair_lock_lock(&instancesLock) + instancesLock.lock() // Unlock before the function returns. - defer { os_unfair_lock_unlock(&instancesLock) } + defer { instancesLock.unlock() } if let associatedInstances = instances[app.name] { for instance in associatedInstances { diff --git a/FirebaseStorage/CHANGELOG.md b/FirebaseStorage/CHANGELOG.md index cb40acb0b9f..af4496d0ed7 100644 --- a/FirebaseStorage/CHANGELOG.md +++ b/FirebaseStorage/CHANGELOG.md @@ -1,3 +1,6 @@ +# Unreleased +- [fixed] Replaced unsafe uses of `os_unfair_lock` (#14548). + # 11.1.0 - [fixed] Fix a potential data race in Storage initialization. (#13369) diff --git a/FirebaseStorage/Sources/Storage.swift b/FirebaseStorage/Sources/Storage.swift index b58cc4a8c30..ad03eaf77c3 100644 --- a/FirebaseStorage/Sources/Storage.swift +++ b/FirebaseStorage/Sources/Storage.swift @@ -249,13 +249,13 @@ import FirebaseCore private var instances: [String: Storage] = [:] /// Lock to manage access to the instances array to avoid race conditions. - private var instancesLock: os_unfair_lock = .init() +private let instancesLock = OSAllocatedUnfairLock() private init() {} func storage(app: FirebaseApp, bucket: String) -> Storage { - os_unfair_lock_lock(&instancesLock) - defer { os_unfair_lock_unlock(&instancesLock) } + instancesLock.lock() + defer { instancesLock.unlock() } if let instance = instances[bucket] { return instance diff --git a/FirebaseVertexAI/CHANGELOG.md b/FirebaseVertexAI/CHANGELOG.md index e7fc4c18d6c..28bc66c263b 100644 --- a/FirebaseVertexAI/CHANGELOG.md +++ b/FirebaseVertexAI/CHANGELOG.md @@ -1,6 +1,7 @@ # Unreleased - [feature] The Vertex AI SDK no longer requires `@preconcurrency` when imported in Swift 6. - [feature] The Vertex AI Sample App now includes an image generation example. +- [fixed] Replaced unsafe uses of `os_unfair_lock` (#14548). # 11.9.0 - [feature] **Public Preview**: Added support for generating images using the diff --git a/FirebaseVertexAI/Sources/VertexAI.swift b/FirebaseVertexAI/Sources/VertexAI.swift index 16fc8be0561..2d62ec43dd8 100644 --- a/FirebaseVertexAI/Sources/VertexAI.swift +++ b/FirebaseVertexAI/Sources/VertexAI.swift @@ -124,20 +124,17 @@ public class VertexAI { let apiConfig: APIConfig + /// Lock to manage access to the `instances` array to avoid race conditions. + private static let instancesLock = OSAllocatedUnfairLock() + #if compiler(>=6) /// A map of active `VertexAI` instances keyed by the `FirebaseApp` name and the `location`, in /// the format `appName:location`. private nonisolated(unsafe) static var instances: [InstanceKey: VertexAI] = [:] - - /// Lock to manage access to the `instances` array to avoid race conditions. - private nonisolated(unsafe) static var instancesLock: os_unfair_lock = .init() #else /// A map of active `VertexAI` instances keyed by the `FirebaseApp` name and the `location`, in /// the format `appName:location`. private static var instances: [InstanceKey: VertexAI] = [:] - - /// Lock to manage access to the `instances` array to avoid race conditions. - private static var instancesLock: os_unfair_lock = .init() #endif let location: String? @@ -149,10 +146,10 @@ public class VertexAI { fatalError("No instance of the default Firebase app was found.") } - os_unfair_lock_lock(&instancesLock) + instancesLock.lock() // Unlock before the function returns. - defer { os_unfair_lock_unlock(&instancesLock) } + defer { instancesLock.unlock() } let instanceKey = InstanceKey(appName: app.name, location: location, apiConfig: apiConfig) if let instance = instances[instanceKey] {