Skip to content

Commit ce11235

Browse files
authored
Merge pull request #1 from sedwards-ibowl/master
Merge in recent changes to supporter newer macOS versions
2 parents 9a50b88 + 26dcff1 commit ce11235

11 files changed

Lines changed: 367 additions & 8 deletions

File tree

.github/workflows/build.yml

Lines changed: 13 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,17 @@ jobs:
44
build:
55
runs-on: macos-latest
66
steps:
7-
- uses: actions/checkout@v2
8-
# https://github.com/mxcl/xcodebuild
9-
- uses: mxcl/xcodebuild@v1
7+
- uses: actions/checkout@v4
108
with:
11-
platform: macOS
12-
working-directory: MacDependency
13-
action: build # default = `test`
9+
submodules: true
10+
11+
- name: Build MacDependency
12+
run: |
13+
cd MacDependency
14+
xcodebuild -project MacDependency.xcodeproj \
15+
-scheme MacDependency \
16+
-configuration Release \
17+
CODE_SIGN_IDENTITY="-" \
18+
AD_HOC_CODE_SIGNING_ALLOWED=YES \
19+
ONLY_ACTIVE_ARCH=YES \
20+
build

.gitignore

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,34 @@ xcuserdata/
2020

2121
# End of https://www.toptal.com/developers/gitignore/api/xcode
2222

23+
# Build artifacts
2324
build/
2425
build.xcresult/
26+
DerivedData/
27+
*.app
28+
*.dmg
29+
*.dSYM
30+
31+
# macOS
2532
.DS_Store
33+
.AppleDouble
34+
.LSOverride
35+
36+
# Thumbnails
37+
._*
38+
39+
# Files that might appear in the root of a volume
40+
.DocumentRevisions-V100
41+
.fseventsd
42+
.Spotlight-V100
43+
.TemporaryItems
44+
.Trashes
45+
.VolumeIcon.icns
46+
.com.apple.timemachine.donotpresent
47+
48+
# Directories potentially created on remote AFP share
49+
.AppleDB
50+
.AppleDesktop
51+
Network Trash Folder
52+
Temporary Items
53+
.apdisk

MacDependency/AppDelegate.h

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
//
2+
// AppDelegate.h
3+
// MacDependency
4+
//
5+
// Application delegate to handle auto-opening MacDependency binary
6+
// and command-line argument processing.
7+
//
8+
9+
#import <Cocoa/Cocoa.h>
10+
11+
@interface AppDelegate : NSObject <NSApplicationDelegate>
12+
13+
@end

