oj-docs/judger/api.md
2024-04-04 22:17:34 +08:00

5.0 KiB

Judger for OnlineJudge

build

sudo apt-get install libseccomp-dev
mkdir build && cd build && cmake .. && make && sudo make install

libjudger.so is built in both executable and library format.

Command Line

./libjudger.so --help shows the usage

C API

#include <runner.h> then call run function with struct config and struct result pointer.

struct config members

  • max_cpu_time (ms): max cpu time this process can cost, -1 for unlimited
  • max_real_time (ms): max time this process can run, -1 for unlimited
  • max_memory (byte): max size of the process' virtual memory (address space), -1 for unlimited
  • max_stack (byte): max size of the process' stack size
  • max_process_number: max number of processes that can be created for the real user id of the calling process, -1 for unlimited
  • max_output_size (byte): max size of data this process can output to stdout, stderr and file, -1 for unlimited
  • memory_limit_check_only: if this value equals 0, we will only check memory usage number, because setrlimit(maxrss) will cause some crash issues
  • exe_path: path of file to run
  • input_file: redirect content of this file to process's stdin
  • output_file: redirect process's stdout to this file
  • error_file: redirect process's stderr to this file
  • args (string array terminated by NULL): arguments to run this process
  • env (string array terminated by NULL): environment variables this process can get
  • log_path: judger log path
  • seccomp_rule_name(string or NULL): seccomp rules used to limit process system calls. Name is used to call corresponding functions.
  • uid: user to run this process
  • gid: user group this process belongs to

struct result members

  • cpu_time: cpu time the process has used
  • real_time: actual running time of the process
  • memory: max vaule of memory used by the process
  • signal: signal number
  • exit_code: process's exit code
  • result: judger result, details in runner.h
  • error: args validation error or judger internal error, error code in runner.h

result return value

  • WRONG_ANSWER (judger module will never return this value, it's used for awswer checker)
  • SUCCESS = 0 (this only means the process exited normally)
  • CPU_TIME_LIMIT_EXCEEDED = 1
  • REAL_TIME_LIMIT_EXCEEDED = 2
  • MEMORY_LIMIT_EXCEEDED = 3
  • RUNTIME_ERROR = 4
  • SYSTEM_ERROR = 5

error return value

  • SUCCESS = 0
  • INVALID_CONFIG = -1
  • FORK_FAILED = -2
  • PTHREAD_FAILED = -3
  • WAIT_FAILED = -4
  • ROOT_REQUIRED = -5
  • LOAD_SECCOMP_FAILED = -6
  • SETRLIMIT_FAILED = -7
  • DUP2_FAILED = -8
  • SETUID_FAILED = -9
  • EXECVE_FAILED = -10
  • SPJ_ERROR = -11 (judger module will never return this value, it's used for awswer checker)

Python binding (Python 2.7 and 3.5+)

sudo python setup.py install

Python demo

Args with string must be Python str type

>>> import _judger
>>> _judger.VERSION

[2, 0, 1]

>>> _judger.run(max_cpu_time=1000,
...             max_real_time=2000,
...             max_memory=128 * 1024 * 1024,
...             max_process_number=200,
...             max_output_size=10000,
...             max_stack=32 * 1024 * 1024,
...             # five args above can be _judger.UNLIMITED
...             exe_path="/bin/echo",
...             input_path="/dev/null",
...             output_path="echo.out",
...             error_path="echo.out",
...             # can be empty list
...             args=["HelloWorld"],
...             # can be empty list
...             env=["foo=bar"],
...             log_path="judger.log",
...             # can be None
...             seccomp_rule_name="c_cpp",
...             uid=0,
...             gid=0)

{'cpu_time': 0, 'signal': 0, 'memory': 4554752, 'exit_code': 0, 'result': 0, 'error': 0, 'real_time': 2}

There are six constants in the module you can use

  • RESULT_SUCCESS
  • RESULT_CPU_TIME_LIMIT_EXCEEDED
  • RESULT_REAL_TIME_LIMIT_EXCEEDED
  • RESULT_MEMORY_LIMIT_EXCEEDED
  • RESULT_RUNTIME_ERROR
  • RESULT_SYSTEM_ERROR

Run tests

cd tests &&  sudo python test.py

Note

  • Linux x64 and kernel version > 3.17 required
  • Judger security relies on Docker with default security config More
  • Tested under Ubuntu docker container. System calls may vary due to different system and kernel versions
  • Root user required to change uid / gid
  • Why use seccomp instead of ptrace? Ptrace can decrease process's performance significantly, for each system call, twice context switch between child process and parent process is needed.
  • How to custom seccomp rule? Example here.

Known issues

  • Parent process' memory usage will affect child process' memory usage data ref1 ref2

License

The Star And Thank Author License (SATA)