// This source file is part of the Swift.org open source project
//
// Copyright (c) 2014 - 2016 Apple Inc. and the Swift project authors
// Licensed under Apache License v2.0 with Runtime Library Exception
//
// See http://swift.org/LICENSE.txt for license information
// See http://swift.org/CONTRIBUTORS.txt for the list of Swift project authors
//

import CoreFoundation

extension Set : _ObjectTypeBridgeable {
    public typealias _ObjectType = NSSet
    public func _bridgeToObjectiveC() -> _ObjectType {
        let buffer = UnsafeMutablePointer<AnyObject>.allocate(capacity: count)
        
        for (idx, obj) in enumerated() {
            buffer.advanced(by: idx).initialize(to: (obj as! _ObjectBridgeable)._bridgeToAnyObject())
        }
        
        let set = NSSet(objects: buffer, count: count)
        
        buffer.deinitialize(count: count)
        buffer.deallocate(capacity: count)
        
        return set
    }
    
    public static func _forceBridgeFromObjectiveC(_ source: _ObjectType, result: inout Set?) {
        result = _unconditionallyBridgeFromObjectiveC(source)
    }
    
    @discardableResult
    public static func _conditionallyBridgeFromObjectiveC(_ source: _ObjectType, result: inout Set?) -> Bool {
        var set = Set<Element>()
        var failedConversion = false
        
        if type(of: source) == NSSet.self || type(of: source) == NSMutableSet.self {
            source.enumerateObjects(options: []) { obj, stop in
                if let o = obj as? Element {
                    set.insert(o)
                } else {
                    failedConversion = true
                    stop.pointee = true
                }
            }
        } else if type(of: source) == _NSCFSet.self {
            let cf = source._cfObject
            let cnt = CFSetGetCount(cf)
            
            let objs = UnsafeMutablePointer<UnsafeRawPointer?>.allocate(capacity: cnt)
            
            CFSetGetValues(cf, objs)
            
            for idx in 0..<cnt {
                let obj = unsafeBitCast(objs.advanced(by: idx), to: AnyObject.self)
                if let o = obj as? Element {
                    set.insert(o)
                } else {
                    failedConversion = true
                    break
                }
            }
            objs.deinitialize(count: cnt)
            objs.deallocate(capacity: cnt)
        }
        if !failedConversion {
            result = set
            return true
        }
        return false
    }
    
    static public func _unconditionallyBridgeFromObjectiveC(_ source: _ObjectType?) -> Set {
        if let object = source {
            var value: Set<Element>?
            _conditionallyBridgeFromObjectiveC(object, result: &value)
            return value!
        } else {
            return Set<Element>()
        }
    }
}
