news 2026/9/25 17:31:29

Seastar 高性能服务器框架实战指南:从编译构建、构建模式到异步编程工程接入

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
Seastar 高性能服务器框架实战指南:从编译构建、构建模式到异步编程工程接入
  • 后端
  • 异步编程
  • 网络

【免费下载链接】seastar

High performance server-side application framework

项目地址:https://gitcode.com/gh_mirrors/se/seastar
点击查看免费下载

Seastar 是一个基于事件驱动与 future 编程模型的高性能服务器端 C++ 框架,支持 C++23/C++26,采用共享无内存(share-nothing)的多核架构,为网络与存储 I/O 提供零拷贝能力。本文以仓库根目录 README.md 为主线,系统讲解 Seastar 的编译构建流程、四种构建模式、pkg-config/CMake 两种消费方式、C++ 标准选择以及第一个 Hello World 应用的编写与运行,并结合 HACKING.md、configure.py、demos/hello-world.cc 等仓库源码给出可复现的实战方案。

Seastar 是什么

Seastar 是一个事件驱动框架(event-driven framework),它允许开发者以相对直接的方式(一旦理解之后)编写非阻塞、异步的 C++ 代码。其 API 全部基于future(未来值)与continuation(延续回调)模型,这一点在 README.md 与 doc/mini-tutorial.md 中都有明确说明。

Seastar 的设计初衷是同时解决传统服务器编程中的两大矛盾:既要效率(如 DPDK 只能处理简单的逐包应用),又要复杂度(如允许构建庞大复杂的应用)。它的第一个实践用例是 Scylla——一个用 Seastar 重写的 Apache Cassandra,在吞吐量上获得了数量级的提升,同时显著降低了延迟抖动。

四大核心设计支柱

Seastar 依赖以下四个概念来达到极致性能:

  1. 协作式微任务调度器(Cooperative micro-task scheduler):每个 CPU 核运行一个协作式任务调度器,而不是传统线程。每个任务非常轻量,只执行处理上一次 I/O 结果并提交下一次 I/O 所需的时间,杜绝了上下文切换开销。
  2. 共享无多核架构(Share-nothing SMP architecture):每个核独立运行,内存、数据结构和 CPU 时间均不共享,核间通信通过显式消息传递完成。一个 Seastar 核通常称为一个 shard。
  3. 基于 future 的 API:通过 future 提交 I/O 操作并链式调度后续任务,可以轻松并行执行多个 I/O 操作,例如在一个 TCP 请求的响应路径中同时发起多个磁盘 I/O、向其他核发送消息、聚合结果后再返回响应。
  4. 共享无 TCP 协议栈与 DMA 存储 API:Seastar 自带高性能用户态 TCP/IP 协议栈,双向零拷贝;存储 API 同样支持零拷贝 DMA 传输。

这四个概念的具体展开可见 doc/tutorial.md 的 Introduction 章节,源码层面则散落在 src/core/reactor.cc、src/core/smp.cc 等核心实现中。

编译构建 Seastar

Seastar 的构建流程以configure.py(CMake 包装脚本)配合 Ninja 构建系统为核心,详见 README.md。

第一步:安装系统依赖

假设你希望使用系统包(RPM 或 DEB)来满足 Seastar 的依赖,先运行仓库根目录下的依赖安装脚本:

$ sudo ./install-dependencies.sh

该脚本会根据当前发行版安装编译 Seastar 所需的系统库(如 Boost、hwloc、yaml-cpp、c-ares、fmt、lz4 等)。更详细的替代工作流请参考 HACKING.md。

第二步:配置(release 模式)

$ ./configure.py --mode=release

configure.py本质上是 CMake 的包装脚本(源码见 configure.py),--mode参数直接映射到CMAKE_BUILD_TYPE。配置完成后会生成对应的构建目录。

第三步:编译

$ ninja -C build/release

如果编译失败并出现类似g++: internal compiler error: Killed (program cc1plus)的错误,说明 GCC 内存不足。解决方法是限制并行任务数并使用-j1,同时至少为机器分配 4 GiB 内存:

$ ninja -C build/release -j1

依赖缺失时的处理:--cook

如果你缺少 Seastar 的某个依赖,可以让配置过程在本地临时获取该依赖的版本用于开发。例如在本地获取fmt:

$ ./configure.py --mode=dev --cook fmt