MacDependency/AppDelegate.m

Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
//
2+
// AppDelegate.m
3+
// MacDependency
4+
//
5+
// Application delegate to handle auto-opening MacDependency binary
6+
// and command-line argument processing.
7+
//
8+
9+
#import "AppDelegate.h"
10+
11+
@implementation AppDelegate
12+
13+
- (void)applicationDidFinishLaunching:(NSNotification *)notification {
14+
// Get command line arguments from NSProcessInfo
15+
NSArray<NSString *> *arguments = [[NSProcessInfo processInfo] arguments];
16+
17+
// arguments[0] is the executable path, so check if there are additional args
18+
if (arguments.count > 1) {
19+
// User provided file path(s) as arguments
20+
[self openFilesFromCommandLine:arguments];
21+
} else {
22+
// No arguments - auto-open MacDependency binary itself
23+
[self openDefaultFile];
24+
}
25+
}
26+
27+
- (void)openFilesFromCommandLine:(NSArray<NSString *> *)arguments {
28+
// Skip first argument (executable path)
29+
for (NSInteger i = 1; i < arguments.count; i++) {
30+
NSString *filePath = arguments[i];
31+
32+
// Convert to absolute path if needed
33+
if (![filePath isAbsolutePath]) {
34+
NSString *currentDir = [[NSFileManager defaultManager] currentDirectoryPath];
35+
filePath = [currentDir stringByAppendingPathComponent:filePath];
36+
}
37+
38+
NSURL *fileURL = [NSURL fileURLWithPath:filePath];
39+
40+
// Use NSDocumentController to open the document
41+
[[NSDocumentController sharedDocumentController]
42+
openDocumentWithContentsOfURL:fileURL
43+
display:YES
44+
completionHandler:^(NSDocument *document, BOOL wasAlreadyOpen, NSError *error) {
45+
if (error) {
46+
NSLog(@"Error opening file %@: %@", filePath, error.localizedDescription);
47+
// Show error dialog to user
48+
[[NSAlert alertWithError:error] runModal];
49+
}
50+
}];
51+
}
52+
}
53+
54+
- (void)openDefaultFile {
55+
// Get path to the MacDependency executable inside Contents/MacOS/
56+
NSString *executablePath = [[NSBundle mainBundle] executablePath];
57+
58+
NSURL *fileURL = [NSURL fileURLWithPath:executablePath];
59+
60+
// Open the executable using NSDocumentController
61+
[[NSDocumentController sharedDocumentController]
62+
openDocumentWithContentsOfURL:fileURL
63+
display:YES
64+
completionHandler:^(NSDocument *document, BOOL wasAlreadyOpen, NSError *error) {
65+
if (error) {
66+
NSLog(@"Error opening default file: %@", error.localizedDescription);
67+
// Don't show error dialog here - user didn't explicitly request this
68+
}
69+
}];
70+
}
71+
72+
// Don't interfere with normal document opening via Finder
73+
- (BOOL)application:(NSApplication *)sender openFile:(NSString *)filename {
74+
// Return NO to let NSDocumentController handle it normally
75+
return NO;
76+
}
77+
78+
@end

MacDependency/Base.lproj/MainMenu.xib

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,11 @@
66
<plugIn identifier="com.apple.InterfaceBuilder.CocoaPlugin" version="11542"/>
77
</dependencies>
88
<objects>
9-
<customObject id="-2" userLabel="File's Owner" customClass="NSApplication"/>
9+
<customObject id="-2" userLabel="File's Owner" customClass="NSApplication">
10+
<connections>
11+
<outlet property="delegate" destination="9F0" id="9F1"/>
12+
</connections>
13+
</customObject>
1014
<customObject id="-1" userLabel="First Responder" customClass="FirstResponder"/>
1115
<customObject id="-3" userLabel="Application" customClass="NSObject"/>
1216
<menu title="AMainMenu" systemMenu="main" id="29" userLabel="MainMenu">
@@ -145,5 +149,6 @@
145149
</items>
146150
</menu>
147151
<customObject id="419" customClass="NSFontManager"/>
152+
<customObject id="9F0" customClass="AppDelegate"/>
148153
</objects>
149154
</document>

MacDependency/Info.plist

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,5 +43,9 @@
4343
<string>MainMenu</string>
4444
<key>NSPrincipalClass</key>
4545
<string>NSApplication</string>
46+
<key>NSAppleEventsUsageDescription</key>
47+
<string>MacDependency needs to access system files to analyze Mach-O binaries and their dependencies.</string>
48+
<key>NSSystemAdministrationUsageDescription</key>
49+
<string>MacDependency requires access to system libraries and frameworks to display dependency information.</string>
4650
</dict>
4751
</plist>
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
3+
<plist version="1.0">
4+
<dict>
5+
<key>com.apple.security.cs.allow-unsigned-executable-memory</key>
6+
<true/>
7+
<key>com.apple.security.cs.disable-library-validation</key>
8+
<true/>
9+
<key>com.apple.security.automation.apple-events</key>
10+
<true/>
11+
<key>com.apple.security.files.user-selected.read-only</key>
12+
<true/>
13+
<key>com.apple.security.files.user-selected.read-write</key>
14+
<true/>
15+
</dict>
16+
</plist>

