Skip to content

Commit 113e329

Browse files
authored
Handle .bundle in .deb (#84)
Handle .bundle in .deb
1 parent add1a09 commit 113e329

File tree

2 files changed

+78
-25
lines changed

2 files changed

+78
-25
lines changed

CHANGELOG.md

Lines changed: 1 addition & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1 @@
1-
- 修复 ZIP 归档中位于子目录的 dylib 文件无法正确导入的问题。
2-
- 新增 “所有应用” 分类。
3-
- 新增免责声明。
4-
- 新增中文名称 “巨魔注入器”。
5-
6-
------
7-
8-
- Fixed an issue where dylib files located in subdirectories in ZIP archives could not be imported correctly.
9-
- Added “All Applications” category.
10-
- Added disclaimer.
1+
- Inject `.bundle` additionally if `.deb` file contains both `.dylib` and `.bundle`

TrollFools/InjectorV3+Preprocess.swift

Lines changed: 77 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -141,28 +141,90 @@ fileprivate extension InjectorV3 {
141141

142142
var hasAnyDylib = false
143143
var tarReader = TarReader(fileHandle: tarHandle)
144+
var processedBundles = Set<String>()
145+
var bundleContents: [String: [(info: TarEntryInfo, data: Data?)]] = [:]
144146
while let entry = try tarReader.read() {
145-
guard entry.info.type == .regular,
146-
entry.info.name.hasSuffix(".dylib"),
147-
let entryData = entry.data
148-
else {
149-
continue
150-
}
151-
152-
let dylibName = URL(fileURLWithPath: entry.info.name, relativeTo: targetURL).lastPathComponent
153-
guard !dylibName.hasPrefix(".") else {
154-
continue
155-
}
147+
if entry.info.type == .regular && entry.info.name.hasSuffix(".dylib") {
148+
guard let entryData = entry.data else {
149+
continue
150+
}
151+
let dylibName = URL(fileURLWithPath: entry.info.name, relativeTo: targetURL).lastPathComponent
152+
guard !dylibName.hasPrefix(".") else {
153+
continue
154+
}
156155

157-
DDLogWarn("Found dylib \(entry.info.name) name \(dylibName)", ddlog: logger)
156+
DDLogWarn("Found dylib \(entry.info.name) name \(dylibName)", ddlog: logger)
157+
158+
let entryURL = targetURL.appendingPathComponent(dylibName)
159+
try entryData.write(to: entryURL)
160+
hasAnyDylib = true
161+
} else if entry.info.type == .directory && entry.info.name.hasSuffix(".bundle") {
162+
// Extract bundle name
163+
let bundleName = URL(fileURLWithPath: entry.info.name).lastPathComponent
164+
// Avoid processing duplicate or nested bundles
165+
guard !processedBundles.contains(bundleName) else {
166+
continue
167+
}
168+
// Track that we're processing this bundle
169+
processedBundles.insert(bundleName)
170+
// Store bundle entries for later processing
171+
bundleContents[entry.info.name] = []
158172

159-
let entryURL = targetURL.appendingPathComponent(dylibName)
160-
try entryData.write(to: entryURL)
161-
hasAnyDylib = true
173+
DDLogWarn("Found bundle \(entry.info.name) name \(bundleName)", ddlog: logger)
174+
} else {
175+
// Collect contents for all bundles
176+
for (bundlePath, _) in bundleContents {
177+
if entry.info.name.starts(with: bundlePath + "/") {
178+
bundleContents[bundlePath]?.append((entry.info, entry.data))
179+
}
180+
}
181+
}
162182
}
163183

164184
if !hasAnyDylib {
165185
throw Error.generic(NSLocalizedString("No dylib found in the Debian package.", comment: ""))
166186
}
187+
let fileManager = FileManager.default
188+
// Process collected bundle contents
189+
for (bundlePath, contents) in bundleContents {
190+
let bundleName = URL(fileURLWithPath: bundlePath).lastPathComponent
191+
192+
DDLogInfo("Preparing to copy bundle \(bundlePath)", ddlog: logger)
193+
194+
// Destination for the bundle
195+
let destinationBundleURL = targetURL.appendingPathComponent(bundleName)
196+
// Remove existing bundle if it exists
197+
if fileManager.fileExists(atPath: destinationBundleURL.path) {
198+
try fileManager.removeItem(at: destinationBundleURL)
199+
}
200+
// Create destination directory for the bundle
201+
try fileManager.createDirectory(at: destinationBundleURL, withIntermediateDirectories: true)
202+
203+
// Copy bundle contents
204+
for entry in contents {
205+
// Get relative path within the bundle
206+
let relativePath = String(entry.info.name.dropFirst(bundlePath.count + 1))
207+
let destinationPath = destinationBundleURL.appendingPathComponent(relativePath)
208+
// Handle different entry types
209+
switch entry.info.type {
210+
case .directory:
211+
// Create subdirectories
212+
try fileManager.createDirectory(at: destinationPath, withIntermediateDirectories: true)
213+
case .regular:
214+
// Ensure destination directory exists
215+
try fileManager.createDirectory(at: destinationPath.deletingLastPathComponent(), withIntermediateDirectories: true)
216+
// Write file contents
217+
guard let fileData = entry.data else {
218+
DDLogWarn("Unable to read data for \(entry.info.name)", ddlog: logger)
219+
continue
220+
}
221+
try fileData.write(to: destinationPath)
222+
default:
223+
continue
224+
}
225+
}
226+
227+
DDLogInfo("Successfully copied bundle \(bundleName)", ddlog: logger)
228+
}
167229
}
168230
}

0 commit comments

Comments
 (0)