1 个不稳定版本

0.1.0-alpha2019年4月1日

#410 in 配置

MIT/Apache

95KB
2.5K SLoC

Soma:您的单点CTF问题管理工具

Build Status

什么是Soma?

Soma是一款跨平台的CTF问题容器管理器。

  • Soma帮助问题作者轻松创建和分发可重复的CTF问题环境。
  • Soma帮助CTF玩家在比赛后轻松下载和运行本地机器上的CTF问题。

为问题解决者

下载和运行问题就像运行三个命令那么简单。

$ soma add https://github.com/PLUS-POSTECH/simple-bof.git
$ soma build simple-bof
$ soma run simple-bof 31337

CTF问题通常包含公共文件。您也可以使用soma轻松获取它们。

# this will copy public files to the current working directory
$ soma fetch simple-bof

为问题设置者

在项目根目录中添加描述您问题的 soma.toml 文件。以下配置文件展示了示例。

name = "simple-bof"

[binary]
os = "ubuntu:16.04"
cmd = "./simple-bof"

[[binary.executable]]
path = "build/simple-bof"
public = true

[[binary.readonly]]
path = "flag"

这就完成了!Soma 从这12行配置中获取了足够的信息来运行您的二进制文件。

Soma 将使用合理的默认值来处理其他未指定的事项,例如默认工作目录、文件权限、派生守护进程和标准流缓冲。当然,如果需要,它们也可以手动配置 :)

如果您的项目包含多个问题,您可以将 soma-list.toml 放入其中,该文件列出了每个问题目录。

problems = [
    # these subdirectories contain soma.toml files
    "problem1",
    "sub-dir/problem2"
]

依赖项

Soma 需要在系统上安装 Docker

当前状态

Soma 处于 alpha 阶段。目前,它支持在 socat 派生服务器下运行二进制文件。

我们希望为它添加更多场景,特别是使用 PHP 和 MySQL 的网页问题设置以及基于 Python 的设置。

与 0.1.0 版本相关的问题已在 0.1.0 里程碑 中标记。

路线图

  • 更好地记录功能文档。(优先级:高)
  • 支持单个问题的多个容器。(优先级:低)
  • 支持云部署,如 AWS、GCP、Azure 以及本地部署。(优先级:低)

如何使用

安装

如果您系统上安装了 Rust 工具链,请使用 cargo install soma-ctf。此命令将从 crates.io 下载最新发布的版本并构建可执行文件。

$ cargo install soma-ctf

或者,从 发布页面 下载预编译的二进制文件。

如果您想尝试最新的 master 分支,您也可以从源代码构建自己的二进制文件。具体来说,克隆此 git 仓库并运行 cargo install

$ git clone https://github.com/PLUS-POSTECH/soma.git
$ cd soma
$ cargo install

命令概述

添加/创建 删除
仓库 添加 删除
镜像 构建 清理
容器 运行 停止

此外,更新

添加仓库

Soma 仓库在其顶级目录中包含 soma.tomlsoma-list.toml,并可以包含一个或多个问题。要使用 Soma,首先添加问题仓库。我们将使用 soma-bata-list 作为本文件的示例。

您可以使用 add 子命令添加仓库

$ soma add https://github.com/PLUS-POSTECH/soma-bata-list.git

add 子命令需要一个仓库源作为参数,如上述命令中的 https://github.com/PLUS-POSTECH/soma-bata-list.git。Soma 支持以下仓库源

  • Git 仓库(目前仅支持 HTTPS 且无需身份验证)

    例如,https://github.com/PLUS-POSTECH/soma-bata-list.git

  • 本地文件系统目录

    例如,/home/linux-user/soma-repo

默认情况下,Soma 将从仓库源字符串中解析仓库名称。例如,https://github.com/PLUS-POSTECH/soma-bata-list.git 将返回 soma-bata-list,而 /home/linux-user/soma-repo 将返回 soma-repo 作为默认仓库名称。如果您想使用另一个名称,请使用 --name [NAME] 标志。此标志将使 Soma 在给定的名称下注册仓库。

另外,请注意仓库名称有一些要求。有关更多详细信息,请参阅 "名称规则" 部分。

构建问题镜像

Soma使用Docker来管理问题镜像和容器。镜像是一个问题环境的快照,容器是镜像的一个实例。为了运行问题,您首先应该构建问题镜像。

当您执行构建命令时,Soma会自动从问题清单生成Dockerfile。您可以通过执行以下命令来构建问题镜像:

$ soma build r0pbaby
# or
$ soma build soma-bata-list.r0pbaby

如您所见,有两种不同的方式选择问题。请参阅"问题查询"部分获取更多详细信息。

运行问题

当问题镜像准备就绪后,您可以使用以下命令运行问题容器!

$ soma run r0pbaby 13337
# or
$ soma run soma-bata-list.r0pbaby 13337

在这里,13337表示绑定到问题容器的端口号。这个端口号会将问题暴露给主机网络。在这个例子中,r0pbaby可以通过your.host.address:13337访问。在您的机器上尝试nc localhost 13337以开始解决问题。

