【问题标题】:How to import a private framework in Xcode 8.3 without getting "Undefined symbols for architecture arm64"如何在 Xcode 8.3 中导入私有框架而不获取“架构 arm64 的未定义符号”
【发布时间】:2017-10-13 05:18:54
【问题描述】:

我正在尝试使用 _CDBatterySaver 来打开低功耗模式,只需使用

    [[_CDBatterySaver batterySaver] setMode:1];

我知道没有与以前的 Xcode 相同类型的目录,因此这些方法不起作用。

我也尝试过只导入“.h”文件,但这不起作用。

它是 CoreDuet 框架的一部分(从 GitHub 下载)

谢谢

【问题讨论】:

    标签: ios xcode jailbreak iphone-privateapi


    【解决方案1】:

    您需要一个.tbd 文件来链接。

    Apple 停止为从 iOS 9.3 SDK 开始的私有框架提供这些,但您可以自己生成它们,但需要付出一些努力:

    1. 获取一些最新 iOS 版本的 IPSW(ipsw.methe iPhone wiki 有很好的列表)。
    2. 解压 IPSW 并挂载根文件系统(.dmg,即多 GB)。
    3. /System/Library/Caches/com.apple.dyld/dyld_shared_cache_arm* 中查找适合您架构的共享库缓存。
    4. 使用one of various tools(我更喜欢jtool),从中提取CoreDuet,例如:

      jtool -e CoreDuet /path/to/dyld_shared_cache
      
    5. 可选:对多个架构执行第 4 步,然后将提取的文件组合成一个胖二进制文件:

      lipo -output CoreDuet dyld_shared_cache_*.CoreDuet
      
    6. 使用machotbd 或我自己的工具tbdumpnotes,从您刚刚提取的库/框架中创建一个.tbd 文件,例如:

      tbdump CoreDuet > CoreDuet.tbd
      

      notes 1. 我写的,所以我显然是附属的。
      2.它是一个测试版,目前对符号有点过分热情,甚至打印
      它不应该的那些 - 但到目前为止它对我来说一直很好。

    7. 像这样创建一个文件夹结构:

      some_path/
          CoreDuet.framework/
              CoreDuet.tbd
      
    8. 在 XCode 中将 CoreDuet.framework 添加到您的框架中,或者使用这些编译器标志:

      -Fsome_path -framework CoreDuet
      
    9. 利润。

    另外,如果步骤 1-6 对您来说太麻烦并且您只需要 _CDBatterySaver 符号,那么您可以将它用于您的 CoreDuet.tbd 并完成它:

    ---
    archs:           [ armv7, armv7s, arm64 ]
    platform:        ios
    install-name:    /System/Library/PrivateFrameworks/CoreDuet.framework/CoreDuet
    exports:
      - archs:           [ armv7, armv7s, arm64 ]
        objc-classes:    [ __CDBatterySaver ]
    ...
    

    【讨论】:

    • 按照 AvatarKit 和 tbdump 的这些说明,我得到“文件不包含任何 LC_VERSION_MIN_* 加载命令”。有什么想法吗?
    【解决方案2】:

    基于Siguza的回答

    较新版本的Xcode 使用tbd v2 格式。这是一个.tbd 存根文件,它将使用最新版本的 Xcode 进行编译。

    --- !tapi-tbd-v2
    archs:           [ armv7, armv7s, arm64 ]
    uuids:           [ 'armv7: CBD84526-2D11-4CF3-83A7-4408DA532D3E', 'armv7s: 37ACF720-FA66-4B2D-8411-09D0B607E1A0',
                       'arm64: 19F91B79-9FA2-4944-9E68-3E632C938AE3' ]
    platform:        ios
    install-name:    /System/Library/PrivateFrameworks/CoreDuet.framework/CoreDuet
    objc-constraint: none
    exports:
      - archs:           [ armv7, armv7s, arm64 ]
        objc-classes:    [ __CDBatterySaver ]
        objc-ivars:      [ __CDBatterySaver._connection ]
    ...
    

    【讨论】:

      【解决方案3】:

      现在有一个官方工具可以生成.tbd 文件,tapi(基于文本的 API)。不确定它的确切发布时间,但它至少与 Xcode 9 一样长。

      要为二进制文件生成.tbd,请执行以下操作。在这里,我在 OSX 上使用私有的 SafariShared.framework。如果您需要 iOS 框架的 .tbd,则必须按照 Siguza 的答案开头获取二进制文件,否则,此过程的其余部分将起作用。

      1. 为名为“SafariShared.framework”的框架存根创建一个空目录:

        $ md SafariShared.framework
        
      2. 运行如下命令生成存根:

        $ xcrun tapi stubify -o SafariShared.framework/SafariShared.tbd /System/Library/PrivateFrameworks/SafariShared.framework/SafariShared
        

        -o 参数是输出文件,最后一个参数是二进制文件的路径(注意它不是.framework 本身的路径;你会得到一个错误如果你这样做)。根据需要替换两者。

      3. 有一个潜在的陷阱。存根文件可以包含允许与该二进制文件链接的程序列表,如果您的程序未列在该列表中,则链接器将失败。在您喜欢的文本编辑器中打开 .tbd 并查找如下行:

        allowable-clients: [ <a bunch of bundle IDs>, ... ]
        

        删除所有这些(可能没有)并保存文件。

      现在你可以开始了!您在步骤 1 中创建的存根 .framework 目录将像 Xcode 中的真实框架一样工作。在您的 Xcode 项目的常规设置中,您可以单击“Linked Frameworks and Libraries”中的加号并添加存根目录。

      (您可能还必须将包含存根 .framework 的目录添加到“框架搜索路径”项目设置中。这是否会自动发生似乎很不稳定。)

      【讨论】:

      • 我上次尝试时,tapi 对从 dyld_shared_cache 提取的库不起作用 - 是否改变了?
      猜你喜欢
      • 1970-01-01
      • 2019-05-20
      • 2021-01-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-01-22
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多