sqlite阅读笔记(一)安装和源码概述
前言
总归要阅读代码,学习前人的智慧才能真的掌握知识,才能真的学会知识。
下载源码
sqlite使用fossil管理源码,我们首先要安装fossil。
brew install fossil
然后创建sqlite目录,用fossil下载源码
mkdir ~/sqlite
cd ~/sqlite
fossil clone https://www.sqlite.org/src sqlite.fossil
fossil open sqlite.fossil --force 不知道为什么提示我目录存在,无法创建。
fossil update trunk ;# latest trunk check-in 更新到主干代码
fossil update release ;# latest official release 更新到最新release版本
fossil ui # 通过浏览器查看代码
编译
mkdir bld ;# Build will occur in a sibling directory 在同级目录创建一个build目录
cd bld ;# Change to the build directory
../sqlite/configure ;# Run the configure script
make ;# Run the makefile.
make sqlite3.c ;# Build the "amalgamation" source file
make test ;# Run some tests (requires Tcl)
最后一步,运行测试用例失败了(感觉和我的tcl版本有关系),剩下都成功了。总之开始看代码吧。
源文件概览
大部分源码都在src目录下面。
shell.c是sqlite3命令行程序的实现。
ext/ 目录下面包含了扩展的代码,例如全文搜索引擎ext/fts3。R-Tree引擎ext/rtree。
ext/misc 下面包含了单个文件的扩展程序,例如REGEXP正则匹配操作。
tool/ 目录包含了各种脚本程序,用来生成源码文件或者生成测试程序。
parse.c
sql语言的parser由parse.c实现。它是由src/parse.y(用lemon的LALR(1)文法书写)文件生成的。lemon文法的源码在tool/lemon.c中。lemon使用tool/lempar.c文件作为模版来生成parser。lemon也生成了parse.h头文件。
opcodes.h
opcodes.h头文件包含了VDBE虚拟机的opcode的宏定义。opcodes.h是通过扫描src/vdbe.c文件,通过./mkopcodeh.tcl脚本生成的。另一个脚本./mkopcodec.tcl通过opcodes.h生成opcodes.c文件。opcodes.c文件包含了opcode-number和opcode-name的映射关系,用于explan命令。
keywordhash.h
keywordhash.h头文件包含了sql语言关键字(create,select,index等等)的hash映射。keywordhash.h文件是由mkkeywordhash.c工具生成的。
pragma.h
pragma预编译指令。pragma.h文件包含了PRAGMA指令声明的定义和实现。这个文件是tool/mkpragmatab.tcl脚本生成的。
sqlite3.c
所有c文件和头文件可以聚合成一个大的源文件sqlite3.c。这个大文件是通过tool/mksqlite3c.tcl脚本生成的。生成的前提是tsrc子目录下面的文件都编译存在。这个大文件有20万行,通过大文件编译出来的程序要比单个文件快5%左右。
sqlite3.h
sqlite3.h头文件包含了所有sqlite定义的接口和对象。这个文件是src/sqlite.h.in,./manifest.uuid和./VERSION三个文件生成的。生成的脚本是tool/mksqlite3h.tcl。
其他核心文件
sqlite.h.in
sqlite对外api,是sqlite3.h的源文件。
sqliteInt.h
sqlite内部使用的数据结构定义头文件。
vdbe.c
这个文件实现了虚拟机功能。
where.c
这个文件(以及其他以where*.c)用于分析where语句,生成虚拟机器码
btree.c
这个文件包含了存储引擎的b树实现。对外接口是btree.h。另外btreeInt.h定义了btree.c内部使用的对象。
pager.c
和pager.h功能使用。实现了事务。
os_unix.c和os_win.c
这两个文件实现了不同操作系统平台的VFS(虚拟文件系统)接口。
ext/misc/json1.c
这个文件实现了sqlite的json函数。
后续todo
从sqlite的功能看,有四个方面是需要额外学习才能了解核心功能。
- tcl脚本
- lemon和编译原理
- vdbe和虚拟机
- sqlite3的使用
总结
- 虽然sqlite3代码并不多,但是里面五脏俱全(parser,虚拟机,存储引擎,事务引擎,代码生成,模块化的设计思想,用c实现的面向对象等),应有尽有。
- 官网说到manifest文件应该是自解释的,深表认同。
[me]:很多时候我们的代码也应该是自解释的,但是不知道为什么我总看莫名其妙的操作,意义不明的变量和业务无法直接关联的代码。