Showing Posts From
Dfu
nRF芯片设备DFU升级(适配Xcode10.2.1)
这里主要参考这个项目:iOS-nRF-Toolbox,它是Nordic公司开发的测试工程,包含一整套nRF设备的测试解决方案。项目是用Swift写的,不过之前还是有OC版本的,但是后来由于一些**(不可描述的问题),才变成了现在的纯Swift版本。对于使用Swift开发的人员,直接仿照Demo操作即可。如果你是用Swift开发的,那下面的内容你可以不用看了。接下来我就讲一下针对OC引用DFU升级的操作步骤和我遇到的问题。 代码研究 nRF-Toolbox项目包含BGM,HRM,HTM,DFU等多个模块,我们今天只关注其中的DFU升级模块。打开项目,在对应的NORDFUViewController.swift中我们能够看到有三个引用库 import UIKit,import CoreBluetooth,import iOSDFULibrary,这里的iOSDFULibrary就是DFU升级的库,也是解决DFU升级最重要的组件。我们只要把这个库集成到我们的项目中,就能够完成nRF设备的DFU升级了。 集成步骤 有两种方案集成:通过cocoapods集成 编译出framework然后把库导入项目第一种方案是作者推荐的,但是我试了很久,引入DFULibrary会出现头文件找不到等一系列问题,无奈只能放弃,如果有人通过这种方式成功,还望告知。下面讲的是通过第二种方案的集成。 第一步:导出iOSDFULibrary 这一步是最关键也是最容易出问题的,这个库也是由Swift写成的,我们将这个库clone到本地,然后选择iOSDFULibrary进行编译最后生成两个framework:iOSDFULibrary.framework Zip.framework这时库内的代码已经变成了我们熟悉的OC语言。理论上这个库应该是没问题的了,但是事实还是有问题的,见issues#39。作者给出的解决方法是:1、On your mac please install carthage (instructions) 2、Create a file named cartfile anywhere on your computer 3、add the following content to the file:github "NordicSemiconductor/IOS-Pods-DFU-Library" ~> 2.1.2 github "marmelroy/Zip" ~> 0.61、Open a new terminal and cd to the directory where the file is 2、Enter the command carthage update --platform iOS 3、Carthage will now take care of building your frameworks, the produced .framework files will be found in a newly created directory called Carthage/Build/iOS,copy over iOSDFULibrary.framework and Zip.framework to your project and you are good to go.carthage是一种和cocoapods相似的的类库管理工具,如果不会使用的话可以参照Demo,将framework文件导入到自己的项目。 第二步、导入framework Target->General直接拖入项目默认只会导入到Linked Frameworks and Libraries,我们还需要在Embeded Binaries中引入。 第三步、使用iOSDFULibrary //create a DFUFirmware object using a NSURL to a Distribution Packer(ZIP) DFUFirmware *selectedFirmware = [[DFUFirmware alloc] initWithUrlToZipFile:url];// or //Use the DFUServiceInitializer to initialize the DFU process. DFUServiceInitiator *initiator = [[DFUServiceInitiator alloc] initWithCentralManager: centralManager target:selectedPeripheral]; [initiator withFirmware:selectedFirmware]; // Optional: // initiator.forceDfu = YES/NO; // default NO // initiator.packetReceiptNotificationParameter = N; // default is 12 initiator.logger = self; // - to get log info initiator.delegate = self; // - to be informed about current state and errors initiator.progressDelegate = self; // - to show progress bar // initiator.peripheralSelector = ... // the default selector is usedDFUServiceController *controller = [initiator start];库中有三个代理方法DFUProgressDelegate,DFUServiceDelegate,LoggerDelegate,它们的作用分别为监视DFU升级进度,DFU升级及蓝牙连接状态,打印状态日志。 常见问题 1、selectedFirmware返回nil DFUFirmware *selectedFirmware = [[DFUFirmware alloc] initWithUrlToZipFile:url];需要在General的Embeded Binaries选项卡里导入那Zip.framework和iOSDFULibrary.framework 2、崩溃报错 dyld: Library not loaded: @rpath/libswiftCore.dylibReferenced from: /private/var/containers/Bundle/Application/02516D79-BB30-4278-81B8-3F86BF2AE2A7/XingtelBLE.app/Frameworks/iOSDFULibrary.framework/iOSDFULibraryReason: image not found需要改两个地方如果不起作用,将Runpath Search Paths的选项内容删掉再重新添加一遍即可 3、打包上架时报ERROR IT MS-90087等问题 问题描述: ERROR ITMS-90087: "Unsupported Architectures. The executable for ***.app/Frameworks/SDK.framework contains unsupported architectures '[x86_64, i386]'." ERROR ITMS-90362: "Invalid Info.plist value. The value for the key 'MinimumOSVersion' in bundle ***.app/Frameworks/SDK.framework is invalid. The minimum value is 8.0" ERROR ITMS-90209: "Invalid Segment Alignment. The app binary at '***.app/Frameworks/SDK.framework/SDK' does not have proper segment alignment. Try rebuilding the app with the latest Xcode version." ERROR ITMS-90125: "The binary is invalid. The encryption info in the LC_ENCRYPTION_INFO load command is either missing or invalid, or the binary is already encrypted. This binary does not seem to have been built with Apple's linker."解决方法,添加Run Script PhaseShell脚本内容填写如下内容,再次编译即可 APP_PATH="${TARGET_BUILD_DIR}/${WRAPPER_NAME}"# This script loops through the frameworks embedded in the application and # removes unused architectures. find "$APP_PATH" -name '*.framework' -type d | while read -r FRAMEWORK do FRAMEWORK_EXECUTABLE_NAME=$(defaults read "$FRAMEWORK/Info.plist" CFBundleExecutable) FRAMEWORK_EXECUTABLE_PATH="$FRAMEWORK/$FRAMEWORK_EXECUTABLE_NAME" echo "Executable is $FRAMEWORK_EXECUTABLE_PATH"EXTRACTED_ARCHS=()for ARCH in $ARCHS do echo "Extracting $ARCH from $FRAMEWORK_EXECUTABLE_NAME" lipo -extract "$ARCH" "$FRAMEWORK_EXECUTABLE_PATH" -o "$FRAMEWORK_EXECUTABLE_PATH-$ARCH" EXTRACTED_ARCHS+=("$FRAMEWORK_EXECUTABLE_PATH-$ARCH") doneecho "Merging extracted architectures: ${ARCHS}" lipo -o "$FRAMEWORK_EXECUTABLE_PATH-merged" -create "${EXTRACTED_ARCHS[@]}" rm "${EXTRACTED_ARCHS[@]}"echo "Replacing original executable with thinned version" rm "$FRAMEWORK_EXECUTABLE_PATH" mv "$FRAMEWORK_EXECUTABLE_PATH-merged" "$FRAMEWORK_EXECUTABLE_PATH"done完整OC项目 这个是对应Swift版本用OC写的完整项目,应该是OC停止维护之前的版本。会有一些bug。在将DFUFramework更新之后,我把它搬到了我的github上,有需要的同学可以下载研究:OC-nRFTool-box。以下为更新内容,时间:2017.12.26 收到很多关于无法适配Xcode9.2的反馈,因为最近比较忙没时间处理,不好意思啦,今天抽出时间来把代码更新了一下。 Xcode9.2 出现的问题1、dyld: Library not loaded: @rpath/libswiftCore.dylib Referenced from: /private/var/containers/Bundle/Application/02516D79-BB30-4278-81B8-3F86BF2AE2A7/XingtelBLE.app/Frameworks/iOSDFULibrary.framework/iOSDFULibrary Reason: image not found 2、DFUFirmware *selectedFirmware = [[DFUFirmware alloc] initWithUrlToZipFile:url]; 返回为空或者崩溃问题我的测试结果是更新iOSDFULibrary. framework和Zip.framework可以解决以上问题。 解决方案 Carthage 因为这两个库都是通过Swift维护的,所以更新framework最好还是要用适用Swift的方式,包括以后的更新也一样。所以我推荐用Carthage更新这俩库,下面是使用Carthage的简单介绍,详细的可以看这里Carthage的安装和使用。 另外OC-nRFTool-box也已经更新,里面的Framework可以直接拿来用。 1、安装brew /usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"2、brew更新 $ brew update3、安装Carthage $ brew install carthage4、使用Carthage $ cd ~/路径/项目文件夹 /**进入项目文件夹下*/ $ touch Cartfile /**创建carthage文件*/ $ open Cartfile /**打开carthage文件*/ # /**输入以下内容*/ $ github "NordicSemiconductor/IOS-Pods-DFU-Library" ~> 4.1 $ github "marmelroy/Zip" ~> 1.15、运行Carthage $ carthage update --platform iOS /**编译出iOS版本*/6、更新framework $ cd Carthage/Build/iOS /**framework输出位置,将老的framework替换掉*/注意 nRF Toolbox项目方法变更 [initiator withFirmwareFile:selectedFirmware];/** 旧版本方法 */ initiator = [initiator withFirmware:selectedFirmware];/** 新版本方法 */更新:2019-7-14 针对之前常出的这种问题: dyld: Library not loaded: @rpath/libswiftCore.dylib Referenced from: /private/var/containers/Bundle/Application/CDB2F4ED-C49C-4303-BE1F-5D9D990380F3/nRF Toolbox.app/Frameworks/Zip.framework/Zip Reason: image not found均是由Swift库版本不一致引起的,iOSDFULibrary目前已经支持到Swift 5,所以我们应该升级一下版本。为了方便使用,我将Carthage集成到了项目里,如果以后需要再升级,更新Cartfile文件里的版本号,执行更新命令: $ carthage update --platform iOS如果你想要将DFU的framework集成到你自己的项目里,可以在Carthage/Build/iOS/中找到iOSDFULibrary.framework, ZIPFoundation.framework 将其拖到项目中即可。 上线注意事项(由@jianxiong1997提供)需要删除ZIPFoundation.framework中的libswiftRemoteMirror.dylib Frameworksgithub项目同步更新。