MacDependency/MacDependency.xcodeproj/project.pbxproj

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@
3030
8ED4567B10516D6200FAC99F /* MyDocumentWindow.m in Sources */ = {isa = PBXBuildFile; fileRef = 8ED4567A10516D6200FAC99F /* MyDocumentWindow.m */; };
3131
8EFDEF7A101007B300E4D54D /* ConversionStdString.mm in Sources */ = {isa = PBXBuildFile; fileRef = 8EFDEF79101007B300E4D54D /* ConversionStdString.mm */; };
3232
8EFDEF9310100F1700E4D54D /* VersionFormatter.m in Sources */ = {isa = PBXBuildFile; fileRef = 8EFDEF9210100F1700E4D54D /* VersionFormatter.m */; };
33+
9F00000320241201DEADBEEF /* AppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = 9F00000220241201DEADBEEF /* AppDelegate.m */; };
3334
/* End PBXBuildFile section */
3435

3536
/* Begin PBXContainerItemProxy section */
@@ -101,6 +102,9 @@
101102
8EFDEF79101007B300E4D54D /* ConversionStdString.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = ConversionStdString.mm; sourceTree = "<group>"; wrapsLines = 0; };
102103
8EFDEF9110100F1700E4D54D /* VersionFormatter.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = VersionFormatter.h; sourceTree = "<group>"; wrapsLines = 0; };
103104
8EFDEF9210100F1700E4D54D /* VersionFormatter.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = VersionFormatter.m; sourceTree = "<group>"; wrapsLines = 0; };
105+
9F00000120241201DEADBEEF /* AppDelegate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AppDelegate.h; sourceTree = "<group>"; };
106+
9F00000220241201DEADBEEF /* AppDelegate.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AppDelegate.m; sourceTree = "<group>"; };
107+
9F00000420241202DEADBEEF /* MacDependency.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = MacDependency.entitlements; sourceTree = "<group>"; };
104108
ADCDF191276D87BD002476ED /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = Base; path = Base.lproj/MainMenu.xib; sourceTree = "<group>"; };
105109
ADCDF192276D87BD002476ED /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = Base; path = Base.lproj/MyDocument.xib; sourceTree = "<group>"; };
106110
ADCDF194276D87BF002476ED /* en */ = {isa = PBXFileReference; lastKnownFileType = text.rtf; name = en; path = en.lproj/Credits.rtf; sourceTree = "<group>"; };
@@ -163,6 +167,8 @@
163167
2A37F4ABFDCFA73011CA2CEA /* Classes */ = {
164168
isa = PBXGroup;
165169
children = (
170+
9F00000120241201DEADBEEF /* AppDelegate.h */,
171+
9F00000220241201DEADBEEF /* AppDelegate.m */,
166172
8ECFE3441061192D00685EDF /* PrioritySplitViewDelegate.h */,
167173
8ECFE3451061192D00685EDF /* PrioritySplitViewDelegate.m */,
168174
8EC4F15E10400F02001F9FB8 /* ArchitecturesController.h */,
@@ -212,6 +218,7 @@
212218
8E131503100F7C3C00367510 /* MainMenu.xib */,
213219
8E131505100F7C3C00367510 /* MyDocument.xib */,
214220
8E1314FD100F7C1D00367510 /* Info.plist */,
221+
9F00000420241202DEADBEEF /* MacDependency.entitlements */,
215222
8E1315C3100F8F1400367510 /* Localizable.strings */,
216223
);
217224
name = Resources;
@@ -327,6 +334,7 @@
327334
isa = PBXSourcesBuildPhase;
328335
buildActionMask = 2147483647;
329336
files = (
337+
9F00000320241201DEADBEEF /* AppDelegate.m in Sources */,
330338
8ED32F48100B68FF00EBF623 /* MachOModel.mm in Sources */,
331339
8ED330CE100BD19800EBF623 /* SymbolTableEntryModel.mm in Sources */,
332340
8E1314FA100F7BFC00367510 /* MyDocument.mm in Sources */,
@@ -403,6 +411,7 @@
403411
buildSettings = {
404412
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
405413
CLANG_ENABLE_OBJC_ARC = YES;
414+
CODE_SIGN_ENTITLEMENTS = MacDependency.entitlements;
406415
CODE_SIGN_IDENTITY = "Apple Development";
407416
CODE_SIGN_STYLE = Automatic;
408417
COPY_PHASE_STRIP = NO;
@@ -426,6 +435,7 @@
426435
buildSettings = {
427436
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
428437
CLANG_ENABLE_OBJC_ARC = YES;
438+
CODE_SIGN_ENTITLEMENTS = MacDependency.entitlements;
429439
CODE_SIGN_IDENTITY = "Apple Development";
430440
CODE_SIGN_STYLE = Automatic;
431441
DEAD_CODE_STRIPPING = YES;

MacDependency/README.md

Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,3 +6,82 @@ MacDependency shows all dependent libraries and frameworks of a given executable
66
More information available in the [Wiki](../../wiki).
77

88
![Screenshot](images/macdependency.png)
9+
10+
## Features
11+
12+
- **Auto-open Example**: When launched without arguments, MacDependency automatically opens and displays its own binary as a working example
13+
- **Command-Line Support**: Open files directly from the command line
14+
- **Multiple Architectures**: View dependencies for different CPU architectures (x86_64, ARM64, etc.)
15+
- **Symbol Table Viewer**: Browse symbol tables and exported functions
16+
- **Dependency Tree**: Hierarchical view of all library dependencies
17+
18+
## Usage
19+
20+
### GUI Usage
21+
22+
Simply double-click `MacDependency.app` or drag a file onto the application icon to analyze it.
23+
24+
When launched without any file, MacDependency will automatically open itself as an example, showing you how the application works.
25+
26+
### Command-Line Usage
27+
28+
You can also launch MacDependency from the command line to analyze specific files:
29+
30+
```bash
31+
# Open a single application
32+
MacDependency.app/Contents/MacOS/MacDependency /Applications/Safari.app
33+
34+
# Open a binary directly
35+
MacDependency.app/Contents/MacOS/MacDependency /bin/ls
36+
37+
# Open multiple files (each opens in a separate window)
38+
MacDependency.app/Contents/MacOS/MacDependency /bin/ls /bin/cat /usr/bin/tar
39+
40+
# Use relative paths
41+
cd /Applications
42+
MacDependency.app/Contents/MacOS/MacDependency Safari.app
43+
```
44+
45+
## Building
46+
47+
### Requirements
48+
- macOS with Xcode installed
49+
- Command line tools for Xcode
50+
51+
### Build Instructions
52+
53+
To build MacDependency from source:
54+
55+
```bash
56+
cd MacDependency
57+
xcodebuild -project MacDependency.xcodeproj -scheme MacDependency -configuration Release \
58+
CODE_SIGN_IDENTITY="-" AD_HOC_CODE_SIGNING_ALLOWED=YES clean build
59+
```
60+
61+
The built application will be located at:
62+
```
63+
~/Library/Developer/Xcode/DerivedData/MacDependency-*/Build/Products/Release/MacDependency.app
64+
```
65+
66+
**Note**: The build command includes ad-hoc code signing which is required for the app to run on modern macOS versions. After building, you may need to sign the embedded framework:
67+
68+
```bash
69+
codesign -f -s - ~/Library/Developer/Xcode/DerivedData/MacDependency-*/Build/Products/Release/MacDependency.app/Contents/Frameworks/MachO.framework
70+
codesign -f -s - ~/Library/Developer/Xcode/DerivedData/MacDependency-*/Build/Products/Release/MacDependency.app
71+
```
72+
73+
### Alternative Build Method
74+
75+
You can also open the project in Xcode and build from the IDE:
76+
77+
1. Open `MacDependency/MacDependency.xcodeproj` in Xcode
78+
2. Select the MacDependency scheme
79+
3. Choose Product > Build (⌘B)
80+
81+
### Creating a DMG
82+
83+
After building, you can create a DMG installer using the included script:
84+
85+
```bash
86+
./create_dmg_for_app.sh
87+
```

0 commit comments

Comments
 (0)