your telling me it just can't be done
No. I was telling you the exact opposite. Notarization is as simple as falling off a log. I had planned to give you step-by-step instructions on how to create a demo app using the built-in Xcode templates, add your helper and run. I did that, but discovered that you do have a special case here. The xmrig executable does need special entitlements. Unfortunately, I have no idea what you are doing, so I will continue with my "sanity check" instructions. Due to the nature of the xmrig project, they are more complicated than normal.
1) Build xmrig according to official directions. Note that the official instructions will never, ever work in a real app.
2) Copy the xmrig app to working location
3) Copy the file /usr/local/opt/hwloc/lib/libhwloc.15.dylib to the same location
4) Fix the dylib to make it embeddable with the following command:
install_name_tool -id @rpath/libhwloc.15.dylib libhwloc.15.dylib
5) Fix the xmrig tool so that it will work with the dylib:
install_name_tool -change /usr/local/opt/hwloc/lib/libhwloc.15.dylib @executable_path/../Frameworks/libhwloc.15.dylib xmrig
Note that xmrig will not work at this point. It has to be properly embedded in the app before it will work.
6) Create a new macOS Swift app in Xcode from the template
7) Add the xmrig tool and the dylib to the project. Click the "copy" option.
8) Xcode will try to figure out what to do with these two files. It will guess wrong. Go into Build Phases and remove xmrig from the "Copy Bundle Resources" step. Also remove the dylib from "Link Files" step. In this simple case, I don't have any other dylibs, so I just removed the entire step. The executable can't be in the Resources folder. The dylib is for the helper executable, so it does no good to link it to the app itself.
9) Add a new Copy Files step to copy the dylib to the Frameworks Destination
10) Add another Copy Files step to copy the xmrig tool to the Wrapper Destination with the Subpath "Contents/Helpers". Use can uncheck "Code Sign On Copy" if you want because we need a custom code signing step for this file. Or you can leave it in and add "--force" to overwrite it. Doesn't matter.
11) Add a Run Script step to do the manual code signing. Use the following content:
/usr/bin/codesign --timestamp --options=runtime -s "Developer ID Application: whoeveryouare" --entitlements $SRCROOT/xmrigapp/xmrig.entitlements --force -v $TARGET_BUILD_DIR/$CONTENTS_FOLDER_PATH/Helpers/xmrig
12) The key in the above step is that entitlements file. You will need to create that. Use the following as contents:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>com.apple.security.cs.allow-unsigned-executable-memory</key>
<true/>
<key>com.apple.security.cs.disable-library-validation</key>
<true/>
</dict>
</plist>
13) You will have to create this file manually and save it as "xmrig.entitlements". My project is named "xmrigapp". You may have to adjust paths if you used something different. You can add it to your Xcode project just so it is handy. But you aren't using it directly in Xcode.
14) In your Swift source code, load and run the tool. Just print out the help text for now. Here is the source for that:
func applicationDidFinishLaunching(_ aNotification: Notification)
{
let xmrig = Process()
xmrig.executableURL =
Bundle.main.bundleURL.appendingPathComponent("Contents/Helpers/xmrig")
xmrig.arguments = ["--help"]
do
{
let outputPipe = Pipe()
let errorPipe = Pipe()
xmrig.standardOutput = outputPipe
xmrig.standardError = errorPipe
try xmrig.run()
xmrig.waitUntilExit()
let outputData = outputPipe.fileHandleForReading.readDataToEndOfFile()
let errorData = outputPipe.fileHandleForReading.readDataToEndOfFile()
let output = String(decoding: outputData, as: UTF8.self)
let error = String(decoding: errorData, as: UTF8.self)
print(output)
print(error)
print("Success!")
}
catch
{
print("xmrig failed!")
}
}
This is not production-quality code. It just a quick-n-dirty example.
15) Build and test it. Hopefully it works.
16) Archive it and distribute as Developer ID. Click the "Upload" option to Notarize.
17) Wait for the notification that the notarization was successful.
18) Export your notarized app from the archive using the Organizer.
I realize this is rather complicated. There are some important takeaways here:
1) Notarization is the easy part. Always.
2) Your app would have never worked on a different machine, even without the notarization requirement. The dylib would have always broken it. All of your problems came from that funky open-source project
3) Never use homebrew. Homebrew is fine for what it is: "home" "brewing". Never distribute code from homebrew or from anything built using homebrew. It seems to have worked in this example only because this particular project was ridiculously easy to build and hack up the linkage. Normally, such things are much more difficult. I used Homebrew in a VM to build it. It was just dumb luck that I only hack to hack up a single dylib. I have no idea if the tool will do anything more than print the help text. The Homebrew instructions had several dependences, but only one dylib seemd to be required in the end. That's suspicious.
4) All of your problems came from the xmrig tool. I have no idea what it is doing. Neither do you. This is a Red Flag. This exact tool has been used in malware distributions. It is possible that your app's notarization could be revoked at some point just because the xmrig code gets flagged as a malware component. Isn't cryptocurrency fun!
I don't think I've missed any steps. You should strongly consider a VM or a factory-fresh machine to test your built code. One you install homebrew on your development machine, you can't ever trust it to build distributable software again. All of the above could be substantially improved. It just a quick-n-dirty demonstration. Ironically enough, the only part that is easy and would exactly the same in a production-quality app is the notarization part.