OpenJML入门
OpenJML 获取
下载
OpenJML下载可以通过其github仓库获取。传送门
使用
下载完成后,可以直接使用命令行进行操作,但是比较麻烦。这里提供两个版本的辅助文件简化操作
Linux
# filename : openjml
#!/bin/bash
java -jar path/to/openjml.jar "$@"
其中jar包的路径需要自行修改。
Windows
::openjml.bat
@echo off
set java=java -jar "%~dp0openjml.jar" -noPurityCheck
set prove=-prover cvc4 -exec "%~dp0Solvers-windows\cvc4-1.6.exe"
set runtime=-cp %~dp0jmlruntime.jar;
set allparam=
set rac=
:param
set str=%1
if "%str%"=="" (
goto end
)
if "%str%"=="-rac" (
set rac=rac
)
if "%str%"=="-prove" (
set str=%prove%
)
set allparam=%allparam% %str%
shift /0
goto param
:end
if "%allparam%"=="" (
goto eof
)
rem remove left right blank
:intercept_left
if "%allparam:~0,1%"==" " set "allparam=%allparam:~1%"&goto intercept_left
:intercept_right
if "%allparam:~-1%"==" " set "allparam=%allparam:~0,-1%"&goto intercept_right
:eof
%java% %allparam%
set filename=
if "%rac%"=="rac" (
:input
set /p filename=Input file name:
if "%filename%"=="" (
goto input
)
java %runtime% %filename%
)
pause
用户可以将上述代码拷贝到解压后的文件夹中,然后将该文件夹加入环境变量。即可通过命令行调用openjml命令了。这里为了简化验证时的参数传递,提供了一个-prove参数。用户指定这一参数后,程序将选定prover并执行。
Parsing and Type-checking
OpenJML最基本的功能就是对JML注释的完整性进行检查。检查包括经典的类型检查、变量可见性与可写性等。通过命令行使用OpenJML时,可以通过-check参数(缺省)指定类型检查。
openjml [-check] options files
举例来说
public class main {
/*@
@ require args != null
@*/
public static void main(String[] args) {
System.out.println(args);
}
}
运行语法检查后报错
C:\>openjml main.java
main.java:17: 错误: 需要';'
@ require args != null
^
main.java:17: 错误: 找不到符号
@ require args != null
^
符号: 类 require
位置: 类 main
2 个错误
类型检查检测出了注释中的两处错误。分别更改后的程序如下
public class main {
/*@
@ requires args != null;
@*/
public static void main(String[] args) {
System.out.println(args);
}
}
再次运行后即可通过检查。
Extended Static Checking
类型检查只能确保jml注释的格式正确,但是对规格内容不进行检查。下述程序中明显违背了规格的描述,但是类型检查仍然通过了。
public class main {
/*@
@ requires a != 0 && b != 0;
@ ensures \result <= 1 && \result >= 0;
@*/
public static int fun(int a, int b) {
return a > b ? 1 : 0;
}
public static void main(String[] args) {
fun(1, 0);
}
}
为了对规格内容进行检查,需要使用-esc参数
C:\>openjml -esc -prove main.java
main.java:10: 警告: The prover cannot establish an assertion (Precondition: main.java:6: 注: ) in method main
fun(1, 0);
^
main.java:6: 警告: Associated declaration: main.java:10: 注:
public static int fun(int a, int b) {
^
main.java:3: 警告: Precondition conjunct is false: b != 0
@ requires a != 0 && b != 0;
^
3 个警告
这里需要注意,静态检查需要指定prover。在上述Windows版的批处理函数中,默认指定了一个prover。用户也可以使用-prover等参数指定自定义检查器。
那么esc是如何完成的呢?好奇的话可以通过-progress参数或-verboseness参数来查看检查的具体过程。下面截取了部分输出
C:\>openjml -esc -prove main.java -verboseness=3
...
STARTING PROOF OF main.main(java.lang.String[])
/*@
public behavior
requires args != null;
signals_only java.lang.RuntimeException;
assignable \everything;
accessible \everything;
*/
{
fun(1, 0);
}
...
可以看出OpenJML在验证前会首先重整规格,而后针对性生成测试程序。由于生成程序过长,可以在本地尝试。此处使用的是-verboseness=3,如果使用 4 将会输出大量信息。
Runtime Assertion Checking
使用-rac选项可以执行运行时检查。上述批处理文件中存在 bug,第一次输入文件名时可能会要求再次输入。
C:\>openjml -rac main.java
Input file name:main
main.java:10: 警告: JML precondition is false
fun(1, 0);
^
main.java:6: 警告: Associated declaration: main.java:10: 注:
public static int fun(int a, int b) {
^
这时会自动运行生成出来的.class文件,但经过反汇编后我的.class文件并不能编译。因此目前还没有看懂rac的具体流程。此外,-rac选项有许多补充选项,功能十分丰富,大家可以多多尝试。
参考
OpenJML 基本使用 伦泽标
OpenJML入门的更多相关文章
- BUAA OO 2019 第三单元作业总结
目录 总 JML规格化设计 理论基础 工具链 规格验证 验证代码 代码静态检查 自动生成测试样例 生成结果 错误分析 作业设计 第九次作业 架构 代码实现 第十次作业 架构 代码实现 第十一次作业 架 ...
- Angular2入门系列教程7-HTTP(一)-使用Angular2自带的http进行网络请求
上一篇:Angular2入门系列教程6-路由(二)-使用多层级路由并在在路由中传递复杂参数 感觉这篇不是很好写,因为涉及到网络请求,如果采用真实的网络请求,这个例子大家拿到手估计还要自己写一个web ...
- ABP入门系列(1)——学习Abp框架之实操演练
作为.Net工地搬砖长工一名,一直致力于挖坑(Bug)填坑(Debug),但技术却不见长进.也曾热情于新技术的学习,憧憬过成为技术大拿.从前端到后端,从bootstrap到javascript,从py ...
- Oracle分析函数入门
一.Oracle分析函数入门 分析函数是什么?分析函数是Oracle专门用于解决复杂报表统计需求的功能强大的函数,它可以在数据中进行分组然后计算基于组的某种统计值,并且每一组的每一行都可以返回一个统计 ...
- Angular2入门系列教程6-路由(二)-使用多层级路由并在在路由中传递复杂参数
上一篇:Angular2入门系列教程5-路由(一)-使用简单的路由并在在路由中传递参数 之前介绍了简单的路由以及传参,这篇文章我们将要学习复杂一些的路由以及传递其他附加参数.一个好的路由系统可以使我们 ...
- Angular2入门系列教程5-路由(一)-使用简单的路由并在在路由中传递参数
上一篇:Angular2入门系列教程-服务 上一篇文章我们将Angular2的数据服务分离出来,学习了Angular2的依赖注入,这篇文章我们将要学习Angualr2的路由 为了编写样式方便,我们这篇 ...
- Angular2入门系列教程4-服务
上一篇文章 Angular2入门系列教程-多个组件,主从关系 在编程中,我们通常会将数据提供单独分离出来,以免在编写程序的过程中反复复制粘贴数据请求的代码 Angular2中提供了依赖注入的概念,使得 ...
- wepack+sass+vue 入门教程(三)
十一.安装sass文件转换为css需要的相关依赖包 npm install --save-dev sass-loader style-loader css-loader loader的作用是辅助web ...
- wepack+sass+vue 入门教程(二)
六.新建webpack配置文件 webpack.config.js 文件整体框架内容如下,后续会详细说明每个配置项的配置 webpack.config.js直接放在项目demo目录下 module.e ...
随机推荐
- IOC注解详解
@Component 修改一个类,将这个类交给Spring管理 相当于在配置文件当中配置<bean id="" class=""> @Compone ...
- 转:sql 经典50题--可能是你见过的最全解析
题记:从知乎上看到的一篇文章,刚好最近工作中发现遇到的题目与这个几乎一样,可能就是从这里来的吧.^_^ 里面的答案没有细看,SQL求解重在思路,很多时候同一种结果可能有多种写法,比如题中的各科成绩取前 ...
- EMQ 与 mqtt 与 IOT设备
1.IOT设备的特性 IOT(物联网things of internet)设备和传统的智能设备有什么区别,笔者总结下的IOT设备有如下特点: 硬件能力差(存储能力基本只有几MB,CPU频率低连使用HT ...
- 工具系列 | VScode VS Live Share 实时编码分享(和你的小伙伴一起写代码吧)
Visual Studio Live Share能干啥? 分享任何语言,任何应用程序 无论您正在构建什么类型的应用程序,您正在编写什么语言,或者您的操作系统如何:在您需要协作时,Live Share会 ...
- 如何下载官网最新版 win10 系统?
如何下载官网最新版 win10 系统?步骤: 一. 下载 遨游浏览器 将UA切换成,手机访问:推荐 UC浏览器,UA设置: Mozilla/5.0 (Linux; U; Android 8.0.0; ...
- 取未清PO逻辑
注意这里的 GR qty [ WEMNG] 和 Open Quantity [OBMNG] *&---------------------------------------------- ...
- [LeetCode] 261. Graph Valid Tree 图是否是树
Given n nodes labeled from 0 to n - 1 and a list of undirected edges (each edge is a pair of nodes), ...
- UE4 window打包ios备忘
1.生成SHH key 2.安装证书 *.cer,*.p12 以下转自:http://wangjie.rocks/2017/11/30/ue4-ios-build-on-windows/ 问题一 12 ...
- mysql查询之分数排名
编写一个 SQL 查询来实现分数排名.如果两个分数相同,则两个分数排名(Rank)相同 +----+-------+ | Id | Score | +----+-------+ | 1 | 3.50 ...
- WPF外包团队:2019 WPF数据监控系统案例演示
项目版权均为客户所有,如有WPF项目外包欢迎联系我们. QQ:372900288 TEL:13911652504 WX:Liuxiang0884