Skip to content

Commit

Permalink
Add RunLoopThread, a base class for background threads operating a ru…
Browse files Browse the repository at this point in the history
…nloop.
  • Loading branch information
mickeyl committed Oct 18, 2024
1 parent 162a835 commit f267440
Showing 1 changed file with 69 additions and 0 deletions.
69 changes: 69 additions & 0 deletions Sources/CornucopiaCore/Threading/RunLoopThread.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
//
// Cornucopia – (C) Dr. Lauer Information Technology
//
import Foundation
import Dispatch

private let logger = Cornucopia.Core.Logger()

public extension Cornucopia.Core {

/// Base class for threads that operate a ``RunLoop``.
open class RunLoopThread: Thread {

private var loop: RunLoop!
private let semaphore: DispatchSemaphore = .init(value: 0)
private var timer: Timer!

/// Construction blocks until the thread and the RunLoop is actually running.
public override init() {
super.init()
self.start()
self.semaphore.wait()
}

public override func main() {

assert(!Self.isMainThread)
assert(self == Thread.current)
self.loop = RunLoop.current
assert(self.loop != RunLoop.main)

self.timer = .init(timeInterval: 10.0, target: self, selector: #selector(self.onTimerFired), userInfo: nil, repeats: true)
self.loop.add(self.timer, forMode: RunLoop.Mode.common)

logger.trace("Entering runloop")
self.semaphore.signal()
CFRunLoopRun()
logger.trace("Exiting runloop")
self.semaphore.signal()
}

/// Perform a `block` of work in the context of this thread.
public func perform(_ block: @escaping () -> Void) {
self.loop.perform(block)
}

/// Shutdown the RunLoop.
open func shutdown() {
self.timer.invalidate(); self.timer = nil
self.loop.perform {
CFRunLoopStop(self.loop.getCFRunLoop())
}
CFRunLoopWakeUp(self.loop.getCFRunLoop())
self.semaphore.wait()
logger.trace("Shutdown OK. Runloop exited")
}

deinit {
logger.trace("Destroyed")
}
}
}

extension Cornucopia.Core.RunLoopThread {

@objc private func onTimerFired() {
logger.trace("Thread still healthy")
}
}

0 comments on commit f267440

Please sign in to comment.