//===----------------------------------------------------------------------===//
//
// 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 https://swift.org/LICENSE.txt for license information
// See https://swift.org/CONTRIBUTORS.txt for the list of Swift project authors
//
//===----------------------------------------------------------------------===//

@_exported import Dispatch

import CDispatch

/// dispatch_assert

@available(macOS 10.12, iOS 10.0, tvOS 10.0, watchOS 3.0, *)
public enum DispatchPredicate {
	case onQueue(DispatchQueue)
	case onQueueAsBarrier(DispatchQueue)
	case notOnQueue(DispatchQueue)
}

@available(macOS 10.12, iOS 10.0, tvOS 10.0, watchOS 3.0, *)
public func _dispatchPreconditionTest(_ condition: DispatchPredicate) -> Bool {
	switch condition {
	case .onQueue(let q):
		dispatch_assert_queue(q.__wrapped)
	case .onQueueAsBarrier(let q):
		dispatch_assert_queue_barrier(q.__wrapped)
	case .notOnQueue(let q):
		dispatch_assert_queue_not(q.__wrapped)
	}
	return true
}

@_transparent
@available(macOS 10.12, iOS 10.0, tvOS 10.0, watchOS 3.0, *)
public func dispatchPrecondition(condition: @autoclosure () -> DispatchPredicate, file: StaticString = #file, line: UInt = #line) {
	// precondition is able to determine release-vs-debug asserts where the overlay
	// cannot, so formulating this into a call that we can call with precondition()
	precondition(_dispatchPreconditionTest(condition()), "dispatchPrecondition failure", file: file, line: line)
}

/// qos_class_t

public struct DispatchQoS : Equatable {
	public let qosClass: QoSClass
	public let relativePriority: Int

	@available(macOS 10.10, iOS 8.0, *)
	public static let background = DispatchQoS(qosClass: .background, relativePriority: 0)

	@available(macOS 10.10, iOS 8.0, *)
	public static let utility = DispatchQoS(qosClass: .utility, relativePriority: 0)

	@available(macOS 10.10, iOS 8.0, *)
	public static let `default` = DispatchQoS(qosClass: .default, relativePriority: 0)

	@available(macOS 10.10, iOS 8.0, *)
	public static let userInitiated = DispatchQoS(qosClass: .userInitiated, relativePriority: 0)

	@available(macOS 10.10, iOS 8.0, *)
	public static let userInteractive = DispatchQoS(qosClass: .userInteractive, relativePriority: 0)

	public static let unspecified = DispatchQoS(qosClass: .unspecified, relativePriority: 0)

	public enum QoSClass {
		@available(macOS 10.10, iOS 8.0, *)
		case background

		@available(macOS 10.10, iOS 8.0, *)
		case utility

		@available(macOS 10.10, iOS 8.0, *)
		case `default`

		@available(macOS 10.10, iOS 8.0, *)
		case userInitiated

		@available(macOS 10.10, iOS 8.0, *)
		case userInteractive

		case unspecified

		// _OSQoSClass is internal on Linux, so this initialiser has to 
		// remain as an internal init.
		@available(macOS 10.10, iOS 8.0, *)
		internal init?(rawValue: _OSQoSClass) {
			switch rawValue {
			case .QOS_CLASS_BACKGROUND: self = .background
			case .QOS_CLASS_UTILITY: self = .utility
			case .QOS_CLASS_DEFAULT: self = .default
			case .QOS_CLASS_USER_INITIATED: self = .userInitiated
			case .QOS_CLASS_USER_INTERACTIVE: self = .userInteractive
			case .QOS_CLASS_UNSPECIFIED: self = .unspecified
			default: return nil
			}
		}

		@available(macOS 10.10, iOS 8.0, *)
		internal var rawValue: _OSQoSClass {
			switch self {
			case .background: return .QOS_CLASS_BACKGROUND
			case .utility: return .QOS_CLASS_UTILITY
			case .default: return .QOS_CLASS_DEFAULT
			case .userInitiated: return .QOS_CLASS_USER_INITIATED
			case .userInteractive: return .QOS_CLASS_USER_INTERACTIVE
			case .unspecified: return .QOS_CLASS_UNSPECIFIED
			}
		}
	}

	public init(qosClass: QoSClass, relativePriority: Int) {
		self.qosClass = qosClass
		self.relativePriority = relativePriority
	}
}

public func ==(a: DispatchQoS, b: DispatchQoS) -> Bool {
	return a.qosClass == b.qosClass && a.relativePriority == b.relativePriority
}

/// 

public enum DispatchTimeoutResult {
    static let KERN_OPERATION_TIMED_OUT:Int = 49
	case success
	case timedOut
}

/// dispatch_group

extension DispatchGroup {
	public func notify(qos: DispatchQoS = .unspecified, flags: DispatchWorkItemFlags = [], queue: DispatchQueue, execute work: @escaping @convention(block) () -> ()) {
		if #available(macOS 10.10, iOS 8.0, *), qos != .unspecified || !flags.isEmpty {
			let item = DispatchWorkItem(qos: qos, flags: flags, block: work)
			dispatch_group_notify(self.__wrapped, queue.__wrapped, item._block)
		} else {
			dispatch_group_notify(self.__wrapped, queue.__wrapped, work)
		}
	}

	@available(macOS 10.10, iOS 8.0, *)
	public func notify(queue: DispatchQueue, work: DispatchWorkItem) {
		dispatch_group_notify(self.__wrapped, queue.__wrapped, work._block)
	}

	public func wait() {
		_ = dispatch_group_wait(self.__wrapped, DispatchTime.distantFuture.rawValue)
	}

	public func wait(timeout: DispatchTime) -> DispatchTimeoutResult {
		return dispatch_group_wait(self.__wrapped, timeout.rawValue) == 0 ? .success : .timedOut
	}

	public func wait(wallTimeout timeout: DispatchWallTime) -> DispatchTimeoutResult {
		return dispatch_group_wait(self.__wrapped, timeout.rawValue) == 0 ? .success : .timedOut
	}
}

/// dispatch_semaphore

extension DispatchSemaphore {
	@discardableResult
	public func signal() -> Int {
		return Int(dispatch_semaphore_signal(self.__wrapped))
	}

	public func wait() {
		_ = dispatch_semaphore_wait(self.__wrapped, DispatchTime.distantFuture.rawValue)
	}

	public func wait(timeout: DispatchTime) -> DispatchTimeoutResult {
		return dispatch_semaphore_wait(self.__wrapped, timeout.rawValue) == 0 ? .success : .timedOut
	}

	public func wait(wallTimeout: DispatchWallTime) -> DispatchTimeoutResult {
		return dispatch_semaphore_wait(self.__wrapped, wallTimeout.rawValue) == 0 ? .success : .timedOut
	}
}