目前,run命令需要端口号,但我们计划在将来支持自动端口绑定(参见#64)。

获取问题附件

CTF问题通常提供一些附件(通常是问题二进制文件)。有一个专门的子命令可以获取这些文件到当前工作目录

$ soma fetch r0pbaby
# or
$ soma fetch soma-bata-list.r0pbaby

停止问题

解决问题后,通过调用以下命令停止并删除问题容器:

$ soma stop r0pbaby
# or
$ soma stop soma-bata-list.r0pbaby

删除问题镜像

您可能出于多种原因(例如,释放磁盘空间、删除仓库)想要删除现有的问题镜像。您可以通过以下方式清理现有的镜像:

$ soma clean r0pbaby
# or
$ soma clean soma-bata-list.r0pbaby

在尝试删除镜像之前,检查是否存在任何关联的容器。如果存在从该镜像运行的容器,Soma将拒绝执行该命令。

删除仓库

如果您想删除已注册的仓库,请使用以下命令

$ soma remove soma-bata-list

使用此命令时,仓库不应有任何相关的问题镜像或容器。如果需要,请使用cleanstop命令来删除它们。为了您的方便,将来将实现自动修剪(参见#115)。

更新仓库

您可以使用update命令更新和同步仓库

$ soma update soma-bata-list

请注意,此命令不会影响已运行的问题容器。更新仓库后,您可能需要停止、构建并重新运行问题。

关于仓库和问题名的说明

问题查询

有两种方法来识别问题。您只需指定问题的名称(例如,r0pbaby)或包含其所在仓库的完整问题名称(例如,soma-bata-list.r0pbaby)。

如果问题名称是唯一的(即,问题名称只在单个仓库中使用),您可以使用前者。否则,您必须使用后者,否则Soma将给出错误信息,表示问题名称在多个仓库中找到。

命名规则

所有仓库和问题名称应遵循Docker名称组件规则,不允许使用.(例如,^[a-z0-9]+((?:_|__|[-]*)[a-z0-9]+)*$,更多详情请参阅Docker正则表达式定义)。此措施是为了防止在提供恶意输入时Soma表现不佳。我们选择Docker名称组件规则作为仓库和问题名称,因为它们是Docker镜像名称的子串。添加'不允许使用.'规则,是因为Soma使用.作为名称分隔符。

如何将Soma支持添加到您的仓库

为了支持Soma,仓库应在其顶级目录中包含soma.tomlsoma-list.tomlsoma-list.toml列出了包含soma.toml文件的每个子目录,而soma.toml是Soma问题清单文件的名称。

如果您的仓库在顶级目录中只包含一个问题,可以直接使用soma.toml而不需要soma-list.toml

soma.toml语法

仓库中的每个问题都需要一个清单文件,soma.toml,位于其目录中。问题清单文件包含Soma管理问题所需的信息。我们将通过此示例分节讨论soma.toml的语法。

name = "simple-bof"
work_dir = "/home/simple-bof"

[binary]
os = "ubuntu:16.04"
cmd = "./simple-bof"

[[binary.executable]]
path = "build/simple-bof"
public = true

[[binary.readonly]]
path = "flag"
target_path = "/you_cannot_guess_this_very_secret_flag_name"

根部分

清单根包含两个问题元数据。

name = "simple-bof"
work_dir = "/home/simple-bof"
name字段

根节点的name字段定义了问题的名称。Soma将识别此字段(而不是目录名称)作为问题名称。

work_dir字段(可选)

根节点的work_dir字段包含问题镜像内部工作目录的路径。此字段的默认值是与问题名称相同的用户的家目录(例如,上述示例中的"/home/simple-bof")。

[binary]部分

[binary]节包含使用二进制子配置所需的信息。二进制子配置支持在TCP连接上通过fork守护进程运行可执行文件并管道标准输入和输出的场景;这是CTF竞赛中最常见的设置之一。

[binary]
os = "ubuntu:16.04"
cmd = "./simple-bof"

[[binary.executable]]
path = "build/simple-bof"
public = true

[[binary.readonly]]
path = "flag"
target_path = "/you_cannot_guess_this_very_secret_flag_name"
os字段

os字段指示问题使用哪种操作系统类型。目前,该字段被重定向到Dockerfile的父镜像名称。然而,将来它将只允许预选的选择。

cmd字段

cmd字段定义了如何运行问题二进制文件。指定的二进制文件将通过socat守护进程执行。

文件条目

[[binary.executable]][[binary.readonly]]节包含子配置的文件条目。

[[binary.readwrite]][[binary.with-permissions]][[binary.fetchonly]]为未来的实现保留(见#50#84)。

path字段

path字段包含从问题目录到文件的相对路径。计划在未来支持外部源,如URL(见#114)。

target_path字段(可选)

target_path字段指定文件应在问题映像内部复制到的位置。此字段默认为根部分中的work_dir

public字段(可选)

当用户调用fetch子命令时,将public字段设置为true的文件条目将被复制到当前工作目录。此字段的默认值为false

其他子配置

计划在未来的版本中支持常见的CTF设置的其他子配置,如apache-php7python-uwsgimysql(见#50)。子配置语法设计用于支持未来的多配置问题,其处理方式类似于Docker compose

soma-list.toml语法

problems字段

soma-list.toml包含一个字段problems,它是一个指向每个问题目录的相对路径数组。

problems = [
    # these subdirectories contain soma.toml files
    "simple-bof",
    "hard/complicated-bof"
]

开发

先决条件

  • 安装Rust稳定工具链。
  • 安装openssl(由openssl-sys包要求)。
  • 安装clippyrustfmt
    • rustupcomponent add clippy rustfmt
  • hooks目录中的文件复制到.git/hooks

测试、构建和运行

Soma是用Rust编写的,并使用Cargo作为构建和测试系统。

您可以使用以下命令进行测试、构建和运行。

$ cargo test
$ cargo build
$ cargo run

许可协议

许可协议为以下之一

贡献

除非您明确表示,否则您有意提交以包含在作品中的任何贡献均应按上述方式双重许可,不附加任何额外条款或条件。

依赖关系

~29–41MB
~734K SLoC