--cook可以重复多次以选择多个依赖。该机制基于 cmake-cooking(配方定义见 cooking_recipe.cmake),会把依赖安装到构建目录下的_cooking区域,实现可复现的开发环境。有效配方名(如fmt、c-ares、dpdk等)由configure.py在运行期从cooking_recipe.cmake中解析校验(见 configure.py)。

构建模式详解

configure.py --mode支持以下模式,完整表格来自 README.md,每个模式映射到特定的 CMake 构建类型:

模式CMake 模式调试信息优化Sanitizers分配器检查用途
debugDebug有-O0ASAN, UBSAN系统全部gdb 调试
releaseRelWithDebInfo有-O3无Seastar 自研Asserts生产环境
devDev(自定义)无-O1无Seastar 自研Asserts构建与测试循环
sanitizeSanitize(自定义)有-OsASAN, UBSAN系统全部第二轮测试、追踪 bug

注意:Seastar 对分配器和优化比一般项目更敏感。粗略的经验法则是:release比dev快约 2 倍,比sanitize快约 150 倍,比debug快约 300 倍。该结论来自 README 原文,建议根据你的实际硬件自行验证。

模式到 CMake 构建类型的映射可以在 configure.py 中确认:release → RelWithDebInfo、debug → Debug、dev → Dev、sanitize → Sanitize。此外还有fuzz模式(映射到Fuzz)。

configure.py 进阶选项

从 configure.py 可以看到configure.py还支持大量可定制选项,常用者包括:

  • --build-root:自定义构建根目录名,允许同一仓库内并存多个配置;
  • --cflags/--ldflags/--optflags:追加编译器、链接器与 release 专用优化参数;
  • --compiler/--c-compiler:指定 C++/C 编译器(默认 g++/gcc),也可改用 clang;
  • --compiler-cache:自动选择 sccache/ccache 加速增量编译;
  • --c++-standard:显式指定 C++ 标准(23 或 26);
  • --cook:以 cmake-cooking 方式在本地供应某个依赖;
  • --dpdk/--disable-dpdk、--io-uring、--gnutls、--openssl、--lttng:三态开关控制 DPDK、io_uring(liburing)、TLS 后端与 LTTng 追踪支持;
  • --prefix:安装路径(默认/usr/local);
  • --scheduling-groups-count:reactor 中可用的调度组数量(默认 16);
  • --api-level:兼容性 API 级别(默认 10,即最新);
  • --without-tests/--without-apps/--without-demos:默认不构建测试、应用或示例;
  • --compile-commands-json:生成compile_commands.json以配合 clangd。

在不安装的情况下使用 Seastar

Seastar 支持直接从构建目录消费(无需安装到系统),既可以用 pkg-config,也可以用 CMake,详见 README.md。以下假设 Seastar 仓库位于$seastar_dir。

方式一:pkg-config

$ g++ my_app.cc $(pkg-config --libs --cflags --static $seastar_dir/build/release/seastar.pc) -o my_app

--static是必需的:当前 Seastar 以静态库形式构建,必须告诉 pkg-config 在链接命令中包含其私有依赖。seastar.pc的生成模板位于 pkgconfig/seastar.pc.in,其中Libs.private段聚合了 dl、rt、lksctp-tools、liburing、LTTng、stdatomic、DPDK 等全部静态传递依赖。

方式二:CMake 的 Seastar 包

my_app的CMakeLists.txt如下(注意CMAKE_CXX_STANDARD设为 23):

set (CMAKE_CXX_STANDARD 23) find_package (Seastar REQUIRED) add_executable (my_app my_app.cc) target_link_libraries (my_app Seastar::seastar)

随后在构建目录中执行:

$ mkdir $my_app_dir/build $ cd $my_app_dir/build $ cmake -DCMAKE_PREFIX_PATH="$seastar_dir/build/release;$seastar_dir/build/release/_cooking/installed" -DCMAKE_MODULE_PATH=$seastar_dir/cmake $my_app_dir

其中CMAKE_PREFIX_PATH保证 CMake 能定位到 Seastar 及其编译好的子模块,CMAKE_MODULE_PATH保证 CMake 能使用 Seastar 自带的查找脚本(cmake/ 目录下的 Find*.cmake)来定位依赖。

安装后使用 Seastar

也可以将 Seastar 安装到文件系统后再消费,详见 README.md。

重要前提:Seastar 与定制版 DPDK 配合工作,默认会构建并把 DPDK 子模块安装到$build_dir/_cooking/installed。

先配置安装路径:

$ ./configure.py --mode=release --prefix=/usr/local

再执行 install 目标:

$ ninja -C build/release install

之后用 pkg-config 消费:

$ g++ my_app.cc $(pkg-config --libs --cflags --static seastar) -o my_app

或用与之前完全相同的CMakeLists.txt,但 CMake 调用大幅简化:

$ cmake ..

如果 Seastar 没有安装到/usr或/usr/local这类标准位置,则需要加-DCMAKE_PREFIX_PATH=$my_install_root。

HACKING.md 还提供了多文件编译的 pkg-config 用法:先分别编译.o目标文件(只带--cflags),最后统一链接(带--libs --static),以及通过ninja test_unit、ninja test、ninja test_unit_thread_run运行测试(见 HACKING.md)。

C++ 标准:C++23 或 C++26

Seastar 同时支持 C++23 与 C++26,构建默认采用编译器支持的最新标准,但可以通过--c++-standard配置选项显式选择,例如:

$ ./configure.py --c++-standard=23

如果直接使用 CMake,则设置CMAKE_CXX_STANDARD变量。从 configure.py 的源码可以看到,未显式指定时,configure 会依次探测 C++26、C++23,取编译器支持的第一个;若都不支持则直接报错。

兼容性策略详见 doc/compatibility.md:Seastar 将一直支持 ISO C++ 委员会最新批准的两个标准,每当新标准获批,较老的一个即被退役;同时保持源码级向后兼容(二进制协议如 RPC 也保持兼容),但不维护链接级兼容——不能用某个版本的 Seastar 链接用另一版本构建的应用。Seastar 支持 GCC 与 Clang(当前两个大版本),平台为 Linux。

快速上手:第一个 Seastar 程序

仓库中的示例程序 demos/hello-world.cc 使用日志 API 输出 Hello World。更简化的入门版在 doc/tutorial.md:

#include <seastar/core/app-template.hh> #include <seastar/core/reactor.hh> #include <iostream> int main(int argc, char** argv) { seastar::app_template app; return app.run(argc, argv, [] { std::cout << "Hello world\n"; return seastar::make_ready_future<>(); }); }

每个 Seastar 程序都必须定义一个app_template对象并调用其run方法:它会启动主事件循环(Seastarengine),在一个或多个 CPU 上运行,然后执行传入的 lambda。return make_ready_future<>();让事件循环在打印完消息后立即退出;更典型的服务器程序应返回一个决定何时退出的 future。注意不应使用 C 语言exit(),否则会阻止 Seastar 与应用执行清理。

所有 Seastar 类型与函数都位于seastar命名空间。编译这个程序(对应 demos/hello-world.cc)可以直接使用 Docker(Dockerfile 见 docker/dev/Dockerfile):

$ docker build -t seastar-dev -f ./docker/dev/Dockerfile . $ docker run -it --rm -v $(pwd):/seastar seastar-dev /seastar/configure.py --mode=dev --cook=c-ares $ docker run -it --rm -v $(pwd):/seastar seastar-dev ninja -C /seastar/build/dev $ docker run -it --rm -v $(pwd):/seastar seastar-dev /seastar/build/dev/demos/hello-world_demo -c1

不用 Docker 的话,先用 pkg-config 编译($SEASTAR为构建目录):

$ c++ getting-started.cc `pkg-config --cflags --libs --static $SEASTAR/build/release/seastar.pc`

如果 Seastar 已安装,命令行更短:

$ c++ getting-started.cc `pkg-config --cflags --libs --static seastar`

或用 CMake(CMakeLists.txt中使用find_package(Seastar REQUIRED)与target_link_libraries(example PRIVATE Seastar::seastar)),随后mkdir build && cd build && cmake .. && make,运行结果:

$ ./example Hello world

核心概念:future 与 continuation

future是 Seastar 异步编程的基石,一个 future 表示一个可能尚未就绪的计算结果,例如:从网络读到的数据缓冲区、定时器到期、磁盘写完成、或需要多个 future 值组合才能得到的结果。future<>表示某件事最终会完成但不返回任何值。

future 通过then()方法消费,传入回调(通常为 lambda),即可把多个异步步骤链式组合:

future<int> get(); // 承诺最终产生一个 int future<> put(int); // 承诺存储一个 int future<> f() { return get().then([] (int value) { return put(value + 1).then([] { std::cout << "value stored successfully\n"; }); }); }

由于then()的 lambda 若返回 future x,则then()本身返回的 future y 会承载相同的值,因此可以扁平化嵌套:

