iOS开发 - OCLint自定义规则的编译与Xcode调试

OCLint的编译

基于版本 oclint version 0.15

OCLint 需要自定义规则的话需要自己编译,如果是简单的使用,参考 OCLint的使用

Github下拉代码:
git clone https://github.com/oclint/oclint

README.md
oclint-core
oclint-driver
oclint-metrics
oclint-reporters
oclint-rules
oclint-scripts

编译过程比较长,需要 富墙 才会快一点

过程中提示错误,这里需要提前安装 cmake 以及 Ninja

  • 安装 cmake
  1. 官网下载CMake,传送门:https://cmake.org/download/

  2. 命令行输入 sudo "/Applications/CMake.app/Contents/bin/cmake-gui" --install

  3. 修改 ~/.bash_profile 文件

export CMAKE_ROOT=/Applications/CMake.app/Contents/bin/
 
export PATH=$CMAKE_ROOT:$PATH
  1. 终端运行source ~/.bash_profile使修改生效
  • 安装 Ninjia

ninja需要依赖于re2c,否则编译是会报错,re2c是一款语法分析器

  1. 安装re2c

http://re2c.org/index.html 下载 re2c

下载 re2c-1.3.tar 解压,然后

cd re2c-1.3
./configure
make 
make install
  1. 安装ninjia
git clone git://github.com/ninja-build/ninja.git && cd ninja
./configure.py --bootstrap
 
//mac 10.14以上版本权限可能不够
cp ninja /usr/bin/

或者拷贝至 /Applications/CMake.app/Contents/bin/
  • 编译OCLint

然后进入oclint-scripts,执行./make

sheng@chengpengdeMacBook-Pro oclint-scripts % ./make
Cloning into 'oclint-json-compilation-database'...
remote: Enumerating objects: 88, done.
remote: Total 88 (delta 0), reused 0 (delta 0), pack-reused 88
Unpacking objects: 100% (88/88), done.
Cloning into 'oclint-xcodebuild'...
remote: Enumerating objects: 85, done.
remote: Total 85 (delta 0), reused 0 (delta 0), pack-reused 85
Unpacking objects: 100% (85/85), done.
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
100   657  100   657    0     0    503      0  0:00:01  0:00:01 --:--:--   503
100  424M  100  424M    0     0  4238k      0  0:01:42  0:01:42 --:--:-- 4720k

...
...
-- The C compiler identification is Clang 10.0.0
-- The CXX compiler identification is Clang 10.0.0
-- Detecting C compiler ABI info
-- Detecting C compiler ABI info - done
-- Check for working C compiler: /Volumes/CaiCai/OCLint/oclint/build/llvm-install/bin/clang - skipped
-- Detecting C compile features
-- Detecting C compile features - done
-- Detecting CXX compiler ABI info
-- Detecting CXX compiler ABI info - done
-- Check for working CXX compiler: /Volumes/CaiCai/OCLint/oclint/build/llvm-install/bin/clang++ - skipped
-- Detecting CXX compile features
-- Detecting CXX compile features - done
LLVM_ROOT: /Volumes/CaiCai/OCLint/oclint/build/llvm-install
-- Found LLVM LLVM_PACKAGE_VERSION: 10.0.0 - LLVM_VERSION_RELEASE: 10.0.0
-- Using LLVMConfig.cmake in: /Volumes/CaiCai/OCLint/oclint/build/llvm-install/lib/cmake/llvm
-- Configuring done
-- Generating done
-- Build files have been written to: /Volumes/CaiCai/OCLint/oclint/build/oclint-driver
[14/14] Linking CXX executable bin/oclint-0.15

到这里OCLint算编译成功了,但是还无法使用,参考官方文档 installation 部分说明,我们采用直接添加进PATH方式

修改 ~/.bash_profile 文件 ,加入以下内容

OCLINT_HOME=/Users/sheng/Documents/Caicai/OCLint/oclint/build/oclint-release
export PATH=$OCLINT_HOME/bin:$PATH

然后 source ~/.bash_profile 使得修改生效

命令行输入 oclint 进行验证

sheng@chengpengdeMacBook-Pro ~ % oclint
LLVM ERROR: CommonOptionsParser: failed to parse command-line arguments. [CommonOptionsParser]: oclint: Not enough positional command line arguments specified!
Must specify at least 1 positional argument: See: oclint --help

这样就算成功了

自定义规则

rule 添加

OCLint 提供了一个脚本程序,位于 oclint-scripts/scaffoldRule

通过他传入要生成的规则名,级别,类型,脚本就会在目录oclint-rules/rules/custom/自动帮我们生成一个模板代码,并且加入编译路径中。举个例子:

//生成一个名为 CCRuleTest ,类型为 ASTVisitor 的规则模板
oclint-scripts/scaffoldRule CCRuleTest -t ASTVisitor

你可以查看 scaffoldRule文件了解更多可配置的参数

arg_parser = argparse.ArgumentParser()
arg_parser.add_argument("class_name", help="class name of the rule")
arg_parser.add_argument("-t", "--type", dest='rule_type', choices=['Generic', 'SourceCodeReader', 'ASTVisitor', 'ASTMatcher'], default="Generic")
arg_parser.add_argument("-c", "--category", dest='rule_category', default="custom")
arg_parser.add_argument("-n", "--name", dest='rule_name', default="")
arg_parser.add_argument("-p", "--priority", type=int, dest='rule_priority', choices=[1, 2, 3], default=3)
arg_parser.add_argument(      "--test",    dest='generate_tests', action='store_true',  help="Generate a test for the new rule (default)")
arg_parser.add_argument(      "--no-test", dest='generate_tests', action='store_false', help="Do not generate a test for the new rule")
arg_parser.set_defaults(generate_tests=True)
args = arg_parser.parse_args()

