代码检查过程中为什么需要涉及到编译呢?
本文分享自华为云社区 《代码检查过程中为什么需要涉及到编译呢?》,作者:gentle_zhou。
随着大家对软件安全越来越重视,在编码阶段针对源码安全的保障也被各行各业企业研发测试运维团队与个人开发者越来越频繁的被提及,其中静态代码检查SAST工具尤为突出。
SAST代码检查服务作为一款可以对源码进行质量(包括风格)、安全、规范等方面进行检查的工具,它可以检测出代码中存在的缺陷与风险。而随着大家对工具深入的使用,很多小伙伴在使用过程中产生了困惑,不是说好只针对源码进行检查吗?为什么还会涉及编译?为什么在我本地编译成功,放到云端环境就说编译失败了呢?
本文尝试针对上述这些问题一一进行解释,让小伙伴们了解清楚其中的过程与原理。
1、不是说好只针对源码进行检查吗?为什么还会涉及编译?
一般来说是的,SAST静态代码检查是一种静态应用程序安全测试技术,通常是在代码编译之前进行的;也就是说,SAST工具并不是强制需要执行或运行代码才可以使用,针对源码本身就可以去分析代码的语法、结构、逻辑等。
但是,这并不意味着SAST工具就与编译无关了;事实上,SAST工具在必要的时候,也需要借助编译构建工具来将代码编译之后,对生成的编译产物进行分析,可以对代码的语义和逻辑有更深入的理解和分析。
2、编译的大概过程是怎么样的?
在讲编译的过程前,让我们先了解几个专有名词。
AST,Abstract Syntax Tree 抽象语法树,是一种用来表示程序代码结构的树形数据结构,它可以反映出代码的语法和逻辑。AST可以应用在语法检查、代码风格检查、格式化代码、语法高亮、错误提示、自动补全等方面。 IR,Intermediate Representation 中间表示,是一种用来表示程序代码语义的数据结构,它可以把不同编程语言的代码转换为一种通用的形式,方便进行分析和优化。CFG,Control Flow Graph 控制流图,是一种用来表示程序代码执行流程的图形数据结构,它可以把代码分割为基本块,并用边表示基本块之间的跳转关系。
上述3个技术侧专有名词,在代码检查过程中,起到了让工具可以更好地理解和处理代码的语义和逻辑的作用,帮助提高分析的准确性。
我们言归正传,那在SAST代码检查工具的编译过程中,都会经历哪些过程呢?一般来说,完整的编译过程会经历:对源代码进行语法、词法、语义的分析,生成AST,接着转换为IR,生成CFG,对数据流进行分析、优化,生成目标代码。
因此,SAST代码检查并不是完全脱离编译,在一定程度上是需要依赖于编译构建工具来辅助深度分析的。
3、为什么在我本地编译成功,放到云端环境就编译失败了呢?
到此,相信大部分小伙伴会对在SAST工具中采用了编译操作表示理解,但是我相信在使用过程中依然会有扫描不成功的场景,其中最典型的必然就是小标题里这个问题了:为什么在我本地编译成功,放到云端环境检查期间就说编译失败了呢?
具体来看,大致有以下几种原因:
- 最常见的是,在本地环境中,项目中引用了一些存放在本地的私有依赖活配置。而在云端环境,在SAST编译过程中,找不到这些依赖或配置,编译也就失败了。
- 用户的这个工程项目本身就不是编译类项目 或则 这个项目虽然是编译类项目但在项目中没有做好正确配置。比如经常碰到的问题就是用户刚接手某个项目,得到的信息这就是个编译类项目,但其实在项目中并未含有核心配置文件,比如maven项目中缺少了核心配置文件pom.xml。
- 云端SAST工具中的检查编译参数没有选择正确。比如用户的工程是个Maven项目,但用户错误以为这是gradle项目,在云端选取了gradle作为编译工具。又比如在C#项目中,针对msbuild编译工程,.net框架选错了版本(3.5选成了4.8)。
- 用户的项目代码中有一些语法错误或类型错误(比如拼写错误、缺少分号、类型不匹配等),在本地环境中,IDE帮助自动修正或则本地编译器没有检查出来。而云端SAST工具中采用了更严格或更高级别的编译器,导致编译不通过。
- 用户的工程中有一些特殊的语言特性或语法糖,例如Lambda表达式、列表推导等,本地编译器支持这些特性;而云端SAST工具使用了不支持这些特性的编译器或较低的语言版本,导致编译不通过。
当然,不同的SAST工具会采用不同的扫描方法和技术,因此也有着不同的编译方式和对编译环境深浅不一的依赖程度。
参考资料
1、https://en.wikipedia.org/wiki/Abstract_syntax_tree
2、https://www.twilio.com/blog/abstract-syntax-trees
3、https://www.cs.princeton.edu/courses/archive/spr03/cs320/notes/IR-trans1.pdf
4、https://gcc.gnu.org/onlinedocs/gccint/Control-Flow.html#:~:text=A control flow graph (CFG) is a data,behavior of a function that is being compiled.
5、https://www.csl.cornell.edu/~zhiruz/5997/pdf/lecture04.pdf