随着信息技术的迅猛发展,传统的试卷考核学生算法编程能力的方式已经淡出人们的视野,由于数据量大、主观性强、算法思路好坏不一,这种方式显得尤为耗时且容易出错,给老师带来很大的负担。一套完整而在线评测系统必将取代传统的纸质形式的测试。本文设计并实现了基于LAMP的在线评测系统,在普通Web项目的基础上嵌入判题内核,确保提交的程序能够平稳运行。 With the rapid development of information technology, the traditional method of assessing student’s algorithmic programming ability has faded people’s horizons. This method is particularly time-consuming and error-prone because of the large amount of data, subjectivity, and mixed algorithm ideas, bringing a great burden to the teacher. A complete and online judge system will replace the traditional paper form test. This paper designs and implements an online judge system based on LAMP. It embeds the judgment kernel on the basis of common Web projects to ensure the smooth running of submitted programs.
武建,李新霞,孙琦
南京中医药大学信息技术学院,江苏 南京
收稿日期:2019年4月23日;录用日期:2019年5月1日;发布日期:2019年5月8日
随着信息技术的迅猛发展,传统的试卷考核学生算法编程能力的方式已经淡出人们的视野,由于数据量大、主观性强、算法思路好坏不一,这种方式显得尤为耗时且容易出错,给老师带来很大的负担。一套完整而在线评测系统必将取代传统的纸质形式的测试。本文设计并实现了基于LAMP的在线评测系统,在普通Web项目的基础上嵌入判题内核,确保提交的程序能够平稳运行。
关键词 :在线评测,程序设计竞赛,轮询,管道
Copyright © 2019 by author(s) and Hans Publishers Inc.
This work is licensed under the Creative Commons Attribution International License (CC BY).
http://creativecommons.org/licenses/by/4.0/
ACM国际大学生程序设计竞赛(ACM International Collegiate Programming Contest (ICPC))是由美国计算机协会(ACM)主办的一项旨在展示大学生编写程序、分析和解决问题能力的年度竞赛 [
本系统 [
为了满足程序系统的需求,进行灵活的判题分析,系统采用B/S架构。架构图如图1所示。具体分析该系统,将其设计为如下四个组成部分:
1) 网站系统(Web端):Web端与普通系统相同,解决用户管理、题库管理、提交代码和统计分析等基本功能。
2) 判题核心(Judge):和判题守护进程相互配合,一旦判题队列中出现了用户提交的代码,就对这段代码进行编译、运行,并对运行下来的结果与样式输出进行比较,将结果存入数据库。需要修建围墙来
图1. 系统架构图
保证系统的安全性,不能够接受恶意代码。
3) 封装层(Judge Wrapper):这一层是Web端与判题内核互通的一个桥梁,它负责调用Judge层来完成Web端的响应,这使得判题核心成为一个独立的功能模块。此外,可以屏蔽掉Web端带来的一些恶意代码的危害,将一些潜在的威胁在进入到核心判题层之前先打退回去,确保系统安全平稳运行。
4) 侦听守护进程(Daemon):守护程序是一个基于多线程的TCP服务,始终轮询数据库的solution表是否有新的记录出现,若有,则调用封装层,并由封装层对核心判题层进行调用。
系统将采用LAMP的模式,如图2所示,客户访问架设在Apache服务器上的Web前端,服务器会读取目录下存放的.html和.php文件,并使用PHP连接MySQL,通过标准SQL语句操作存储网站内容的数据库反馈给用户。
图2. LAMP模式原理图
整个系统划分为六个功能模块,即用户管理模块、题库管理模块、答题模块、判题模块、统计分析模块和算法教育模块。整个系统的功能结构图3所示。
图3. 功能模块图
数据库中设计了用户表、题目表、状态表、源代码表和编译表5张表,建库后数据库关系图如图4所示。
图4. 数据库关系图
判题模块由两部分组成:
judged(judge daemon):是一个守护进程,负责隔一段时间查找一下数据库中solution表是否存在新的用户提交的代码,若有,则加入判题队列。当有新的任务时开启judge client进程。judged流程图如图5所示。
Judge_client是核心的判题程序,担负着编译、运行和监测的工作,是系统的核心功能模块,也是最容易出现问题导致系统不能正常运行的一个模块。Judge_client流程图如图6所示。
用于判题守护进程中响应用户的答案提交行为,判题守护进程隔一段时间检查solution表中是否有新增数据,若有,则生成一个子进程来编译用户的代码,这些子进程形成一个任务队列,由判题内核依次执行。
图5. 判题守护进程流程图
图6. 判题内核流程图
用于进程间的通信,在指定文件夹下保存一份用户提交的代码,视情况而定调用不同编译器并利用exec族函数执行文件可以达到目的,编译时由父进程监视子进程的执行,若执行完,则在队列中执行下一个子进程。在结果对比中,判题程序每次从管道中读取一个字符,并与样式输出进行比对,直到匹配结束,一致则说明结果正确。
为了避免用户提交的恶意代码对判题机产生危害,需要从几个方面对用户代码生成程序加以限制。
1) 输入输出
由于禁止用户程序开启文件,需要通过freopen函数重定向输入输出流,主要指用户程序stdin(标准输入)、stdout(标准输出)、stderr(标准错误输出)三个流。
2) 权限
通过setuid系统调用限制用户进程的权限(设置为持有最低权限的用户ID,本系统采用了nobody这个操作系统内置的、权限最低的用户)。在资源限制方面,进程的时间、内存、栈空间和输出文件大小都需要受到限制。这些资源限制通过setrlimit和setitimer等系统调用结合来完成。
3) 运行时检测
使用ptrace函数,主要监测以下几点:① 监测程序是否安全退出。② 监测程序是否收到了如SIGALRM、SIGVTALRM、SIGXCPU、SIGXFSZ、SIGSEGV、SIGFPE、SIGBUS、SIGABRT等异常信号。③ 监测资源是否超出了最大限度。④ 监测是否合法地进行了系统的调用。若任一项出现问题,一定是因为子进程的某些错误所致,必须即刻终止子进程。
篇幅所限,这里只给出系统部分运行截图(如图7~10)。
图7. 用户登陆
图8. 题目显示
图9. 判题结果显示
图10. 统计分析
对系统功能制定了严格的测试计划,编写了完备的测试用例表对系统进行功能测试,并在测试的基础上进行修改,重新测试,最终所有功能模块均能满足期望目标。
本文设计并实现了一个基于LAMP架构的在线评测系统,提供了一个开放的自动判题的平台,通过网络技术,帮助学校更快更好地完成程序设计选拔和日常训练工作。
南京中医药大学教师教学发展专项课题(编号:nzyjsfz-201620)。
武 建,李新霞,孙 琦. 基于LAMP模式的在线评测系统的设计与实现Design and Implementation of Online Judge System Based on LAMP Mode[J]. 计算机科学与应用, 2019, 09(05): 833-840. https://doi.org/10.12677/CSA.2019.95093