diff --git a/extra/usbgpu/tbgpu/installer/.gitignore b/extra/usbgpu/tbgpu/installer/.gitignore new file mode 100644 index 0000000000..5427d09d18 --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/.gitignore @@ -0,0 +1,13 @@ +xcuserdata/ + +**/*.xcodeproj/project.xcworkspace/* +!**/*.xcodeproj/project.xcworkspace/xcshareddata + +**/*.xcodeproj/project.xcworkspace/xcshareddata/* +!**/*.xcodeproj/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings + +**/*.playground/playground.xcworkspace/* +!**/*.playground/playground.xcworkspace/xcshareddata + +**/*.playground/playground.xcworkspace/xcshareddata/* +!**/*.playground/playground.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings diff --git a/extra/usbgpu/tbgpu/installer/Shared/Assets.xcassets/AccentColor.colorset/Contents.json b/extra/usbgpu/tbgpu/installer/Shared/Assets.xcassets/AccentColor.colorset/Contents.json new file mode 100644 index 0000000000..eb87897008 --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/Shared/Assets.xcassets/AccentColor.colorset/Contents.json @@ -0,0 +1,11 @@ +{ + "colors" : [ + { + "idiom" : "universal" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/extra/usbgpu/tbgpu/installer/Shared/Assets.xcassets/AppIcon.appiconset/Contents.json b/extra/usbgpu/tbgpu/installer/Shared/Assets.xcassets/AppIcon.appiconset/Contents.json new file mode 100644 index 0000000000..c136eaff76 --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/Shared/Assets.xcassets/AppIcon.appiconset/Contents.json @@ -0,0 +1,148 @@ +{ + "images" : [ + { + "idiom" : "iphone", + "scale" : "2x", + "size" : "20x20" + }, + { + "idiom" : "iphone", + "scale" : "3x", + "size" : "20x20" + }, + { + "idiom" : "iphone", + "scale" : "2x", + "size" : "29x29" + }, + { + "idiom" : "iphone", + "scale" : "3x", + "size" : "29x29" + }, + { + "idiom" : "iphone", + "scale" : "2x", + "size" : "40x40" + }, + { + "idiom" : "iphone", + "scale" : "3x", + "size" : "40x40" + }, + { + "idiom" : "iphone", + "scale" : "2x", + "size" : "60x60" + }, + { + "idiom" : "iphone", + "scale" : "3x", + "size" : "60x60" + }, + { + "idiom" : "ipad", + "scale" : "1x", + "size" : "20x20" + }, + { + "idiom" : "ipad", + "scale" : "2x", + "size" : "20x20" + }, + { + "idiom" : "ipad", + "scale" : "1x", + "size" : "29x29" + }, + { + "idiom" : "ipad", + "scale" : "2x", + "size" : "29x29" + }, + { + "idiom" : "ipad", + "scale" : "1x", + "size" : "40x40" + }, + { + "idiom" : "ipad", + "scale" : "2x", + "size" : "40x40" + }, + { + "idiom" : "ipad", + "scale" : "1x", + "size" : "76x76" + }, + { + "idiom" : "ipad", + "scale" : "2x", + "size" : "76x76" + }, + { + "idiom" : "ipad", + "scale" : "2x", + "size" : "83.5x83.5" + }, + { + "idiom" : "ios-marketing", + "scale" : "1x", + "size" : "1024x1024" + }, + { + "idiom" : "mac", + "scale" : "1x", + "size" : "16x16" + }, + { + "idiom" : "mac", + "scale" : "2x", + "size" : "16x16" + }, + { + "idiom" : "mac", + "scale" : "1x", + "size" : "32x32" + }, + { + "idiom" : "mac", + "scale" : "2x", + "size" : "32x32" + }, + { + "idiom" : "mac", + "scale" : "1x", + "size" : "128x128" + }, + { + "idiom" : "mac", + "scale" : "2x", + "size" : "128x128" + }, + { + "idiom" : "mac", + "scale" : "1x", + "size" : "256x256" + }, + { + "idiom" : "mac", + "scale" : "2x", + "size" : "256x256" + }, + { + "idiom" : "mac", + "scale" : "1x", + "size" : "512x512" + }, + { + "idiom" : "mac", + "scale" : "2x", + "size" : "512x512" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/extra/usbgpu/tbgpu/installer/Shared/Assets.xcassets/Contents.json b/extra/usbgpu/tbgpu/installer/Shared/Assets.xcassets/Contents.json new file mode 100644 index 0000000000..73c00596a7 --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/Shared/Assets.xcassets/Contents.json @@ -0,0 +1,6 @@ +{ + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/extra/usbgpu/tbgpu/installer/Shared/TinyGPUApp.swift b/extra/usbgpu/tbgpu/installer/Shared/TinyGPUApp.swift new file mode 100644 index 0000000000..1f4f6d4248 --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/Shared/TinyGPUApp.swift @@ -0,0 +1,19 @@ +import AppKit +import SwiftUI + +final class AppDelegate: NSObject, NSApplicationDelegate { + func applicationShouldTerminateAfterLastWindowClosed(_ sender: NSApplication) -> Bool { + true + } +} + +@main +struct TinyGPUApp: App { + @NSApplicationDelegateAdaptor(AppDelegate.self) var appDelegate + + var body: some Scene { + WindowGroup { + TinyGPUView() + } + } +} diff --git a/extra/usbgpu/tbgpu/installer/Shared/TinyGPUView.swift b/extra/usbgpu/tbgpu/installer/Shared/TinyGPUView.swift new file mode 100644 index 0000000000..f4a6b14efc --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/Shared/TinyGPUView.swift @@ -0,0 +1,33 @@ +import SwiftUI + +struct TinyGPUView: View { + @ObservedObject var viewModel = TinyGPUViewModel() + + var body: some View { +#if os(macOS) + VStack(alignment: .center) { + Text("TinyGPU Intsaller") + .padding() + .font(.title) + Text(self.viewModel.dextLoadingState) + .multilineTextAlignment(.center) + HStack { + Button( + action: { + self.viewModel.activateMyDext() + }, label: { + Text("Install extension") + } + ) + } + } + .frame(width: 500, height: 200, alignment: .center) +#endif + } +} + +struct TinyGPUView_Previews: PreviewProvider { + static var previews: some View { + TinyGPUView() + } +} diff --git a/extra/usbgpu/tbgpu/installer/Shared/TinyGPUViewModel.swift b/extra/usbgpu/tbgpu/installer/Shared/TinyGPUViewModel.swift new file mode 100644 index 0000000000..a175714333 --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/Shared/TinyGPUViewModel.swift @@ -0,0 +1,149 @@ +import Foundation +import os.log +import SystemExtensions + +class TinyGPUDriverLoadingStateMachine { + enum State { case unloaded, activating, needsApproval, activated, activationError } +} + +class TinyGPUViewModel: NSObject { + + @Published private var state: TinyGPUDriverLoadingStateMachine.State = .unloaded + + override init() { + super.init() + refreshInitialDextState() + } + + private func refreshInitialDextState() { +#if os(macOS) + Task.detached { [dextIdentifier] in + let newState = Self.queryDextState(bundleID: dextIdentifier) + await MainActor.run { self.state = newState } + } +#endif + } + +#if os(macOS) + private static func queryDextState(bundleID: String) -> TinyGPUDriverLoadingStateMachine.State { + let tool = "/usr/bin/systemextensionsctl" + let p = Process() + p.executableURL = URL(fileURLWithPath: tool) + p.arguments = ["list"] + + let pipe = Pipe() + p.standardOutput = pipe + p.standardError = Pipe() + + do { + try p.run() + p.waitUntilExit() + let data = pipe.fileHandleForReading.readDataToEndOfFile() + guard let output = String(data: data, encoding: .utf8) else { return .unloaded } + + // Look for our bundle id line + if let line = output.split(separator: "\n").first(where: { $0.contains(bundleID) }) { + if line.contains("[activated enabled]") { return .activated } + if line.contains("[activated waiting for user]") { return .needsApproval } + if line.contains("terminated waiting to uninstall") { return .unloaded } + return .activating + } else { + return .unloaded + } + } catch { + return .unloaded + } + } +#endif + + private let dextIdentifier: String = Bundle.main.bundleIdentifier! + ".Driver" + + public var dextLoadingState: String { + switch state { + case .unloaded: + return "TinyGPUDriver isn't loaded." + case .activating: + return "Activating TinyGPUDriver, please wait." + case .needsApproval: + return "Please follow the prompt to approve TinyGPUDriver." + case .activated: + return "TinyGPUDriver has been activated and is ready to use. You can close the installer." + case .activationError: + return "TinyGPUDriver has experienced an error during activation.\nPlease check the logs to find the error." + } + } +} + +extension TinyGPUViewModel: ObservableObject { + +#if os(macOS) + func activateMyDext() { + activateExtension(dextIdentifier) + } + + func deactivateMyDext() { + deactivateExtension(dextIdentifier) + } + + func activateExtension(_ dextIdentifier: String) { + + let request = OSSystemExtensionRequest + .activationRequest(forExtensionWithIdentifier: dextIdentifier, + queue: .main) + request.delegate = self + OSSystemExtensionManager.shared.submitRequest(request) + + self.state = .activating + } + + func deactivateExtension(_ dextIdentifier: String) { + + let request = OSSystemExtensionRequest.deactivationRequest(forExtensionWithIdentifier: dextIdentifier, queue: .main) + request.delegate = self + OSSystemExtensionManager.shared.submitRequest(request) + + self.state = .unloaded + } +#endif +} + +#if os(macOS) +extension TinyGPUViewModel: OSSystemExtensionRequestDelegate { + + func request( + _ request: OSSystemExtensionRequest, + actionForReplacingExtension existing: OSSystemExtensionProperties, + withExtension ext: OSSystemExtensionProperties) -> OSSystemExtensionRequest.ReplacementAction { + + var replacementAction: OSSystemExtensionRequest.ReplacementAction + + os_log("sysex actionForReplacingExtension: %@ %@", existing, ext) + + // Add appropriate logic here to determine whether to replace the extension + // with the new extension. Common things to check for include + // testing whether the new extension's version number is newer than + // the current version number, or whether the bundleIdentifier is different. + // For simplicity, this sample always replaces the current extension + // with the new one. + replacementAction = .replace + + self.state = .activating + return replacementAction + } + + func requestNeedsUserApproval(_ request: OSSystemExtensionRequest) { + os_log("sysex requestNeedsUserApproval") + self.state = .needsApproval + } + + func request(_ request: OSSystemExtensionRequest, didFinishWithResult result: OSSystemExtensionRequest.Result) { + os_log("sysex didFinishWithResult: %d", result.rawValue) + self.state = .activated + } + + func request(_ request: OSSystemExtensionRequest, didFailWithError error: Error) { + os_log("sysex didFailWithError: %@", error.localizedDescription) + self.state = .activationError + } +} +#endif diff --git a/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension.xcodeproj/project.pbxproj b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension.xcodeproj/project.pbxproj new file mode 100644 index 0000000000..dfe1322314 --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension.xcodeproj/project.pbxproj @@ -0,0 +1,587 @@ +// !$*UTF8*$! +{ + archiveVersion = 1; + classes = { + }; + objectVersion = 54; + objects = { + +/* Begin PBXBuildFile section */ + 0ACB55392E9CB880007029EF /* PCIDriverKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 0ACB55382E9CB880007029EF /* PCIDriverKit.framework */; }; + 54798269286A3512009785F6 /* CoreAudio.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 54798268286A3512009785F6 /* CoreAudio.framework */; }; + 549EB121286A1A37009D38AB /* TinyGPUViewModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 549EB11F286A1A37009D38AB /* TinyGPUViewModel.swift */; }; + 549EB123286A1D48009D38AB /* org.tinygrad.tinygpu.Driver.dext in Embed System Extensions */ = {isa = PBXBuildFile; fileRef = C5B7D9BC26128AC50089B4C3 /* org.tinygrad.tinygpu.Driver.dext */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; }; + 549EB131286A2B98009D38AB /* IOKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 549EB130286A2B98009D38AB /* IOKit.framework */; }; + 54E42BC8286A1697000E1E9A /* TinyGPUApp.swift in Sources */ = {isa = PBXBuildFile; fileRef = 54E42BB8286A1696000E1E9A /* TinyGPUApp.swift */; }; + 54E42BCA286A1697000E1E9A /* TinyGPUView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 54E42BB9286A1696000E1E9A /* TinyGPUView.swift */; }; + 54E42BCC286A1697000E1E9A /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 54E42BBA286A1697000E1E9A /* Assets.xcassets */; }; + C5B7D9C326128AC50089B4C3 /* TinyGPUDriver.cpp in Sources */ = {isa = PBXBuildFile; fileRef = C5B7D9C226128AC50089B4C3 /* TinyGPUDriver.cpp */; }; + C5B7D9C526128AC50089B4C3 /* TinyGPUDriver.iig in Sources */ = {isa = PBXBuildFile; fileRef = C5B7D9C426128AC50089B4C3 /* TinyGPUDriver.iig */; }; + C5C3BBB32612ACDC003C7BFE /* AudioDriverKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = C5C3BBB12612ACD3003C7BFE /* AudioDriverKit.framework */; }; + C5C3BBB52612ACEF003C7BFE /* DriverKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = C5C3BBB42612ACEF003C7BFE /* DriverKit.framework */; }; + C5D787AC261667FC006047E5 /* TinyGPUDriverUserClient.iig in Sources */ = {isa = PBXBuildFile; fileRef = C5D787AB261667FC006047E5 /* TinyGPUDriverUserClient.iig */; }; + C5D787AE26168E59006047E5 /* TinyGPUDriverUserClient.cpp in Sources */ = {isa = PBXBuildFile; fileRef = C5D787AD26168D1E006047E5 /* TinyGPUDriverUserClient.cpp */; }; +/* End PBXBuildFile section */ + +/* Begin PBXContainerItemProxy section */ + 549EB126286A1D66009D38AB /* PBXContainerItemProxy */ = { + isa = PBXContainerItemProxy; + containerPortal = C5B7D9B326128AC50089B4C3 /* Project object */; + proxyType = 1; + remoteGlobalIDString = C5B7D9BB26128AC50089B4C3; + remoteInfo = SimpleAudioDriver; + }; +/* End PBXContainerItemProxy section */ + +/* Begin PBXCopyFilesBuildPhase section */ + 549EB122286A1D3A009D38AB /* Embed System Extensions */ = { + isa = PBXCopyFilesBuildPhase; + buildActionMask = 2147483647; + dstPath = "$(SYSTEM_EXTENSIONS_FOLDER_PATH)"; + dstSubfolderSpec = 16; + files = ( + 549EB123286A1D48009D38AB /* org.tinygrad.tinygpu.Driver.dext in Embed System Extensions */, + ); + name = "Embed System Extensions"; + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXCopyFilesBuildPhase section */ + +/* Begin PBXFileReference section */ + 0ACB55382E9CB880007029EF /* PCIDriverKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = PCIDriverKit.framework; path = System/DriverKit/System/Library/Frameworks/PCIDriverKit.framework; sourceTree = SDKROOT; }; + 54798268286A3512009785F6 /* CoreAudio.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CoreAudio.framework; path = Platforms/MacOSX.platform/Developer/SDKs/MacOSX13.0.sdk/System/Library/Frameworks/CoreAudio.framework; sourceTree = DEVELOPER_DIR; }; + 549EB11F286A1A37009D38AB /* TinyGPUViewModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TinyGPUViewModel.swift; sourceTree = ""; usesTabs = 1; }; + 549EB130286A2B98009D38AB /* IOKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = IOKit.framework; path = Platforms/MacOSX.platform/Developer/SDKs/MacOSX13.0.sdk/System/Library/Frameworks/IOKit.framework; sourceTree = DEVELOPER_DIR; }; + 549EB132286A2B9D009D38AB /* IOKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = IOKit.framework; path = Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS16.0.sdk/System/Library/Frameworks/IOKit.framework; sourceTree = DEVELOPER_DIR; }; + 54E42BB8286A1696000E1E9A /* TinyGPUApp.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TinyGPUApp.swift; sourceTree = ""; }; + 54E42BB9286A1696000E1E9A /* TinyGPUView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TinyGPUView.swift; sourceTree = ""; }; + 54E42BBA286A1697000E1E9A /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; }; + 54E42BC4286A1697000E1E9A /* TinyGPU.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = TinyGPU.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 54E42BC6286A1697000E1E9A /* macOS.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = macOS.entitlements; sourceTree = ""; }; + C5B7D9BC26128AC50089B4C3 /* org.tinygrad.tinygpu.Driver.dext */ = {isa = PBXFileReference; explicitFileType = "wrapper.driver-extension"; includeInIndex = 0; path = org.tinygrad.tinygpu.Driver.dext; sourceTree = BUILT_PRODUCTS_DIR; }; + C5B7D9BF26128AC50089B4C3 /* DriverKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = DriverKit.framework; path = Library/Frameworks/DriverKit.framework; sourceTree = DEVELOPER_DIR; }; + C5B7D9C226128AC50089B4C3 /* TinyGPUDriver.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = TinyGPUDriver.cpp; sourceTree = ""; usesTabs = 1; }; + C5B7D9C426128AC50089B4C3 /* TinyGPUDriver.iig */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.iig; path = TinyGPUDriver.iig; sourceTree = ""; }; + C5B7D9C626128AC50089B4C3 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; + C5B7D9CC26128ADA0089B4C3 /* AudioDriverKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = AudioDriverKit.framework; path = System/DriverKit/System/Library/Frameworks/AudioDriverKit.framework; sourceTree = SDKROOT; }; + C5B7D9CE26128B150089B4C3 /* TinyGPUDriver.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = TinyGPUDriver.entitlements; sourceTree = ""; }; + C5C0063326178F98003345D8 /* AppKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = AppKit.framework; path = Platforms/MacOSX.platform/Developer/SDKs/MacOSX12.0.sdk/System/Library/Frameworks/AppKit.framework; sourceTree = DEVELOPER_DIR; }; + C5C006352617ACB8003345D8 /* CoreAudio.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CoreAudio.framework; path = Platforms/MacOSX.platform/Developer/SDKs/MacOSX12.0.sdk/System/Library/Frameworks/CoreAudio.framework; sourceTree = DEVELOPER_DIR; }; + C5C3BBB12612ACD3003C7BFE /* AudioDriverKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = AudioDriverKit.framework; path = Platforms/DriverKit.platform/Developer/SDKs/DriverKit.MacOSX21.0.Internal.sdk/System/DriverKit/System/Library/Frameworks/AudioDriverKit.framework; sourceTree = DEVELOPER_DIR; }; + C5C3BBB42612ACEF003C7BFE /* DriverKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = DriverKit.framework; path = Platforms/DriverKit.platform/Developer/SDKs/DriverKit.MacOSX21.0.Internal.sdk/System/DriverKit/System/Library/Frameworks/DriverKit.framework; sourceTree = DEVELOPER_DIR; }; + C5D787AB261667FC006047E5 /* TinyGPUDriverUserClient.iig */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.iig; path = TinyGPUDriverUserClient.iig; sourceTree = ""; }; + C5D787AD26168D1E006047E5 /* TinyGPUDriverUserClient.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = TinyGPUDriverUserClient.cpp; sourceTree = ""; }; + C5D787B026169723006047E5 /* IOKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = IOKit.framework; path = Platforms/MacOSX.platform/Developer/SDKs/MacOSX12.0.sdk/System/Library/Frameworks/IOKit.framework; sourceTree = DEVELOPER_DIR; }; + C5D787B22616973F006047E5 /* SystemExtensions.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = SystemExtensions.framework; path = Platforms/MacOSX.platform/Developer/SDKs/MacOSX12.0.sdk/System/Library/Frameworks/SystemExtensions.framework; sourceTree = DEVELOPER_DIR; }; + C5D787B426169747006047E5 /* Foundation.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Foundation.framework; path = Platforms/MacOSX.platform/Developer/SDKs/MacOSX12.0.sdk/System/Library/Frameworks/Foundation.framework; sourceTree = DEVELOPER_DIR; }; +/* End PBXFileReference section */ + +/* Begin PBXFrameworksBuildPhase section */ + 54E42BC1286A1697000E1E9A /* Frameworks */ = { + isa = PBXFrameworksBuildPhase; + buildActionMask = 2147483647; + files = ( + 54798269286A3512009785F6 /* CoreAudio.framework in Frameworks */, + 549EB131286A2B98009D38AB /* IOKit.framework in Frameworks */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; + C5B7D9B926128AC50089B4C3 /* Frameworks */ = { + isa = PBXFrameworksBuildPhase; + buildActionMask = 2147483647; + files = ( + C5C3BBB32612ACDC003C7BFE /* AudioDriverKit.framework in Frameworks */, + C5C3BBB52612ACEF003C7BFE /* DriverKit.framework in Frameworks */, + 0ACB55392E9CB880007029EF /* PCIDriverKit.framework in Frameworks */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXFrameworksBuildPhase section */ + +/* Begin PBXGroup section */ + 54E42BB7286A1696000E1E9A /* Shared */ = { + isa = PBXGroup; + children = ( + 54E42BB8286A1696000E1E9A /* TinyGPUApp.swift */, + 54E42BB9286A1696000E1E9A /* TinyGPUView.swift */, + 549EB11F286A1A37009D38AB /* TinyGPUViewModel.swift */, + 54E42BBA286A1697000E1E9A /* Assets.xcassets */, + ); + path = Shared; + sourceTree = ""; + }; + 54E42BC5286A1697000E1E9A /* macOS */ = { + isa = PBXGroup; + children = ( + 54E42BC6286A1697000E1E9A /* macOS.entitlements */, + ); + path = macOS; + sourceTree = ""; + }; + C5B7D9B226128AC50089B4C3 = { + isa = PBXGroup; + children = ( + C5B7D9C126128AC50089B4C3 /* TinyGPUDriverExtension */, + 54E42BB7286A1696000E1E9A /* Shared */, + 54E42BC5286A1697000E1E9A /* macOS */, + C5B7D9BE26128AC50089B4C3 /* Frameworks */, + C5B7D9BD26128AC50089B4C3 /* Products */, + ); + sourceTree = ""; + usesTabs = 1; + }; + C5B7D9BD26128AC50089B4C3 /* Products */ = { + isa = PBXGroup; + children = ( + C5B7D9BC26128AC50089B4C3 /* org.tinygrad.tinygpu.Driver.dext */, + 54E42BC4286A1697000E1E9A /* TinyGPU.app */, + ); + name = Products; + sourceTree = ""; + }; + C5B7D9BE26128AC50089B4C3 /* Frameworks */ = { + isa = PBXGroup; + children = ( + 0ACB55382E9CB880007029EF /* PCIDriverKit.framework */, + 54798268286A3512009785F6 /* CoreAudio.framework */, + 549EB130286A2B98009D38AB /* IOKit.framework */, + 549EB132286A2B9D009D38AB /* IOKit.framework */, + C5C006352617ACB8003345D8 /* CoreAudio.framework */, + C5C0063326178F98003345D8 /* AppKit.framework */, + C5D787B426169747006047E5 /* Foundation.framework */, + C5D787B22616973F006047E5 /* SystemExtensions.framework */, + C5D787B026169723006047E5 /* IOKit.framework */, + C5C3BBB42612ACEF003C7BFE /* DriverKit.framework */, + C5B7D9CC26128ADA0089B4C3 /* AudioDriverKit.framework */, + C5C3BBB12612ACD3003C7BFE /* AudioDriverKit.framework */, + C5B7D9BF26128AC50089B4C3 /* DriverKit.framework */, + ); + name = Frameworks; + sourceTree = ""; + }; + C5B7D9C126128AC50089B4C3 /* TinyGPUDriverExtension */ = { + isa = PBXGroup; + children = ( + C5B7D9C226128AC50089B4C3 /* TinyGPUDriver.cpp */, + C5B7D9C426128AC50089B4C3 /* TinyGPUDriver.iig */, + C5D787AD26168D1E006047E5 /* TinyGPUDriverUserClient.cpp */, + C5D787AB261667FC006047E5 /* TinyGPUDriverUserClient.iig */, + C5B7D9C626128AC50089B4C3 /* Info.plist */, + C5B7D9CE26128B150089B4C3 /* TinyGPUDriver.entitlements */, + ); + path = TinyGPUDriverExtension; + sourceTree = ""; + }; +/* End PBXGroup section */ + +/* Begin PBXHeadersBuildPhase section */ + C5B7D9B726128AC50089B4C3 /* Headers */ = { + isa = PBXHeadersBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXHeadersBuildPhase section */ + +/* Begin PBXNativeTarget section */ + 54E42BC3286A1697000E1E9A /* TinyGPU Installer (macOS) */ = { + isa = PBXNativeTarget; + buildConfigurationList = 54E42BD2286A1697000E1E9A /* Build configuration list for PBXNativeTarget "TinyGPU Installer (macOS)" */; + buildPhases = ( + 54E42BC0286A1697000E1E9A /* Sources */, + 54E42BC1286A1697000E1E9A /* Frameworks */, + 54E42BC2286A1697000E1E9A /* Resources */, + 549EB122286A1D3A009D38AB /* Embed System Extensions */, + ); + buildRules = ( + ); + dependencies = ( + 549EB127286A1D66009D38AB /* PBXTargetDependency */, + ); + name = "TinyGPU Installer (macOS)"; + productName = "SimpleAudioDriverExtension2 (macOS)"; + productReference = 54E42BC4286A1697000E1E9A /* TinyGPU.app */; + productType = "com.apple.product-type.application"; + }; + C5B7D9BB26128AC50089B4C3 /* TinyGPUDriver */ = { + isa = PBXNativeTarget; + buildConfigurationList = C5B7D9C926128AC50089B4C3 /* Build configuration list for PBXNativeTarget "TinyGPUDriver" */; + buildPhases = ( + C5B7D9B726128AC50089B4C3 /* Headers */, + C5B7D9B826128AC50089B4C3 /* Sources */, + C5B7D9B926128AC50089B4C3 /* Frameworks */, + C5B7D9BA26128AC50089B4C3 /* Resources */, + ); + buildRules = ( + ); + dependencies = ( + ); + name = TinyGPUDriver; + productName = SimpleAudioDriverExtension; + productReference = C5B7D9BC26128AC50089B4C3 /* org.tinygrad.tinygpu.Driver.dext */; + productType = "com.apple.product-type.driver-extension"; + }; +/* End PBXNativeTarget section */ + +/* Begin PBXProject section */ + C5B7D9B326128AC50089B4C3 /* Project object */ = { + isa = PBXProject; + attributes = { + BuildIndependentTargetsInParallel = YES; + DefaultBuildSystemTypeForWorkspace = Latest; + LastSwiftUpdateCheck = 1400; + LastUpgradeCheck = 1600; + ORGANIZATIONNAME = Apple; + TargetAttributes = { + 54E42BC3286A1697000E1E9A = { + CreatedOnToolsVersion = 14.0; + LastSwiftMigration = 1400; + }; + C5B7D9BB26128AC50089B4C3 = { + CreatedOnToolsVersion = 13.0; + }; + }; + }; + buildConfigurationList = C5B7D9B626128AC50089B4C3 /* Build configuration list for PBXProject "TinyGPUDriverExtension" */; + compatibilityVersion = "Xcode 9.3"; + developmentRegion = en; + hasScannedForEncodings = 0; + knownRegions = ( + en, + Base, + ); + mainGroup = C5B7D9B226128AC50089B4C3; + productRefGroup = C5B7D9BD26128AC50089B4C3 /* Products */; + projectDirPath = ""; + projectRoot = ""; + targets = ( + C5B7D9BB26128AC50089B4C3 /* TinyGPUDriver */, + 54E42BC3286A1697000E1E9A /* TinyGPU Installer (macOS) */, + ); + }; +/* End PBXProject section */ + +/* Begin PBXResourcesBuildPhase section */ + 54E42BC2286A1697000E1E9A /* Resources */ = { + isa = PBXResourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + 54E42BCC286A1697000E1E9A /* Assets.xcassets in Resources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; + C5B7D9BA26128AC50089B4C3 /* Resources */ = { + isa = PBXResourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXResourcesBuildPhase section */ + +/* Begin PBXSourcesBuildPhase section */ + 54E42BC0286A1697000E1E9A /* Sources */ = { + isa = PBXSourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + 549EB121286A1A37009D38AB /* TinyGPUViewModel.swift in Sources */, + 54E42BCA286A1697000E1E9A /* TinyGPUView.swift in Sources */, + 54E42BC8286A1697000E1E9A /* TinyGPUApp.swift in Sources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; + C5B7D9B826128AC50089B4C3 /* Sources */ = { + isa = PBXSourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + C5B7D9C526128AC50089B4C3 /* TinyGPUDriver.iig in Sources */, + C5D787AE26168E59006047E5 /* TinyGPUDriverUserClient.cpp in Sources */, + C5D787AC261667FC006047E5 /* TinyGPUDriverUserClient.iig in Sources */, + C5B7D9C326128AC50089B4C3 /* TinyGPUDriver.cpp in Sources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXSourcesBuildPhase section */ + +/* Begin PBXTargetDependency section */ + 549EB127286A1D66009D38AB /* PBXTargetDependency */ = { + isa = PBXTargetDependency; + target = C5B7D9BB26128AC50089B4C3 /* TinyGPUDriver */; + targetProxy = 549EB126286A1D66009D38AB /* PBXContainerItemProxy */; + }; +/* End PBXTargetDependency section */ + +/* Begin XCBuildConfiguration section */ + 54E42BCF286A1697000E1E9A /* Debug */ = { + isa = XCBuildConfiguration; + buildSettings = { + ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; + ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor; + CLANG_ENABLE_MODULES = YES; + CODE_SIGN_ENTITLEMENTS = macOS/macOS.entitlements; + CODE_SIGN_IDENTITY = "-"; + CODE_SIGN_STYLE = Automatic; + COMBINE_HIDPI_IMAGES = YES; + CURRENT_PROJECT_VERSION = 1; + DEAD_CODE_STRIPPING = YES; + DEVELOPMENT_TEAM = ""; + ENABLE_HARDENED_RUNTIME = YES; + ENABLE_PREVIEWS = YES; + ENABLE_USER_SCRIPT_SANDBOXING = YES; + GENERATE_INFOPLIST_FILE = YES; + INFOPLIST_KEY_NSHumanReadableCopyright = ""; + LD_RUNPATH_SEARCH_PATHS = ( + "$(inherited)", + "@executable_path/../Frameworks", + ); + MACOSX_DEPLOYMENT_TARGET = 12.1; + MARKETING_VERSION = 1.0; + PRODUCT_BUNDLE_IDENTIFIER = org.tinygrad.tinygpu; + PRODUCT_NAME = TinyGPU; + PROVISIONING_PROFILE_SPECIFIER = ""; + SDKROOT = macosx; + SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; + SWIFT_EMIT_LOC_STRINGS = YES; + SWIFT_OPTIMIZATION_LEVEL = "-Onone"; + SWIFT_VERSION = 5.0; + }; + name = Debug; + }; + 54E42BD0286A1697000E1E9A /* Release */ = { + isa = XCBuildConfiguration; + buildSettings = { + ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; + ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor; + CLANG_ENABLE_MODULES = YES; + CODE_SIGN_ENTITLEMENTS = macOS/macOS.entitlements; + CODE_SIGN_IDENTITY = "-"; + CODE_SIGN_STYLE = Automatic; + COMBINE_HIDPI_IMAGES = YES; + CURRENT_PROJECT_VERSION = 1; + DEAD_CODE_STRIPPING = YES; + DEVELOPMENT_TEAM = ""; + ENABLE_HARDENED_RUNTIME = YES; + ENABLE_PREVIEWS = YES; + ENABLE_USER_SCRIPT_SANDBOXING = YES; + GENERATE_INFOPLIST_FILE = YES; + INFOPLIST_KEY_NSHumanReadableCopyright = ""; + LD_RUNPATH_SEARCH_PATHS = ( + "$(inherited)", + "@executable_path/../Frameworks", + ); + MACOSX_DEPLOYMENT_TARGET = 12.1; + MARKETING_VERSION = 1.0; + PRODUCT_BUNDLE_IDENTIFIER = org.tinygrad.tinygpu; + PRODUCT_NAME = TinyGPU; + PROVISIONING_PROFILE_SPECIFIER = ""; + SDKROOT = macosx; + SWIFT_COMPILATION_MODE = wholemodule; + SWIFT_EMIT_LOC_STRINGS = YES; + SWIFT_OPTIMIZATION_LEVEL = "-O"; + SWIFT_VERSION = 5.0; + }; + name = Release; + }; + C5B7D9C726128AC50089B4C3 /* Debug */ = { + isa = XCBuildConfiguration; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + CLANG_ANALYZER_NONNULL = YES; + CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; + CLANG_CXX_LANGUAGE_STANDARD = "gnu++17"; + CLANG_CXX_LIBRARY = "libc++"; + CLANG_ENABLE_MODULES = YES; + CLANG_ENABLE_OBJC_ARC = YES; + CLANG_ENABLE_OBJC_WEAK = YES; + CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; + CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_COMMA = YES; + CLANG_WARN_CONSTANT_CONVERSION = YES; + CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; + CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; + CLANG_WARN_DOCUMENTATION_COMMENTS = YES; + CLANG_WARN_EMPTY_BODY = YES; + CLANG_WARN_ENUM_CONVERSION = YES; + CLANG_WARN_INFINITE_RECURSION = YES; + CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; + CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; + CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; + CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES; + CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; + CLANG_WARN_STRICT_PROTOTYPES = YES; + CLANG_WARN_SUSPICIOUS_MOVE = YES; + CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; + CLANG_WARN_UNREACHABLE_CODE = YES; + CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; + COPY_PHASE_STRIP = NO; + DEBUG_INFORMATION_FORMAT = dwarf; + DRIVERKIT_DEPLOYMENT_TARGET = 21.0; + ENABLE_STRICT_OBJC_MSGSEND = YES; + ENABLE_TESTABILITY = YES; + GCC_C_LANGUAGE_STANDARD = gnu11; + GCC_DYNAMIC_NO_PIC = NO; + GCC_NO_COMMON_BLOCKS = YES; + GCC_OPTIMIZATION_LEVEL = 0; + GCC_PREPROCESSOR_DEFINITIONS = ( + "DEBUG=1", + "$(inherited)", + ); + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; + GCC_WARN_UNDECLARED_SELECTOR = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; + GCC_WARN_UNUSED_FUNCTION = YES; + GCC_WARN_UNUSED_VARIABLE = YES; + MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE; + MTL_FAST_MATH = YES; + ONLY_ACTIVE_ARCH = YES; + SDKROOT = driverkit; + }; + name = Debug; + }; + C5B7D9C826128AC50089B4C3 /* Release */ = { + isa = XCBuildConfiguration; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + CLANG_ANALYZER_NONNULL = YES; + CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; + CLANG_CXX_LANGUAGE_STANDARD = "gnu++17"; + CLANG_CXX_LIBRARY = "libc++"; + CLANG_ENABLE_MODULES = YES; + CLANG_ENABLE_OBJC_ARC = YES; + CLANG_ENABLE_OBJC_WEAK = YES; + CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; + CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_COMMA = YES; + CLANG_WARN_CONSTANT_CONVERSION = YES; + CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; + CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; + CLANG_WARN_DOCUMENTATION_COMMENTS = YES; + CLANG_WARN_EMPTY_BODY = YES; + CLANG_WARN_ENUM_CONVERSION = YES; + CLANG_WARN_INFINITE_RECURSION = YES; + CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; + CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; + CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; + CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES; + CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; + CLANG_WARN_STRICT_PROTOTYPES = YES; + CLANG_WARN_SUSPICIOUS_MOVE = YES; + CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; + CLANG_WARN_UNREACHABLE_CODE = YES; + CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; + COPY_PHASE_STRIP = NO; + DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; + DRIVERKIT_DEPLOYMENT_TARGET = 21.0; + ENABLE_NS_ASSERTIONS = NO; + ENABLE_STRICT_OBJC_MSGSEND = YES; + GCC_C_LANGUAGE_STANDARD = gnu11; + GCC_NO_COMMON_BLOCKS = YES; + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; + GCC_WARN_UNDECLARED_SELECTOR = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; + GCC_WARN_UNUSED_FUNCTION = YES; + GCC_WARN_UNUSED_VARIABLE = YES; + MTL_ENABLE_DEBUG_INFO = NO; + MTL_FAST_MATH = YES; + SDKROOT = driverkit; + SWIFT_COMPILATION_MODE = wholemodule; + }; + name = Release; + }; + C5B7D9CA26128AC50089B4C3 /* Debug */ = { + isa = XCBuildConfiguration; + buildSettings = { + AD_HOC_CODE_SIGNING_ALLOWED = YES; + CODE_SIGN_ENTITLEMENTS = TinyGPUDriverExtension/TinyGPUDriver.entitlements; + CODE_SIGN_IDENTITY = "-"; + CODE_SIGN_STYLE = Automatic; + CURRENT_PROJECT_VERSION = 1; + DEVELOPMENT_TEAM = ""; + DRIVERKIT_DEPLOYMENT_TARGET = 21.0; + ENABLE_USER_SCRIPT_SANDBOXING = YES; + FRAMEWORK_SEARCH_PATHS = ( + "$(inherited)", + "$(SDKROOT)/System/DriverKit/System/Library/Frameworks", + ); + GENERATE_INFOPLIST_FILE = YES; + INFOPLIST_FILE = TinyGPUDriverExtension/Info.plist; + INFOPLIST_KEY_OSBundleUsageDescription = "Sample Code Audio Driver Kit Extension"; + MARKETING_VERSION = 1.0; + PRODUCT_BUNDLE_IDENTIFIER = org.tinygrad.tinygpu.Driver; + PRODUCT_NAME = "$(inherited)"; + PROVISIONING_PROFILE_SPECIFIER = ""; + RUN_CLANG_STATIC_ANALYZER = YES; + SDKROOT = driverkit; + SKIP_INSTALL = YES; + }; + name = Debug; + }; + C5B7D9CB26128AC50089B4C3 /* Release */ = { + isa = XCBuildConfiguration; + buildSettings = { + AD_HOC_CODE_SIGNING_ALLOWED = YES; + CODE_SIGN_ENTITLEMENTS = TinyGPUDriverExtension/TinyGPUDriver.entitlements; + CODE_SIGN_IDENTITY = "-"; + CODE_SIGN_STYLE = Automatic; + CURRENT_PROJECT_VERSION = 1; + DEVELOPMENT_TEAM = ""; + DRIVERKIT_DEPLOYMENT_TARGET = 21.0; + ENABLE_USER_SCRIPT_SANDBOXING = YES; + FRAMEWORK_SEARCH_PATHS = ( + "$(inherited)", + "$(SDKROOT)/System/DriverKit/System/Library/Frameworks", + ); + GENERATE_INFOPLIST_FILE = YES; + INFOPLIST_FILE = TinyGPUDriverExtension/Info.plist; + INFOPLIST_KEY_OSBundleUsageDescription = "Sample Code Audio Driver Kit Extension"; + MARKETING_VERSION = 1.0; + PRODUCT_BUNDLE_IDENTIFIER = org.tinygrad.tinygpu.Driver; + PRODUCT_NAME = "$(inherited)"; + PROVISIONING_PROFILE_SPECIFIER = ""; + RUN_CLANG_STATIC_ANALYZER = YES; + SDKROOT = driverkit; + SKIP_INSTALL = YES; + }; + name = Release; + }; +/* End XCBuildConfiguration section */ + +/* Begin XCConfigurationList section */ + 54E42BD2286A1697000E1E9A /* Build configuration list for PBXNativeTarget "TinyGPU Installer (macOS)" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + 54E42BCF286A1697000E1E9A /* Debug */, + 54E42BD0286A1697000E1E9A /* Release */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; + C5B7D9B626128AC50089B4C3 /* Build configuration list for PBXProject "TinyGPUDriverExtension" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + C5B7D9C726128AC50089B4C3 /* Debug */, + C5B7D9C826128AC50089B4C3 /* Release */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; + C5B7D9C926128AC50089B4C3 /* Build configuration list for PBXNativeTarget "TinyGPUDriver" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + C5B7D9CA26128AC50089B4C3 /* Debug */, + C5B7D9CB26128AC50089B4C3 /* Release */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; +/* End XCConfigurationList section */ + }; + rootObject = C5B7D9B326128AC50089B4C3 /* Project object */; +} diff --git a/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension.xcodeproj/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension.xcodeproj/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings new file mode 100644 index 0000000000..280eff1f10 --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension.xcodeproj/project.xcworkspace/xcshareddata/WorkspaceSettings.xcsettings @@ -0,0 +1,10 @@ + + + + + BuildSystemType + Latest + DerivedDataLocationStyle + Default + + diff --git a/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/Info.plist b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/Info.plist new file mode 100644 index 0000000000..61f599d7a1 --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/Info.plist @@ -0,0 +1,37 @@ + + + + + IOKitPersonalities + + TinyGPUDriver + + IOPCIPrimaryMatch + 0x70001002&0xF000FFFF + IOPCITunnelCompatible + + CFBundleIdentifier + $(PRODUCT_BUNDLE_IDENTIFIER) + IOClass + IOUserService + IOMatchCategory + TinyGPUDriver + IOProviderClass + IOPCIDevice + IOResourceMatch + IOKit + IOUserClass + TinyGPUDriver + IOUserServerName + org.tinygrad.tinygpu.Driver + TinyGPUDriverUserClientProperties + + IOClass + IOUserUserClient + IOUserClass + TinyGPUDriverUserClient + + + + + diff --git a/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriver.cpp b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriver.cpp new file mode 100644 index 0000000000..378b9efc12 --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriver.cpp @@ -0,0 +1,223 @@ +#include "TinyGPUDriver.h" +#include "TinyGPUDriverUserClient.h" +#include +#include +#include +#include +#include +#include +#include +#include +#include + +struct TinyGPUDriver_IVars +{ + IOPCIDevice *pci = nullptr; +}; + +bool TinyGPUDriver::init() +{ + os_log(OS_LOG_DEFAULT, "tinygpu: init"); + + auto answer = super::init(); + if (!answer) { + return false; + } + + ivars = new TinyGPUDriver_IVars(); + if (ivars == nullptr) { + return false; + } + + return true; +} + +void TinyGPUDriver::free() +{ + if (ivars != nullptr) { + + } + IOSafeDeleteNULL(ivars, TinyGPUDriver_IVars, 1); + super::free(); +} + +kern_return_t TinyGPUDriver::Start_Impl(IOService* in_provider) +{ + IOServiceName service_name; + os_log(OS_LOG_DEFAULT, "tinygpu: on gpu detected"); + + kern_return_t err = Start(in_provider, SUPERDISPATCH); + if (err) return err; + + ivars->pci = OSDynamicCast(IOPCIDevice, in_provider); + if (!ivars->pci) return kIOReturnNoDevice; + + err = ivars->pci->Open(this, 0); + if (err) { + os_log(OS_LOG_DEFAULT, "tinygpu: Open() failed 0x%08x", err); + ivars->pci = nullptr; + return err; + } + + uint16_t ven = 0, dev = 0; + ivars->pci->ConfigurationRead16(kIOPCIConfigurationOffsetVendorID, &ven); + ivars->pci->ConfigurationRead16(kIOPCIConfigurationOffsetDeviceID, &dev); + os_log(OS_LOG_DEFAULT, "tinygpu: opened device ven=0x%04x dev=0x%04x", ven, dev); + +#if 0 + uint32_t off = 0x100; + while (off) { + uint32_t hdr = 0, next = 0, cap_id = 0; + ivars->pci->ConfigurationRead32(off, &hdr); + cap_id = hdr & 0xFFFFu; + next = (hdr >> 20) & 0xFFCu; + os_log(OS_LOG_DEFAULT, "tinygpu: cap: %u", cap_id); + if (cap_id == 0x15) { + uint32_t cap = 0, ctrl = 0; + ivars->pci->ConfigurationRead32(off+0x4, &cap); + ivars->pci->ConfigurationRead32(off+0x8, &ctrl); + + uint32_t new_bar_size = 31 - __builtin_clz(cap >> 4); + uint32_t new_ctrl = (ctrl & ~0x1f00) | (new_bar_size << 8); + ivars->pci->ConfigurationWrite32(off+0x8, new_ctrl); + + os_log(OS_LOG_DEFAULT, "tinygpu: rebar: cap=%u ctrl=%u new_bar_size=%u new_ctrl=%u", cap, ctrl, new_bar_size, new_ctrl); + ivars->pci->Reset(0); + break; + } + off = next; + } + ivars->pci->Reset(0); +#endif + + uint16_t commandRegister; + ivars->pci->ConfigurationRead16(kIOPCIConfigurationOffsetCommand, &commandRegister); + commandRegister |= (kIOPCICommandIOSpace | kIOPCICommandBusMaster | kIOPCICommandMemorySpace); + ivars->pci->ConfigurationWrite16(kIOPCIConfigurationOffsetCommand, commandRegister); + + memcpy((void*)service_name, (void*)"tinygpu\0", 8); + SetName(service_name); + + os_log(OS_LOG_DEFAULT, "tinygpu: will register service %s", service_name); + RegisterService(); + + os_log(OS_LOG_DEFAULT, "tinygpu: service started %s", service_name); + return 0; +} + +kern_return_t TinyGPUDriver::Stop_Impl(IOService* in_provider) +{ + ivars->pci->Close(this, 0); + return 0; +} + +kern_return_t TinyGPUDriver::NewUserClient_Impl(uint32_t in_type, IOUserClient** out_user_client) +{ + kern_return_t err = 0; + + IOService* user_client_service = nullptr; + err = Create(this, "TinyGPUDriverUserClientProperties", &user_client_service); + if (err) { + os_log(OS_LOG_DEFAULT, "tinygpu: failed to create NewUserClient"); + goto error; + } + *out_user_client = OSDynamicCast(IOUserClient, user_client_service); + os_log(OS_LOG_DEFAULT, "tinygpu: NewUserClient created"); + +error: + return err; +} + +kern_return_t TinyGPUDriver::MapBar(uint32_t bar, IOMemoryDescriptor** memory) +{ + kern_return_t err = 0; + uint8_t barMemoryIndex, barMemoryType; + uint64_t barMemorySize; + err = ivars->pci->GetBARInfo(bar, &barMemoryIndex, &barMemorySize, &barMemoryType); + if (err) return err; + + os_log(OS_LOG_DEFAULT, "tinygpu: requested bar mapping %d, %d", bar, (uint32_t)barMemoryIndex); + err = ivars->pci->_CopyDeviceMemoryWithIndex(barMemoryIndex, memory, this); + return err; +} + +kern_return_t TinyGPUDriver::CreateDMA(size_t size, TinyGPUCreateDMAResp* dmaDesc) +{ + kern_return_t err = 0; + IOMemoryMap* memoryMap = nullptr; + IOBufferMemoryDescriptor* sharedBuf = nullptr; + IODMACommand* dmaCmd = nullptr; + uint64_t flags = kIOMemoryDirectionInOut; + uint32_t segCount = 32; + IOAddressSegment segments[32]; + IODMACommandSpecification dmaSpec = { + .options = 0, + .maxAddressBits = 40, + }; + + err = IOBufferMemoryDescriptor::Create(kIOMemoryDirectionInOut, size, IOVMPageSize, &sharedBuf); + if (err) { + os_log(OS_LOG_DEFAULT, "tinygpu: failed to alloc user buffer, err=%d", err); + goto error; + } + + err = IODMACommand::Create(ivars->pci, kIODMACommandCreateNoOptions, &dmaSpec, &dmaCmd); + if (err) { + os_log(OS_LOG_DEFAULT, "tinygpu: failed to create dma command, err=%d", err); + goto error; + } + + err = dmaCmd->PrepareForDMA(kIODMACommandPrepareForDMANoOptions, sharedBuf, 0, size, + &flags, &segCount, segments); + if (err) { + os_log(OS_LOG_DEFAULT, "tinygpu: failed to prepare for dma, err=%d", err); + goto error; + } + + // pass addresses to userland + { + // debug + for (int i = 0; i < segCount; i++) { + os_log(OS_LOG_DEFAULT, "tinygpu: new dma mapping (sz=0x%zx) %d 0x%llx 0x%llx", size, i, segments[i].address, segments[i].length); + } + + err = sharedBuf->CreateMapping(0, 0, 0, IOVMPageSize, IOVMPageSize, &memoryMap); // one page should be fine + if (err) { + os_log(OS_LOG_DEFAULT, "tinygpu: failed to map memory, err=%d", err); + goto error; + } + + // Send back gpu addresses + uint64_t* addr = (uint64_t*)memoryMap->GetAddress(); + for (int i = 0; i < segCount; i++) { + addr[i * 2] = segments[i].address; + addr[i * 2 + 1] = segments[i].length; + } + addr[segCount * 2] = 0; + addr[segCount * 2 + 1] = 0; + + // free memoryMap + memoryMap->release(); + memoryMap = nullptr; + } + + dmaDesc->sharedBuf = sharedBuf; + dmaDesc->dmaCmd = dmaCmd; + return 0; + +error: + if (memoryMap) { + memoryMap->release(); + memoryMap = nullptr; + } + if (dmaCmd) { + dmaCmd->CompleteDMA(kIODMACommandCompleteDMANoOptions); + dmaCmd->release(); + dmaCmd = nullptr; + } + if (sharedBuf) { + sharedBuf->release(); + sharedBuf = nullptr; + } + return err; +} diff --git a/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriver.entitlements b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriver.entitlements new file mode 100644 index 0000000000..61385b53ce --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriver.entitlements @@ -0,0 +1,17 @@ + + + + + com.apple.developer.driverkit.transport.pci + + + IOPCIMatch + 0x70001002&0xF000FFFF + + + com.apple.developer.driverkit.allow-any-userclient-access + + com.apple.developer.driverkit + + + diff --git a/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriver.iig b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriver.iig new file mode 100644 index 0000000000..42e7671b5d --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriver.iig @@ -0,0 +1,33 @@ +#ifndef TinyGPUDriver_h +#define TinyGPUDriver_h + +#include +#include +#include +#include +#include + +struct TinyGPUCreateDMAResp +{ + IOBufferMemoryDescriptor* sharedBuf; + IODMACommand* dmaCmd; +}; + +class TinyGPUDriver: public IOService +{ +public: + virtual bool init() override; + + virtual void free() override; + + virtual kern_return_t Start(IOService * provider) override; + + virtual kern_return_t Stop(IOService * provider) override; + + virtual kern_return_t NewUserClient(uint32_t in_type, IOUserClient** out_user_client) override; + + kern_return_t MapBar(uint32_t bar, IOMemoryDescriptor** memory) LOCALONLY; + kern_return_t CreateDMA(size_t size, TinyGPUCreateDMAResp* dmaDesc) LOCALONLY; +}; + +#endif /* TinyGPUDriver_h */ diff --git a/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriverUserClient.cpp b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriverUserClient.cpp new file mode 100644 index 0000000000..82f25dfb70 --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriverUserClient.cpp @@ -0,0 +1,94 @@ +#include "TinyGPUDriverUserClient.h" +#include "TinyGPUDriver.h" +#include +#include +#include + +struct TinyGPUDriverUserClient_IVars +{ + OSSharedPtr provider = nullptr; +}; + +bool TinyGPUDriverUserClient::init() +{ + auto theAnswer = super::init(); + if (!theAnswer) { + return false; + } + + ivars = IONewZero(TinyGPUDriverUserClient_IVars, 1); + if (ivars == nullptr) { + return false; + } + + return true; +} + +void TinyGPUDriverUserClient::free() +{ + if (ivars != nullptr) { + ivars->provider.reset(); + } + + IOSafeDeleteNULL(ivars, TinyGPUDriverUserClient_IVars, 1); + super::free(); +} + +kern_return_t TinyGPUDriverUserClient::Start_Impl(IOService* in_provider) +{ + kern_return_t err = kIOReturnSuccess; + if (!in_provider) { + os_log(OS_LOG_DEFAULT, "tinygpu: provider is null"); + err = kIOReturnBadArgument; + goto error; + } + + err = Start(in_provider, SUPERDISPATCH); + if (err) { + os_log(OS_LOG_DEFAULT, "tinygpu: failed to start super (%d)", err); + goto error; + } + + ivars->provider = OSSharedPtr(OSDynamicCast(TinyGPUDriver, in_provider), OSRetain); + return 0; + +error: + ivars->provider.reset(); + return err; +} + +kern_return_t TinyGPUDriverUserClient::Stop_Impl(IOService* in_provider) +{ + return Stop(in_provider, SUPERDISPATCH); +} + +kern_return_t TinyGPUDriverUserClient::ExternalMethod(uint64_t in_selector, IOUserClientMethodArguments* in_arguments, const IOUserClientMethodDispatch* in_dispatch, OSObject* in_target, void* in_reference) +{ + return kIOReturnUnsupported; +} + +kern_return_t IMPL(TinyGPUDriverUserClient, CopyClientMemoryForType) +{ + if (!memory) { + return kIOReturnBadArgument; + } + + if (ivars->provider.get() == nullptr) { + return kIOReturnNotAttached; + } + + if (type < 6) { + uint32_t bar = (uint32_t)type; + return ivars->provider->MapBar(bar, memory); + } + + // dma page buffer + TinyGPUCreateDMAResp buf; + kern_return_t err = ivars->provider->CreateDMA(type, &buf); + if (err) { + return err; + } + + *memory = buf.sharedBuf; + return 0; +} diff --git a/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriverUserClient.iig b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriverUserClient.iig new file mode 100644 index 0000000000..1668bf93b7 --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/TinyGPUDriverExtension/TinyGPUDriverUserClient.iig @@ -0,0 +1,21 @@ +#ifndef TinyGPUDriverUserClient_h +#define TinyGPUDriverUserClient_h + +#include + +class TinyGPUDriverUserClient : public IOUserClient +{ +public: + virtual bool init() final; + virtual void free() final; + + virtual kern_return_t Start(IOService* in_provider) final; + virtual kern_return_t Stop(IOService* in_provider) final; + + virtual kern_return_t ExternalMethod(uint64_t in_selector, IOUserClientMethodArguments* in_arguments, const IOUserClientMethodDispatch* in_dispatch, OSObject* in_target, void* in_reference) final; + + virtual kern_return_t CopyClientMemoryForType( + uint64_t type, uint64_t *options, IOMemoryDescriptor **memory) final; +}; + +#endif /* TinyGPUDriverUserClient_h */ diff --git a/extra/usbgpu/tbgpu/installer/macOS/macOS.entitlements b/extra/usbgpu/tbgpu/installer/macOS/macOS.entitlements new file mode 100644 index 0000000000..729c9e7634 --- /dev/null +++ b/extra/usbgpu/tbgpu/installer/macOS/macOS.entitlements @@ -0,0 +1,12 @@ + + + + + com.apple.security.app-sandbox + + com.apple.security.files.user-selected.read-only + + com.apple.developer.system-extension.install + + + diff --git a/extra/usbgpu/tbgpu/main.cpp b/extra/usbgpu/tbgpu/main.cpp new file mode 100644 index 0000000000..98e7da6a0c --- /dev/null +++ b/extra/usbgpu/tbgpu/main.cpp @@ -0,0 +1,39 @@ +#include +#include +#include +#include +#include + +static io_connect_t open_uc_by_name(const char *svc_name) { + io_connect_t conn = IO_OBJECT_NULL; + io_service_t service = IOServiceGetMatchingService(kIOMasterPortDefault, IOServiceNameMatching(svc_name)); + if (!service) { fprintf(stderr, "service not found: %s\n", svc_name); return IO_OBJECT_NULL; } + kern_return_t kr = IOServiceOpen(service, mach_task_self(), /*type*/0, &conn); + IOObjectRelease(service); + if (kr) { fprintf(stderr, "IOServiceOpen 0x%x\n", kr); return IO_OBJECT_NULL; } + return conn; +} + +int main(int argc, char **argv) { + uint32_t bar = (argc > 1) ? (uint32_t)strtoul(argv[1], NULL, 0) : 0; // pick BAR index + io_connect_t conn = open_uc_by_name("tinygpu"); + if (!conn) return 2; + + mach_vm_address_t addr = 0; + mach_vm_size_t size = 0; + kern_return_t kr = IOConnectMapMemory64(conn, bar, mach_task_self(), &addr, &size, kIOMapAnywhere); + if (kr) { fprintf(stderr, "Map BAR%u failed 0x%x\n", bar, kr); IOServiceClose(conn); return 3; } + + printf("BAR%u mapped at 0x%llx, size 0x%llx\n", bar, (unsigned long long)addr, (unsigned long long)size); + + // example: read a 32-bit register at offset 0x0 (make sure it’s safe!) + volatile uint32_t *mmio = (volatile uint32_t*)(uintptr_t)addr; + uint32_t v = mmio[0]; + printf("mmio[0]=0x%08x\n", v); + + kr = IOConnectUnmapMemory64(conn, bar, mach_task_self(), addr); + if (kr) fprintf(stderr, "Unmap failed 0x%x\n", kr); + + IOServiceClose(conn); + return 0; +} \ No newline at end of file diff --git a/extra/usbgpu/tbgpu/main.py b/extra/usbgpu/tbgpu/main.py new file mode 100644 index 0000000000..74719f5953 --- /dev/null +++ b/extra/usbgpu/tbgpu/main.py @@ -0,0 +1,82 @@ +import ctypes, ctypes.util, sys + +cf = ctypes.CDLL(ctypes.util.find_library("CoreFoundation")) +iokit = ctypes.CDLL(ctypes.util.find_library("IOKit")) +libsys = ctypes.CDLL(ctypes.util.find_library("System")) + +kern_return_t = ctypes.c_int +mach_port_t = ctypes.c_uint +io_object_t = mach_port_t +io_service_t = io_object_t +io_connect_t = mach_port_t +CFMutableDictionaryRef = ctypes.c_void_p +CFStringRef = ctypes.c_void_p + +kIOMasterPortDefault = mach_port_t(0) + +libsys.mach_task_self_.restype = mach_port_t + +iokit.IOServiceNameMatching.argtypes = [ctypes.c_char_p] +iokit.IOServiceNameMatching.restype = CFMutableDictionaryRef + +iokit.IOServiceGetMatchingService.argtypes = [mach_port_t, CFMutableDictionaryRef] +iokit.IOServiceGetMatchingService.restype = io_service_t + +iokit.IOObjectRelease.argtypes = [io_object_t] +iokit.IOObjectRelease.restype = kern_return_t + +iokit.IOServiceOpen.argtypes = [io_service_t, mach_port_t, ctypes.c_uint32, ctypes.POINTER(io_connect_t)] +iokit.IOServiceOpen.restype = kern_return_t + +iokit.IOConnectCallMethod.argtypes = [io_connect_t, ctypes.c_uint32, ctypes.POINTER(ctypes.c_uint64), ctypes.c_uint32, ctypes.c_void_p, + ctypes.c_size_t, ctypes.POINTER(ctypes.c_uint64), ctypes.POINTER(ctypes.c_uint32), ctypes.c_void_p, ctypes.POINTER(ctypes.c_size_t)] +iokit.IOConnectCallMethod.restype = kern_return_t + +def open_userclient_by_name(name: str, uc_type: int = 0) -> io_connect_t: + mdict = iokit.IOServiceNameMatching(name.encode("utf-8")) + if not mdict: raise RuntimeError("IOServiceNameMatching returned NULL") + + # Grab the first matching service + service = iokit.IOServiceGetMatchingService(kIOMasterPortDefault, mdict) + if not service: raise RuntimeError(f'service "{name}" not found') + + # print("lol", service) + # print(libsys.mach_task_self_) + # cast libsys.mach_task_self_ to uint and print + # print("lol", ctypes.cast(libsys.mach_task_self_, ctypes.POINTER(ctypes.c_uint)).contents.value) + + try: + # Open user client (type -> passed to NewUserClient_Impl) + conn = io_connect_t(0) + # print("lol", libsys.mach_task_self_) + kr = iokit.IOServiceOpen(service, ctypes.cast(libsys.mach_task_self_, ctypes.POINTER(ctypes.c_uint)).contents.value, + ctypes.c_uint32(uc_type), ctypes.byref(conn)) + if kr != 0: raise OSError(kr, f"IOServiceOpen failed (0x{kr:08x})") + return conn + finally: iokit.IOObjectRelease(service) + +def external_method(conn: io_connect_t, selector: int = 0) -> int: + # no scalars in/out, no struct in/out — just ping selector 0 + in_scalars = ctypes.POINTER(ctypes.c_uint64)() # NULL + out_scalars = (ctypes.c_uint64 * 1)() # space if driver returns something + out_scalars_cnt = ctypes.c_uint32(0) # driver can set this + + return iokit.IOConnectCallMethod(conn, ctypes.c_uint32(selector), in_scalars, ctypes.c_uint32(0), None, ctypes.c_size_t(0), + out_scalars, ctypes.byref(out_scalars_cnt), None, ctypes.byref(ctypes.c_size_t(0))) + +def close_userclient(conn: io_connect_t) -> None: + # IOServiceClose is a macro; exported symbol is IOServiceClose in IOKit + iokit.IOServiceClose.argtypes = [io_connect_t] + iokit.IOServiceClose.restype = kern_return_t + iokit.IOServiceClose(conn) + +if __name__ == "__main__": + try: + conn = open_userclient_by_name("tinygpu", uc_type=0) + kr = external_method(conn, selector=0) + print(f"ExternalMethod(0) -> 0x{kr:08x}") + except Exception as e: + print(e) + sys.exit(1) + finally: + if 'conn' in locals() and conn.value: close_userclient(conn) diff --git a/tinygrad/helpers.py b/tinygrad/helpers.py index 766ab4681b..750bf847ed 100644 --- a/tinygrad/helpers.py +++ b/tinygrad/helpers.py @@ -84,6 +84,7 @@ def word_wrap(x, wrap=80): i = 0 while len(ansistrip(x[:i])) < wrap and i < len(x): i += 1 return x[:i] + "\n" + word_wrap(x[i:], wrap) +def pad_bytes(b:bytes, align:int) -> bytes: return b + b'\x00' * ((align - (len(b) % align)) % align) # returns the axes to create new_shape if new_shape can be created by combining axis from old_shape def get_contraction(old_shape:tuple[T, ...], new_shape:tuple[T, ...]) -> list[list[int]]|None: # T is sint diff --git a/tinygrad/runtime/support/am/amdev.py b/tinygrad/runtime/support/am/amdev.py index 7ec9b4ae85..27eb90405e 100644 --- a/tinygrad/runtime/support/am/amdev.py +++ b/tinygrad/runtime/support/am/amdev.py @@ -1,5 +1,5 @@ from __future__ import annotations -import ctypes, collections, dataclasses, functools, os, hashlib +import ctypes, collections, dataclasses, functools, os, hashlib, array from tinygrad.helpers import mv_address, getenv, DEBUG, fetch from tinygrad.runtime.autogen.am import am from tinygrad.runtime.support.hcq import MMIOInterface @@ -168,7 +168,7 @@ class AMDev(PCIDevImplBase): # Memory manager & firmware self.mm = AMMemoryManager(self, self.vram_size, boot_size=(32 << 20), pt_t=AMPageTableEntry, va_shifts=[12, 21, 30, 39], va_bits=48, first_lv=am.AMDGPU_VM_PDB2, va_base=AMMemoryManager.va_allocator.base, - palloc_ranges=[(1 << (i + 12), 0x1000) for i in range(9 * (3 - am.AMDGPU_VM_PDB2), -1, -1)]) + palloc_ranges=[(1 << (i + 12), 0x1000) for i in range(9 * (3 - am.AMDGPU_VM_PDB2), -1, -1)], reserve_ptable=not self.large_bar) self.fw = AMFirmware(self) # Initialize IP blocks @@ -217,14 +217,25 @@ class AMDev(PCIDevImplBase): self.reg("regBIF_BX_PF0_RSMU_INDEX").write(reg) self.reg("regBIF_BX_PF0_RSMU_DATA").write(val) + def _read_vram(self, addr, size) -> bytes: + assert addr % 4 == 0 and size % 4 == 0, f"Invalid address {addr:#x} or size {size:#x}" + res = [] + for caddr in range(addr, addr + size, 4): + self.wreg(0x06, caddr >> 31) + self.wreg(0x00, (caddr & 0x7FFFFFFF) | 0x80000000) + res.append(self.rreg(0x01)) + return bytes(array.array('I', res)) + def _run_discovery(self): # NOTE: Fixed register to query memory size without known ip bases to find the discovery table. # The table is located at the end of VRAM - 64KB and is 10KB in size. mmRCC_CONFIG_MEMSIZE = 0xde3 self.vram_size = self.rreg(mmRCC_CONFIG_MEMSIZE) << 20 + self.large_bar = self.vram.nbytes >= self.vram_size tmr_offset, tmr_size = self.vram_size - (64 << 10), (10 << 10) - self.bhdr = am.struct_binary_header.from_buffer(bytearray(self.vram.view(tmr_offset, tmr_size)[:])) + disc_tbl = self.vram.view(tmr_offset, tmr_size)[:] if self.large_bar else self._read_vram(tmr_offset, tmr_size) + self.bhdr = am.struct_binary_header.from_buffer(bytearray(disc_tbl)) ihdr = am.struct_ip_discovery_header.from_address(ctypes.addressof(self.bhdr) + self.bhdr.table_list[am.IP_DISCOVERY].offset) assert self.bhdr.binary_signature == am.BINARY_SIGNATURE and ihdr.signature == am.DISCOVERY_TABLE_SIGNATURE, "discovery signatures mismatch" diff --git a/tinygrad/runtime/support/am/ip.py b/tinygrad/runtime/support/am/ip.py index 7dc47643d8..1c5c85a018 100644 --- a/tinygrad/runtime/support/am/ip.py +++ b/tinygrad/runtime/support/am/ip.py @@ -1,6 +1,6 @@ import ctypes, time, contextlib, functools from typing import Literal -from tinygrad.helpers import to_mv, data64, lo32, hi32, DEBUG, wait_cond +from tinygrad.helpers import to_mv, data64, lo32, hi32, DEBUG, wait_cond, pad_bytes from tinygrad.runtime.autogen.am import am from tinygrad.runtime.support.amd import import_soc @@ -417,7 +417,8 @@ class AM_PSP(AM_IP): def _prep_msg1(self, data:memoryview): assert len(data) <= self.msg1_view.nbytes, f"msg1 buffer is too small {len(data):#x} > {self.msg1_view.nbytes:#x}" - self.msg1_view[:len(data)+4] = bytes(data) + b'\x00' * 4 + padded_data = pad_bytes(bytes(data) + b'\x00' * 4, 16) # HACK: apple's memcpy requires 16-bytes alignment + self.msg1_view[:len(padded_data)] = padded_data self.adev.gmc.flush_hdp() def _bootloader_load_component(self, fw:int, compid:int): diff --git a/tinygrad/runtime/support/memory.py b/tinygrad/runtime/support/memory.py index 1c22c1ecd9..653a397980 100644 --- a/tinygrad/runtime/support/memory.py +++ b/tinygrad/runtime/support/memory.py @@ -28,7 +28,7 @@ class TLSFAllocator: # self.blocks is more like a linked list, where each entry is a contiguous block. self.blocks:dict[int, tuple[int, int|None, int|None, bool]] = {0: (size, None, None, True)} # size, next, prev, is_free - self._insert_block(0, size) + if size > 0: self._insert_block(0, size) @functools.cache # pylint: disable=method-cache-max-size-none def lv1(self, size): return size.bit_length() @@ -124,7 +124,7 @@ class PageTableTraverseContext: if not pt.valid(pte_idx): assert self.create_pts, "Not allowed to create new page table" - pt.set_entry(pte_idx, self.dev.mm.palloc(0x1000, zero=True, boot=self.boot), table=True, valid=True) + pt.set_entry(pte_idx, self.dev.mm.palloc(0x1000, zero=True, boot=self.boot, ptable=True), table=True, valid=True) assert not pt.is_page(pte_idx), f"Must be table pt={pt.paddr:#x}, {pt.lv=} {pte_idx=} {pt.read_fields(pte_idx)}" child_page_table = self.dev.mm.pt_t(self.dev, pt.address(pte_idx), lv=pt.lv+1) @@ -167,13 +167,14 @@ class MemoryManager: va_allocator: ClassVar[TLSFAllocator|None] = None def __init__(self, dev, vram_size:int, boot_size:int, pt_t, va_bits:int, va_shifts:list[int], va_base:int, - palloc_ranges:list[tuple[int, int]], first_lv:int=0): + palloc_ranges:list[tuple[int, int]], first_lv:int=0, reserve_ptable=False): self.dev, self.vram_size, self.va_shifts, self.va_base, lvl_msb = dev, vram_size, va_shifts, va_base, va_shifts + [va_bits + 1] self.pte_covers, self.pte_cnt = [1 << x for x in va_shifts][::-1], [1 << (lvl_msb[i+1] - lvl_msb[i]) for i in range(len(lvl_msb) - 1)][::-1] - self.pt_t, self.palloc_ranges, self.level_cnt, self.va_bits = pt_t, palloc_ranges, len(va_shifts), va_bits + self.pt_t, self.palloc_ranges, self.level_cnt, self.va_bits, self.reserve_ptable = pt_t, palloc_ranges, len(va_shifts), va_bits, reserve_ptable - self.boot_allocator = TLSFAllocator(boot_size, base=0) # per device - self.pa_allocator = TLSFAllocator(vram_size - (64 << 20), base=self.boot_allocator.size) # per device + self.boot_allocator = TLSFAllocator(boot_size, base=0) + self.ptable_allocator = TLSFAllocator(round_up(vram_size // 512, 1 << 20) if self.reserve_ptable else 0, base=self.boot_allocator.size) + self.pa_allocator = TLSFAllocator(vram_size - (64 << 20), base=self.boot_allocator.size + self.ptable_allocator.size) self.root_page_table = pt_t(self.dev, self.palloc(0x1000, zero=not self.dev.smi_dev, boot=True), lv=first_lv) def _frag_size(self, va, sz, must_cover=True): @@ -250,9 +251,10 @@ class MemoryManager: self.va_allocator.free(vm.va_addr) for paddr, _ in vm.paddrs: self.pa_allocator.free(paddr) - def palloc(self, size:int, align:int=0x1000, zero=True, boot=False) -> int: + def palloc(self, size:int, align:int=0x1000, zero=True, boot=False, ptable=False) -> int: assert self.dev.is_booting == boot, "During booting, only boot memory can be allocated" - paddr = (self.boot_allocator if boot else self.pa_allocator).alloc(round_up(size, 0x1000), align) + allocator = self.boot_allocator if boot else (self.ptable_allocator if self.reserve_ptable and ptable else self.pa_allocator) + paddr = allocator.alloc(round_up(size, 0x1000), align) if zero: self.dev.vram[paddr:paddr+size] = bytes(size) return paddr diff --git a/tinygrad/runtime/support/system.py b/tinygrad/runtime/support/system.py index df575b89fe..f431c3d793 100644 --- a/tinygrad/runtime/support/system.py +++ b/tinygrad/runtime/support/system.py @@ -1,4 +1,4 @@ -import os, mmap, array, functools, ctypes, select, contextlib, dataclasses, sys, errno +import os, mmap, array, functools, ctypes, select, contextlib, dataclasses, sys, errno, itertools from typing import cast, ClassVar from tinygrad.helpers import round_up, to_mv, getenv, OSX, temp from tinygrad.runtime.autogen import libc, vfio @@ -58,6 +58,25 @@ class _System: return vfio_fd except OSError: return None + @functools.cached_property + def iokit(self): return ctypes.CDLL(ctypes.util.find_library("IOKit")) + + @functools.cached_property + def libsys(self): return ctypes.CDLL(ctypes.util.find_library("System")) + + @functools.cached_property + def mach_task_self(self): return ctypes.cast(self.libsys.mach_task_self_, ctypes.POINTER(ctypes.c_uint)).contents.value + + @functools.cached_property + def macos_tinygpu_conn(self): + self.iokit.IOServiceNameMatching.restype = ctypes.c_void_p # CFMutableDictionaryRef + if not (mdict:=self.iokit.IOServiceNameMatching("tinygpu".encode("utf-8"))): raise RuntimeError("IOServiceNameMatching returned NULL") + if not (service:=self.iokit.IOServiceGetMatchingService(ctypes.c_uint(0), ctypes.c_void_p(mdict))): + raise RuntimeError('Service "tinygpu" is not running') + if self.iokit.IOServiceOpen(service, self.mach_task_self, ctypes.c_uint32(0), ctypes.byref(conn:=ctypes.c_uint(0))): + raise RuntimeError("IOServiceOpen failed") + return conn + def flock_acquire(self, name:str) -> int: import fcntl # to support windows @@ -123,13 +142,23 @@ class PCIDevice: libc.madvise(loc:=fd.mmap(addr, sz, mmap.PROT_READ | mmap.PROT_WRITE, mmap.MAP_SHARED | (MAP_FIXED if addr else 0), off), sz, libc.MADV_DONTFORK) return MMIOInterface(loc, sz, fmt=fmt) +class APLPCIDevice(PCIDevice): + def __init__(self, pcibus:str, bars:list[int], resize_bars:list[int]|None=None): self.pcibus, self.bars = pcibus, {b: self.map_mem(b) for b in bars} + def map_mem(self, typ:int) -> MMIOInterface: + if System.iokit.IOConnectMapMemory64(System.macos_tinygpu_conn, ctypes.c_uint32(typ), System.mach_task_self, + ctypes.byref(addr:=ctypes.c_uint64(0)), ctypes.byref(size:=ctypes.c_uint64(0)), 0x1): raise RuntimeError(f"IOConnectMapMemory64({typ=}) failed") + return MMIOInterface(addr.value, size.value) + def map_bar(self, bar:int, off:int=0, addr:int=0, size:int|None=None, fmt='B') -> MMIOInterface: return self.bars[bar].view(off, size, fmt) + def read_config(self, offset:int, size:int): return 0 + def write_config(self, offset:int, value:int, size:int): pass + class PCIDevImplBase: mm: MemoryManager @dataclasses.dataclass class PCIAllocationMeta: mapping:VirtMapping; has_cpu_mapping:bool; hMemory:int=0 # noqa: E702 -class PCIIfaceBase: +class LNXPCIIfaceBase: dev_impl:PCIDevImplBase gpus:ClassVar[list[str]] = [] @@ -166,9 +195,31 @@ class PCIIfaceBase: if b.owner is not None and b.owner._is_cpu(): System.lock_memory(cast(int, b.va_addr), b.size) paddrs, snooped, uncached = [(x, 0x1000) for x in System.system_paddrs(cast(int, b.va_addr), round_up(b.size, 0x1000))], True, True - elif (ifa:=getattr(b.owner, "iface", None)) is not None and isinstance(ifa, PCIIfaceBase): + elif (ifa:=getattr(b.owner, "iface", None)) is not None and isinstance(ifa, LNXPCIIfaceBase): paddrs = [(paddr if b.meta.mapping.system else (paddr + ifa.p2p_base_addr), size) for paddr,size in b.meta.mapping.paddrs] snooped, uncached = b.meta.mapping.snooped, b.meta.mapping.uncached else: raise RuntimeError(f"map failed: {b.owner} -> {self.dev}") self.dev_impl.mm.map_range(cast(int, b.va_addr), round_up(b.size, 0x1000), paddrs, system=True, snooped=snooped, uncached=uncached) + +class APLPCIIfaceBase(LNXPCIIfaceBase): + def __init__(self, dev, dev_id, vendor, devices, bars, vram_bar, va_start, va_size): + self.pci_dev, self.dev, self.vram_bar = APLPCIDevice(pcibus=f'usb4:{dev_id}', bars=bars), dev, vram_bar + + def alloc(self, size:int, host=False, uncached=False, cpu_access=False, contiguous=False, **kwargs) -> HCQBuffer: + if host or uncached or cpu_access: # cpu access memory goes here, since bar is small. + vaddr = self.dev_impl.mm.alloc_vaddr(size:=round_up(size, mmap.PAGESIZE), align=mmap.PAGESIZE) + assert size >= mmap.PAGESIZE, "Size must be at least one page" + + sysmem = cast(APLPCIDevice, self.pci_dev).map_mem(size).view(fmt='Q') + paddrs = list(itertools.takewhile(lambda p: p[1] != 0, zip(sysmem[0::2], sysmem[1::2]))) + + mapping = self.dev_impl.mm.map_range(vaddr, size, paddrs, system=True, snooped=True, uncached=True) + return HCQBuffer(vaddr, size, meta=PCIAllocationMeta(mapping, has_cpu_mapping=True), view=sysmem.view(fmt='B'), owner=self.dev) + + mapping = self.dev_impl.mm.valloc(size:=round_up(size, 4 << 10), uncached=uncached, contiguous=cpu_access) + return HCQBuffer(mapping.va_addr, size, view=None, meta=PCIAllocationMeta(mapping, has_cpu_mapping=False), owner=self.dev) + + def map(self, b:HCQBuffer): raise RuntimeError(f"map failed: {b.owner} -> {self.dev}") + +PCIIfaceBase:type = APLPCIIfaceBase if OSX else LNXPCIIfaceBase