这样就会在 oclint/oclint-rules/rules/custom 路劲下生成对应的文件

在这里插入图片描述

cpp文件是逻辑实现,txt文件是规则匹配

Xcode工程创建

我们通过生成xcode工程来直观的管理各个规则,包括我们新建的ruleOCLint工程使用CMakeLists的方式维护各个文件的依赖关系,我们可以使用CMake自带的功能将这些CMakeLists生成一个xcodeproj工程文件

  • OCLint源码目录下建立一个文件夹,命名为oclint-xcoderules

在这里插入图片描述

并创建一个脚本 ./create-xcode-rules.sh ,键入内容如下:

#! /bin/sh -e

cmake -G Xcode -D CMAKE_CXX_COMPILER=../build/llvm-install/bin/clang++  -D CMAKE_C_COMPILER=../build/llvm-install/bin/clang -D OCLINT_BUILD_DIR=../build/oclint-core -D OCLINT_SOURCE_DIR=../oclint-core -D OCLINT_METRICS_SOURCE_DIR=../oclint-metrics -D OCLINT_METRICS_BUILD_DIR=../build/oclint-metrics -D LLVM_ROOT=../build/llvm-install/ ../oclint-rules

然后 sh create-xcode-rules.sh 运行脚本,就生成了我们的xcode工程 OCLINT_RULES

打开工程我们可以发现创建的rule在里面

在这里插入图片描述

如果使用brew安装,这个路径应该是 /usr/local/Cellar/oclint/0.15/lib/oclint/rules

编译会生成对应的dylib库,那我们之后如何更新 OCLint 的规则呢

更新dylib

oclint/build/oclint-release 是最终编辑结果,当我们添加了自定义规则后,自然要将自定义规则添加到oclint-release 中,我们进入 oclint/build/oclint-release/lib/oclint/rules ,可以看到所有的规则dylib都放在这里,我们将编译后的dylib放进来,就可以了

在这里插入图片描述
这样命令行调用 oclint 命令就会应用该rule,但是问题来了,我们如何调试呢,能够在Xcode里面进行调试最好,不然每次编译,然后查看结果,要崩溃了。

Xcode调试

cd 进入 oclint-driver 目录下,参考之前的方式,创建 Xcode工程

  1. 创建 create-xcode-driver.sh
  2. 脚本内容如下
#! /bin/sh -e

cmake -G Xcode \
    -D CMAKE_CXX_COMPILER=../build/llvm-install/bin/clang++  \
    -D CMAKE_C_COMPILER=../build/llvm-install/bin/clang \
    -D OCLINT_BUILD_DIR=../build/oclint-core \
    -D OCLINT_SOURCE_DIR=../oclint-core \
    -D OCLINT_METRICS_SOURCE_DIR=../oclint-metrics \
    -D OCLINT_METRICS_BUILD_DIR=../build/oclint-metrics \
    -D LLVM_ROOT=../build/llvm-install/ ../oclint-driver

你可以每个文件夹生成Xcode工程,修改最后一个参数
这里对 oclint-driver 生成Xcode工程

  1. 执行脚本 sh create-xcode-driver.sh,生成 Xcode工程

  2. 打开 Schemes 面板,配置 启动参数

-R=/Users/sheng/Documents/Caicai/OCLint/oclint/oclint-xcoderules/rules.dl/Debug -report-type html -o /Users/sheng/Documents/Caicai/OCLint/oclint/output/reporter.html /Users/sheng/Documents/Caicai/OCLint/oclint/demo/test.m -- -x objective-c -isystem /Users/sheng/Documents/Caicai/OCLint/oclint/build/oclint-release/lib/clang/10.0.0/include -iframework /Applications/Xcode.app/Contents/Developer/Platforms/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator.sdk/System/Library/Frameworks -isystem /Applications/Xcode.app/Contents/Developer/Platforms/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator.sdk/usr/include

-R 表示设置rule的路径,我们设置为rule工程的编译debug路径
-report-type html -o html文件报告输出路径
test.m 我们写一个本地变量未使用的rule检测

int main(void) {
    int i=9;
    return 0;
}


见下图:
在这里插入图片描述

  • 拷贝reporters文件

设置运行后,终端打印错误

oclint: error: cannot find dynamic library for report type: html
Program ended with exit code: 2

搜索错误 cannot find dynamic library 断点查看 reportDirPath 值为

/Users/sheng/Documents/Caicai/OCLint/oclint/oclint-driver/bin/Debug/../lib/oclint/reporters

因为我们改了bin的路径,它根据 bin路径/../lib/oclint/reporters 来查找 reporters ,这里直接将 oclint-release 下的 reporters 连父目录一起拷贝,构成这个路径


  • 创建reporter.html

再次运行提示错误

oclint: error: cannot open report output file /Users/sheng/Documents/Caicai/OCLint/oclint/output/reporter.html
Program ended with exit code: 4

这里是创建的 output 文件夹路径写错了,放置到上面所说的正确位置后运行正常

运行正常后,查看 reporter.html

在这里插入图片描述

然后进行断点 UnusedLocalVariableRule.cpp 来进行调试

在这里插入图片描述

成功断点,之后你就可以自行编写 rule,并进行调试了

参考文章: https://www.jianshu.com/p/84fa7b8fd8fe

©️2020 CSDN 皮肤主题: 技术黑板 设计师: CSDN官方博客 返回首页
实付0元
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。

余额充值