future<> f() { return get().then([] (int value) { return put(value + 1); }).then([] { std::cout << "value stored successfully\n"; }); }

循环则通过尾递归实现,make_ready_future<>()返回一个立即可用的 future,对应循环终止条件。上述模式与底层链式回调的完整推导见 doc/mini-tutorial.md 与 doc/tutorial.md(tutorial 还覆盖了线程与内存模型、-c控制线程数、-m/--reserve-memory控制内存分配等深入内容)。

原生 TCP/IP 协议栈

Seastar 自带用户态 TCP/IP 协议栈(share-nothing 架构之上实现),以获得比内核协议栈更优的性能,详见 doc/native-stack.md。它同时提供双向零拷贝:可以直接处理 TCP 栈缓冲区中的数据,也可以把自有数据结构的内容作为消息的一部分发出而无需拷贝。当然,Seastar 也允许使用宿主机操作系统的 TCP 协议栈(POSIX 栈)。协议栈实现位于 src/net/(如 src/net/tcp.cc、src/net/native-stack.cc),DPDK 支持为可选项,构建说明见 doc/building-dpdk.md。

推荐硬件配置

根据 README.md,Seastar 推荐的硬件配置如下:

  • CPU:多多益善,Seastar 非常适合多核与 NUMA 系统;
  • NIC:越快越好,建议 10G 或 40G 网卡;1G 网卡也可用,但吞吐可能受其容量限制。此外每个 CPU 对应的硬件队列越多越好,否则需要在软件中模拟;
  • 磁盘:IOPS 高的快速 SSD;
  • 客户端机器:通常单个客户端机器无法压满服务器。memaslap(memcached 压测)和 wrk(httpd 压测)都可能无法压垮对应服务端,建议把客户端放在服务器之外的机器上,并用多台客户端。

使用 Seastar 的项目

README 明确列出的 Seastar 使用者包括:

  • Scylla:兼容 Cassandra 与 DynamoDB 的快速 NoSQL 数据存储,Seastar 的诞生契机;
  • Redpanda:面向关键任务系统的 Kafka 兼容流式数据平台;
  • cpv-cql-driver:基于 Seastar 的 Cassandra/Scylla C++ 驱动;
  • cpv-framework:基于 Seastar 的 C++ Web 框架;
  • smf:高性能 RPC 框架;
  • Ceph(Crimson):基于 Seastar 的下一代 OSD(对象存储守护进程)实现。

更多学习资源

  • 入门教程:doc/mini-tutorial.md;完整教程:doc/tutorial.md;
  • 用户态网络栈:doc/native-stack.md;DPDK 构建:doc/building-dpdk.md;Docker 构建:doc/building-docker.md;
  • 开发与贡献指引:HACKING.md、CONTRIBUTING.md、coding-style.md;
  • 兼容性与 API 级别:doc/compatibility.md;
  • 可运行的示例代码集中在 demos/(如 hello-world.cc、echo_demo.cc、tcp_demo.cc、rpc_demo.cc),配套应用与测试分别在 apps/ 与 tests/。

从源码结构看,Seastar 的核心实现分布在 src/core/(reactor、smp、app-template、future、io_queue 等)与 src/net/(协议栈与 socket 抽象),公共头文件则在 include/seastar/(如 include/seastar/core/future.hh、include/seastar/core/app-template.hh)。按本文流程完成构建后,即可在这些示例的基础上逐步深入 Seastar 的异步编程世界。

  • 后端
  • 异步编程
  • 网络

【免费下载链接】seastar

High performance server-side application framework

项目地址:https://gitcode.com/gh_mirrors/se/seastar
点击查看免费下载

相关推荐

上一篇:Gas Town Dolt 存储架构:多 Agent 工作区的 Git 化数据库底座
下一篇:OpenSEO v0.1.6 发布解读:共享项目上下文、SAM Skills 与 Google Analytics 深度集成

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/9/25 17:30:27

VirtualBox跑Ubuntu实战指南:Windows宿主机协同调试手册

1. 这不是“装个系统”那么简单&#xff1a;VirtualBox跑Ubuntu到底在解决什么问题&#xff1f;VirtualBox、Ubuntu、虚拟机、安装、系统——这五个词凑在一起&#xff0c;表面看是教你怎么点几下鼠标装个Linux&#xff0c;但实际背后是一整套现代软件开发与系统管理的底层工作…

作者头像 李华