OPENPPP2 Code Analysis Three

OPENPPP2 Code Analysis Three

一、核心理念

OPENPPP2是一个企业级虚拟以太网VNP解决方案,采用现代化的架构设计思想:

1.1 技术特点

  • 全协程+多线程架构:混合并发模型,结合协程的轻量级和多线程的并行能力
  • 同步超线程IO技术(SSMT):在Linux平台上实现多线程包处理优化
  • 虚拟以太网技术:完整实现二层网络虚拟化,支持虚拟子网和广播

1.2 设计原则

该系统遵循以下设计原则:

  • 技术中立原则:作为纯技术实现,不运营服务器、不存储日志
  • 模块化设计:客户端/服务器分离,驱动层、协议层、应用层清晰分层
  • 高性能导向:采用零拷贝、内存池、SIMD优化等技术

二、事件驱动架构模型

OPENPPP2采用完整的事件驱动状态机架构(Event-Driven State Machine Architecture)

2.1 Boost.Asio事件循环

整个系统基于Boost.Asio的io_context构建异步事件处理机制:

核心事件循环组件:

  • Executor(默认上下文):主事件循环
  • Scheduler(调度器上下文):多线程IO完成处理
  • Per-Thread Context:每线程独立事件循环

2.2 回调驱动的包处理

网络包处理采用事件回调模式:

TAP设备的包输入通过PacketInputEventHandler回调实现异步处理。

2.3 定时器事件系统

OnTickOnUpdate方法实现周期性事件处理,用于保活、超时检测等。

三、协程系统架构

3.1 协程核心实现

OPENPPP2实现了自定义的**栈式协程(Stackful Coroutine)**系统:

核心特性:

  • 基于Boost.Context的fcontext实现上下文切换
  • 支持SpawnSuspendResume操作
  • 集成Boost.Asio实现异步操作的同步写法

3.2 协程状态管理

使用原子变量管理协程状态,包括:

  • s_:状态标志
  • callee_/caller_:调用者和被调用者上下文
  • stack_:协程栈内存

3.3 协程调度器

Executors类管理协程调度,提供:

  • 多个io_context实例用于负载均衡
  • 协程在不同上下文间迁移(ShiftToScheduler
  • 与Strand协同工作确保线程安全

四、工程结构

4.1 目录结构

复制代码
openppp2/
├── ppp/                    # 核心库
│   ├── app/               # 应用层
│   │   ├── client/        # 客户端实现
│   │   ├── server/        # 服务端实现
│   │   ├── protocol/      # 协议层
│   │   └── mux/           # 多路复用
│   ├── ethernet/          # 虚拟以太网
│   ├── tap/               # TAP驱动接口
│   ├── net/               # 网络协议栈
│   ├── coroutines/        # 协程系统
│   ├── threading/         # 线程管理
│   ├── transmissions/     # 传输层
│   └── configurations/    # 配置管理
├── common/                # 通用组件
├── windows/               # Windows平台
├── linux/                 # Linux平台
├── darwin/                # macOS平台
└── android/               # Android平台

4.2 应用层结构

PppApplication是应用入口,管理:

  • 配置加载与验证
  • 客户端/服务器模式切换
  • 统计信息收集
  • 生命周期管理

五、数据流架构

5.1 包处理流水线

输入路径(TAP → 虚拟以太网 → 协议栈):

复制代码
TAP设备接收
    ↓
PacketInputEventHandler回调
    ↓
VEthernet::PacketInput()
    ↓
协议分流 (TCP/UDP/ICMP)
    ↓
IPFragment处理分片
    ↓
OnPacketInput()虚拟方法
    ↓
应用层处理

输出路径(应用 → 虚拟以太网 → TAP):

5.2 协议层数据流

协议层定义了多种包动作(PacketAction):

  • INFO/KEEPALIVED:信息和保活
  • FRP系列:端口映射(Fast Reverse Proxy)
  • VNP系列:TCP连接管理(SYN/PSH/FIN)、NAT、UDP转发
  • MUX系列:多路复用

5.3 MUX多路复用数据流

MUX实现带宽聚合,通过多个TCP连接传输数据:

数据流程:

  1. 客户端发起多个并行连接(DoMux
  2. 服务器接受并建立映射(OnMux
  3. 数据包按序号分发到不同连接
  4. 接收端重组数据包

六、数据结构

6.1 IP帧结构

IPFrame是核心数据结构,封装IP层信息:

  • 地址族、源/目标IP、TTL、ToS
  • 协议类型、标志位
  • 载荷和选项的BufferSegment

6.2 配置数据结构

AppConfiguration包含完整配置信息:

  • 并发控制concurrent线程数
  • 加密配置key结构体(协议层/传输层加密)
  • 网络配置:TCP/UDP参数、WebSocket、MUX设置
  • 虚拟内存vmem配置内存池

6.3 内存管理结构

使用BufferswapAllocator实现专用虚拟内存池,优化内存分配性能。

七、驱动结构

7.1 TAP驱动抽象层

ITap接口定义跨平台TAP设备抽象:

  • 输入PacketInput事件处理器
  • 输出Output方法族
  • 配置:IP地址、网关、子网掩码
  • 状态管理OpenDisposeIsReady

7.2 平台特定实现

驱动层针对不同平台有专门实现:

  • WindowsTapWindows - 使用NDIS驱动
  • LinuxTapLinux - 使用TUN/TAP字符设备
  • macOSTapDarwin - 使用utun接口

7.3 虚拟网络栈

VEthernet集成TAP驱动和网络栈:

  • LWIP模式:使用lwIP用户态协议栈(Windows默认)
  • CTCP模式:使用内核协议栈(Linux/macOS默认)
  • VNet模式:启用子网转发功能

八、流程架构

8.1 应用启动流程

主流程:

  1. 环境初始化:解析命令行、加载配置
  2. 防火墙配置(Windows):添加应用规则
  3. TAP设备创建:打开虚拟网卡
  4. 网络切换器创建VEthernetNetworkSwitcher(客户端)或VirtualEthernetSwitcher(服务器)
  5. 启动事件循环Executors::Run

8.2 客户端连接流程



加载配置
创建TAP设备
初始化VEthernetNetworkSwitcher
连接VNP服务器
连接成功?
建立隧道
重连逻辑
启动MUX多路复用
数据转发就绪

8.3 数据包转发流程

协议层定义的数据包处理方法:

  • DoConnect/OnConnect:TCP连接建立
  • DoPush/OnPush:数据推送
  • DoSendTo/OnSendTo:UDP数据报转发
  • DoNat/OnNat:NAT包处理

8.4 协程工作流程



YieldContext::Spawn
分配栈空间
创建fcontext
投递到io_context
协程开始执行
Suspend挂起
异步操作
Resume恢复
继续执行
完成?
释放资源

九、特殊架构特性

9.1 SSMT(Super Synchronous Multi-Threading)

在Linux平台上,OPENPPP2实现了特殊的多线程包处理优化:

SSMT特性:

  • 多线程模式:将包处理分发到多个线程
  • 单线程优化(st):针对单连接大流量
  • 多队列模式(mq):针对多连接高并发

9.2 纸飞机加速技术(PaperAirplane)

Windows平台独有的TCP加速技术,通过LSP(Layered Service Provider)实现分层加速。

9.3 虚拟BGP多线分流

实现智能路由分流,根据目标地址选择最优路径。

十、性能优化技术

10.1 零拷贝与内存池

通过BufferswapAllocator实现专用内存管理,减少内存分配开销。

10.2 SIMD加密优化

支持AES-NI指令集加速:

加速算法:

  • simd-aes-128-cfb
  • simd-aes-256-cfb
  • simd-aes-128-gcm
  • simd-aes-256-gcm

10.3 TCP优化技术

支持:

  • TCP Turbo:窗口优化
  • TCP Fast Open:减少握手延迟
  • 拥塞窗口(cwnd)/接收窗口(rwnd)控制

备注

OPENPPP2采用了现代化的C++17架构设计,核心特点是:

  1. 混合并发模型:协程提供同步编程体验,多线程提供并行能力,事件循环提供高效IO
  2. 分层清晰:驱动层(ITap)→ 虚拟以太网层(VEthernet)→ 协议层(VirtualEthernetLinklayer)→ 应用层
  3. 跨平台设计:通过抽象接口和条件编译支持Windows/Linux/macOS/Android
  4. 高度可配置:通过JSON配置文件控制所有行为参数
  5. 生产级优化:内存池、SIMD、零拷贝等技术确保高性能

系统实现了完整的**事件驱动状态机(Event-Driven State Machine)**模式,通过协程、回调、定时器等机制实现复杂的异步状态管理。

Citations

File: README_CN.md (L14-51)

markdown 复制代码
## <img src="https://img.icons8.com/color/48/000000/features-list.png" width="30" height="30"> 核心技术特点

<div style="display: grid; grid-template-columns: repeat(2, 1fr); gap: 12px;">

<div>

- <img src="https://img.icons8.com/color/24/000000/processor.png" width="20" height="20"> **同步超线程IO技术**  
- <img src="https://media.istockphoto.com/id/1469980757/vector/cloud-multi-threading-icon-in-vector-logotype.jpg?s=612x612&w=0&k=20&c=SgJXI9dkgy1l__U4m4H7Y2SJuCEJk53VpZvwxYqQqDg=" width="20" height="20"> **全协程+多线程架构**  
- <img src="https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcTIHdQXotRNOMUnypnmpRRAMGiTmgtnvmaEOw&s" width="20" height="20"> **支持可打印明文传输**  
- <img src="https://img.ixintu.com/download/jpg/20201107/570f5ecbfba462cec0568a98693aa8cc_512_321.jpg!con" width="20" height="20"> **全双工/半双工隧道**  
- <img src="https://img.icons8.com/color/24/000000/network.png" width="20" height="20"> **VNP虚拟子网**  
- <img src="https://img.icons8.com/color/24/000000/port.png" width="20" height="20"> **端口映射到公网 P-NAT2**  
- <img src="https://cdn-icons-png.flaticon.com/512/7349/7349720.png" width="20" height="20"> **正向代理支持**  
- <img src="https://img.icons8.com/color/24/000000/firewall.png" width="20" height="20"> **虚拟防火墙**  
- <img src="https://img.icons8.com/color/24/000000/route.png" width="20" height="20"> **虚拟BGP多线分流**  
- <img src="https://img.icons8.com/color/24/000000/domain.png" width="20" height="20"> **域名查询分流**  
- <img src="https://img.icons8.com/color/24/000000/router.png" width="20" height="20"> **天然支持软路由**  
- <img src="https://img.icons8.com/color/24/000000/airplane-mode-on.png" width="20" height="20"> **PaperAirplane 分层技术**  
</div>

<div>

- <img src="https://img.icons8.com/color/24/000000/network-card.png" width="20" height="20"> **双网络协议栈支持**  
- <img src="https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcTjxlVdSXIeMvmISIN0dupsU60ISjdSyxN7xw&s" width="20" height="20"> **广播支持(非单播)**  
- <img src="https://www.shutterstock.com/image-vector/tunnel-sign-multi-series-style-260nw-2440158425.jpg" width="20" height="20"> **多种隧道协议支持**  
- <img src="https://img.icons8.com/color/24/000000/merge.png" width="20" height="20"> **MUX多路复用**  
- <img src="https://img.icons8.com/color/24/000000/dns.png" width="20" height="20"> **DNS缓存**  
- <img src="https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcSyLWW0UbSGujy4OkGa0oHvN1Ad1_YXmZGIgSHlpHz1K0-u6a_mYbw84I_aZJA8IzB-jLg&usqp=CAU" width="20" height="20"> **专用虚拟内存**  
- <img src="https://cdn-icons-png.flaticon.com/512/10988/10988147.png" width="20" height="20"> **CDN转发支持**  
- <img src="https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcS8vZjAno4KJAxr9K97IzoIGQiJ1ajH9FQOyA&s" width="20" height="20"> **VNP Turbo**  
- <img src="https://img.icons8.com/color/24/000000/fast-forward.png" width="20" height="20"> **TCP Fast Open**  
- <img src="https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcQ2LHYDgAPNDQrrF-Es68XphlSUJ1XBbqKdpw&s" width="20" height="20"> **固定窗口大小设置**  
- <img src="https://img.icons8.com/color/24/000000/forward.png" width="20" height="20"> **VNP服务器代理转发**  
- <img src="https://play-lh.googleusercontent.com/Ac2LuYFUdHoiSZOVDwnlp0ozwCBMqBC7GALSUevSsQxEtq6eMVCSEGxa7FuEqXnjlw" width="20" height="20"> **UDP多线路宽频聚合**  

</div>

</div>

File: README_CN.md (L191-206)

markdown 复制代码
/* 经三国司法实践验证的免责文本 */  
1. **技术中立原则**  
   本工具系网络协议纯技术实现(RFC 8446标准),开发者:  
   - 不运营任何服务器  
   - 不存储用户流量日志  
   - 不提供商业支持服务  

2. **违法责任隔离机制**  
   ```mermaid
   graph LR
      用户行为-->ISP[网络服务提供商]
      开发者-->代码[GitHub仓库]
      司法取证-->ISP
      开发者-.无权访问.->用户行为
复制代码
**File:** README_CN.md (L507-545)
```markdown
## 🚀 SIMD + AES_NI 优化实现
### 优化算法
| 算法名称               | 实现文件路径                                                                                     |
|------------------------|--------------------------------------------------------------------------------------------------|
| `simd-aes-128-cfb`     | [simd_aes_128_cfb.cpp](https://github.com/liulilittle/openppp2/blob/main/common/aesni/impl/simd_aes_128_cfb.cpp) |
| `simd-aes-256-cfb`     | [simd_aes_256_cfb.cpp](https://github.com/liulilittle/openppp2/blob/main/common/aesni/impl/simd_aes_256_cfb.cpp) |
| `simd-aes-128-gcm`     | [simd_aes_128_gcm.cpp](https://github.com/liulilittle/openppp2/blob/main/common/aesni/impl/simd_aes_128_gcm.cpp) |
| `simd-aes-256-gcm`     | [simd_aes_256_gcm.cpp](https://github.com/liulilittle/openppp2/blob/main/common/aesni/impl/simd_aes_256_gcm.cpp) |

**前提条件**  
1. 仅支持 i386/amd64 处理器平台  
2. CPU 必须支持 AES-NI 指令集  
   (PPP 将通过汇编指令自动检测 CPU 支持性)

**编译步骤**  
1. 修改 `CMakeLists.txt` 文件:
   ```cmake
   SET(__SIMD__ TRUE)  # 原值为 FALSE
2. 按标准 Linux 流程编译:
    ```bash
    mkdir build && cd build
    cmake .. -DCMAKE_BUILD_TYPE=Release
    make -j $(nproc) 
    ```

**注意事项**  
- 仅支持 i386/amd64 平台,其他平台启用将导致编译失败  
- 需 CPU 硬件支持 AES-NI 指令集(PPP 自动检测)  
- 仅优化以下算法:  
  - `simd-aes-128-cfb`  
  - `simd-aes-256-cfb`  
  - `simd-aes-128-gcm`  
  - `simd-aes-256-gcm`  
- 修改 `CMakeLists.txt` 后需完整重编译:
  ```bash
  rm -rf build && mkdir build && cd build
  cmake .. -DCMAKE_BUILD_TYPE=Release
  make clean && make -j $(nproc)


**File:** ppp/threading/Executors.h (L12-62)
```text
        class Executors final
        {
        public:
            typedef ppp::function<int(int argc, const char* argv[])>                                ExecutorStart;
            typedef boost::asio::io_context                                                         Context;
            typedef std::shared_ptr<Context>                                                        ContextPtr;
            typedef boost::asio::strand<boost::asio::io_context::executor_type>                     Strand;
            typedef std::shared_ptr<Strand>                                                         StrandPtr;
            class Awaitable
            {
                typedef std::mutex                                                                  SynchronizedObject;
                typedef std::unique_lock<SynchronizedObject>                                        LK;

            public:
                Awaitable() noexcept;
                virtual ~Awaitable() noexcept = default;

            public:
                virtual void                                                                        Processed() noexcept;
                virtual bool                                                                        Await() noexcept;

            private:
                bool                                                                                completed = false;
                bool                                                                                processed = false;
                SynchronizedObject                                                                  mtx;
                std::condition_variable                                                             cv;
            };
            typedef ppp::function<void(int)>                                                        ApplicationExitEventHandler;

        public:
            static ApplicationExitEventHandler                                                      ApplicationExit;

        public:
            static std::shared_ptr<boost::asio::io_context>                                         GetExecutor() noexcept;
            static std::shared_ptr<boost::asio::io_context>                                         GetScheduler() noexcept;
            static std::shared_ptr<boost::asio::io_context>                                         GetCurrent(bool defaultContext = true) noexcept;
            static std::shared_ptr<boost::asio::io_context>                                         GetDefault() noexcept;
            static std::shared_ptr<Byte>                                                            GetCachedBuffer(const std::shared_ptr<boost::asio::io_context>& context) noexcept;
            static void                                                                             GetAllContexts(ppp::vector<ContextPtr>& contexts) noexcept;

        public:
            static DateTime                                                                         Now() noexcept;
            static uint64_t                                                                         GetTickCount() noexcept;
            static bool                                                                             SetMaxSchedulers(int completionPortThreads) noexcept;

        public:
            static void                                                                             SetMaxThreads(const std::shared_ptr<BufferswapAllocator>& allocator, int completionPortThreads) noexcept;
            static bool                                                                             Exit() noexcept;
            static bool                                                                             Exit(const std::shared_ptr<boost::asio::io_context>& context) noexcept;
            static int                                                                              Run(const std::shared_ptr<BufferswapAllocator>& allocator, const ExecutorStart& start);
            static int                                                                              Run(const std::shared_ptr<BufferswapAllocator>& allocator, const ExecutorStart& start, int argc, const char* argv[]);

File: ppp/tap/ITap.h (L12-62)

text 复制代码
        class ITap : public std::enable_shared_from_this<ITap>
        {
            friend class                                                    WritePacketToKernelNio;
            struct                                                          PacketContent
            {
                std::shared_ptr<Byte>                                       Packet       = NULLPTR;
                int                                                         PacketLength = 0;
            };

        public:
            struct                                                          PacketInputEventArgs
            {
                void*                                                       Packet       = NULLPTR;
                int                                                         PacketLength = 0;
            };
            typedef ppp::function<bool(ITap*, PacketInputEventArgs&)>       PacketInputEventHandler;

        public:
            const uint32_t                                                  IPAddress      = ppp::net::IPEndPoint::AnyAddress;
            const uint32_t                                                  GatewayServer  = ppp::net::IPEndPoint::AnyAddress;
            const uint32_t                                                  SubmaskAddress = ppp::net::IPEndPoint::AnyAddress;

        public:
            PacketInputEventHandler                                         PacketInput;
            std::shared_ptr<ppp::threading::BufferswapAllocator>            BufferAllocator;

        public:
            static constexpr int                                            Mtu = ppp::net::native::ip_hdr::MTU;

        public:
            ITap(const std::shared_ptr<boost::asio::io_context>& context, const ppp::string& id, void* tun, uint32_t ip, uint32_t gw, uint32_t mask, bool hosted_network);
            virtual ~ITap() noexcept;

        public:
            virtual bool                                                    IsReady() noexcept;
            virtual bool                                                    IsOpen() noexcept;
            virtual bool                                                    SetInterfaceMtu(int mtu) noexcept = 0;

        public:
            virtual bool                                                    Open() noexcept;
            virtual void                                                    Dispose() noexcept;
            virtual bool                                                    Output(const std::shared_ptr<Byte>& packet, int packet_size) noexcept;
            virtual bool                                                    Output(const void* packet, int packet_size) noexcept;

        public:
            const ppp::string&                                              GetId() noexcept             { return _id; }
            std::shared_ptr<boost::asio::io_context>                        GetContext() noexcept        { return _context; }
            void*                                                           GetHandle() noexcept         { return _handle; }
            int&                                                            GetInterfaceIndex() noexcept { return _interface_index; }
            bool                                                            IsHostedNetwork() noexcept   { return _hosted_network; }

File: ppp/ethernet/VEthernet.h (L1-20)

text 复制代码
#pragma once

#include <ppp/threading/Timer.h>
#include <ppp/threading/BufferswapAllocator.h>
#include <ppp/tap/ITap.h>
#include <ppp/ethernet/VNetstack.h>
#include <ppp/net/native/ip.h>
#include <ppp/net/native/tcp.h>
#include <ppp/net/packet/IPFragment.h>
#include <ppp/net/packet/IPFrame.h>
#include <ppp/net/packet/UdpFrame.h>
#include <ppp/net/packet/IcmpFrame.h>

struct pbuf;

namespace ppp
{
    namespace ethernet
    {
        class VEthernet : public std::enable_shared_from_this<VEthernet>

File: ppp/ethernet/VEthernet.h (L34-54)

text 复制代码
            VEthernet(const std::shared_ptr<boost::asio::io_context>& context, bool lwip, bool vnet, bool mta) noexcept;
            virtual ~VEthernet() noexcept;

        public:
            std::shared_ptr<VEthernet>                                      GetReference()          noexcept { return shared_from_this(); }
            std::shared_ptr<ITap>                                           GetTap()                noexcept
            {
                std::shared_ptr<VNetstack> netstack = netstack_;
                return NULLPTR != netstack ? netstack->Tap : NULLPTR;
            }
            std::shared_ptr<boost::asio::io_context>                        GetContext()            noexcept { return context_; }
            std::shared_ptr<VNetstack>                                      GetNetstack()           noexcept { return netstack_; }
            SynchronizedObject&                                             GetSynchronizedObject() noexcept { return syncobj_; }
            virtual std::shared_ptr<ppp::threading::BufferswapAllocator>    GetBufferAllocator()    noexcept;

        public:
            virtual bool                                                    Open(const std::shared_ptr<ITap>& tap) noexcept;
            virtual void                                                    Dispose()                              noexcept;
            bool                                                            IsLwip()                               noexcept { return lwip_; }
            bool                                                            IsVNet()                               noexcept { return vnet_; }
            virtual bool                                                    IsDisposed()                           noexcept;

File: ppp/ethernet/VEthernet.h (L57-69)

text 复制代码
            bool                                                            Output(IPFrame* packet) noexcept;
            virtual bool                                                    Output(const void* packet, int packet_length) noexcept;
            virtual bool                                                    Output(const std::shared_ptr<Byte>& packet, int packet_length) noexcept;

        protected:
            virtual std::shared_ptr<IPFragment>                             NewFragment() noexcept;
            virtual std::shared_ptr<VNetstack>                              NewNetstack() noexcept = 0;

        protected:
            virtual bool                                                    OnTick(uint64_t now) noexcept;
            virtual bool                                                    OnUpdate(uint64_t now) noexcept;
            virtual bool                                                    OnPacketInput(const std::shared_ptr<IPFrame>& packet) noexcept;
            virtual bool                                                    OnPacketInput(ppp::net::native::ip_hdr* packet, int packet_length, int header_length, int proto, bool vnet) noexcept;

File: ppp/ethernet/VEthernet.h (L77-109)

text 复制代码
#if !defined(_WIN32)
        public:
            int                                                             Ssmt(int* ssmt) noexcept;
#if defined(_LINUX)
            bool                                                            SsmtMQ(bool* mq) noexcept;
#endif

        private:
            void                                                            StopAllSsmt() noexcept;
            bool                                                            ForkAllSsmt() noexcept;
#endif

        private:
            int                                                             PacketInput(ppp::net::native::ip_hdr* iphdr, int iphdr_hlen, int proto, struct pbuf* packet, int packet_length, bool allocated) noexcept;

        private:
            struct 
            {
                bool                                                        disposed_ : 1;
                bool                                                        lwip_     : 1;
                bool                                                        vnet_     : 1;
                bool                                                        mta_      : 5;
            };
#if !defined(_WIN32)
            int                                                             ssmt_     = 0;
#if defined(_LINUX)
            struct {
                bool                                                        ssmt_mq_                : 1;
                bool                                                        ssmt_mq_to_take_effect_ : 7;
            };
#endif
            std::vector<std::shared_ptr<boost::asio::io_context>/**/>       sssmt_;
#endif

File: ppp/coroutines/YieldContext.h (L1-10)

text 复制代码
#pragma once

#include <ppp/stdafx.h>
#include <boost/coroutine/detail/coroutine_context.hpp>
#include <boost/context/detail/fcontext.hpp>
#include <ppp/threading/Executors.h>
#include <ppp/threading/BufferswapAllocator.h>

namespace ppp
{

File: ppp/coroutines/YieldContext.h (L13-58)

text 复制代码
        class YieldContext final
        {
        public:
            typedef ppp::function<void(YieldContext&)>                          SpawnHander;

        public:
            bool                                                                Resume() noexcept;
            bool                                                                Suspend() noexcept;
            YieldContext*                                                       GetPtr() const noexcept        { return constantof(this);}
            boost::asio::io_context&                                            GetContext() const noexcept    { return context_; }
            boost::asio::strand<boost::asio::io_context::executor_type>*        GetStrand() const noexcept     { return strand_; }

        public:
            bool                                                                S() noexcept { return s_.load() != 0; }
            bool                                                                Y() noexcept { return Suspend(); }
            bool                                                                R() noexcept;

        public:
            operator                                                            bool() const noexcept          { return NULLPTR != GetPtr(); }
            operator                                                            YieldContext*() const noexcept { return GetPtr();         }

        public:
            static bool                                                         Spawn(boost::asio::io_context& context, SpawnHander&& spawn) noexcept
            {
                return YieldContext::Spawn(context, std::move(spawn), PPP_COROUTINE_STACK_SIZE);
            }
            static bool                                                         Spawn(boost::asio::io_context& context, SpawnHander&& spawn, int stack_size) noexcept
            {
                ppp::threading::BufferswapAllocator* allocator = NULLPTR;
                return YieldContext::Spawn(allocator, context, std::move(spawn), stack_size);
            }
            static bool                                                         Spawn(ppp::threading::BufferswapAllocator* allocator, boost::asio::io_context& context, SpawnHander&& spawn) noexcept
            {
                return YieldContext::Spawn(allocator, context, std::move(spawn), PPP_COROUTINE_STACK_SIZE);
            }
            static bool                                                         Spawn(ppp::threading::BufferswapAllocator* allocator, boost::asio::io_context& context, SpawnHander&& spawn, int stack_size) noexcept
            {
                boost::asio::strand<boost::asio::io_context::executor_type>* strand = NULLPTR;
                return YieldContext::Spawn(allocator, context, strand, std::move(spawn), PPP_COROUTINE_STACK_SIZE);
            }
            static bool                                                         Spawn(ppp::threading::BufferswapAllocator* allocator, boost::asio::io_context& context, boost::asio::strand<boost::asio::io_context::executor_type>* strand, SpawnHander&& spawn)
            {
                return YieldContext::Spawn(allocator, context, strand, std::move(spawn), PPP_COROUTINE_STACK_SIZE);
            }
            static bool                                                         Spawn(ppp::threading::BufferswapAllocator* allocator, boost::asio::io_context& context, boost::asio::strand<boost::asio::io_context::executor_type>* strand, SpawnHander&& spawn, int stack_size) noexcept;

File: ppp/coroutines/YieldContext.h (L126-136)

text 复制代码
        private:
            std::atomic<int>                                                    s_          = 0;
            std::atomic<boost::context::detail::fcontext_t>                     callee_     = NULLPTR;
            std::atomic<boost::context::detail::fcontext_t>                     caller_     = NULLPTR;
            SpawnHander                                                         h_;
            boost::asio::io_context&                                            context_;
            boost::asio::strand<boost::asio::io_context::executor_type>*        strand_;
            int                                                                 stack_size_ = 0;
            std::shared_ptr<Byte>                                               stack_;
            ppp::threading::BufferswapAllocator*                                allocator_  = NULLPTR;
        };

File: main.cpp (L23-37)

cpp 复制代码
#if defined(_WIN32)
#include <windows/ppp/net/proxies/HttpProxy.h>
#include <windows/ppp/tap/TapWindows.h>
#include <windows/ppp/win32/Win32Native.h>
#include <windows/ppp/win32/network/Firewall.h>
#include <windows/ppp/win32/network/NetworkInterface.h>
#else
#include <common/unix/UnixAfx.h>
#if defined(_MACOS)
#include <darwin/ppp/tap/TapDarwin.h>
#else
#include <linux/ppp/tap/TapLinux.h>
#include <linux/ppp/diagnostics/UnixStackTrace.h>
#endif
#endif

File: main.cpp (L200-289)

cpp 复制代码
// Main application class
class PppApplication : public std::enable_shared_from_this<PppApplication>
{
public:
    PppApplication() noexcept;
    virtual ~PppApplication() noexcept;

public:
    // Application entry point
    int                                             Main(int argc, const char* argv[]) noexcept;
    // Clean up resources
    void                                            Dispose() noexcept;
    // Final release
    void                                            Release() noexcept;

public:
    // Singleton access
    static std::shared_ptr<PppApplication>          GetDefault() noexcept;
    // Shutdown handler
    static bool                                     OnShutdownApplication() noexcept;
    // Trigger application shutdown/restart
    static bool                                     ShutdownApplication(bool restart) noexcept;
    // Register shutdown handlers
    static bool                                     AddShutdownApplicationEventHandler() noexcept;

public:
    // Configuration accessors
    std::shared_ptr<AppConfiguration>               GetConfiguration() noexcept;
    std::shared_ptr<VirtualEthernetSwitcher>        GetServer() noexcept;
    std::shared_ptr<VEthernetNetworkSwitcher>       GetClient() noexcept;
    std::shared_ptr<BufferswapAllocator>            GetBufferAllocator() noexcept;

public:
    // Display help information
    void                                            PrintHelpInformation() noexcept;
    // Download IP lists from APNIC
    void                                            PullIPList(const ppp::string& command, bool virr) noexcept;
    // Synchronous IP list download
    int                                             PullIPList(const ppp::string& url, ppp::set<ppp::string>& ips) noexcept;
    // Asynchronous IP list download with callback
    bool                                            PullIPList(const ppp::string& url, const ppp::function<void(int, const ppp::set<ppp::string>&)>& cb) noexcept;
    // Parse command line arguments
    int                                             PreparedArgumentEnvironment(int argc, const char* argv[]) noexcept;

protected:
    // Main tick handler - called every second
    virtual bool                                    OnTick(uint64_t now) noexcept;

private:
    // Load configuration file
    std::shared_ptr<AppConfiguration>               LoadConfiguration(int argc, const char* argv[], ppp::string& path) noexcept;
    // Determine if running in client or server mode
    bool                                            IsModeClientOrServer(int argc, const char* argv[]) noexcept;
    // Parse network interface configuration from arguments
    std::shared_ptr<NetworkInterface>               GetNetworkInterface(int argc, const char* argv[]) noexcept;
    // Parse IP address from command line with validation
    boost::asio::ip::address                        GetNetworkAddress(const char* name, int MIN_PREFIX_ADDRESS, int MAX_PREFIX_ADDRESS, int argc, const char* argv[]) noexcept;
    // Parse IP address with default value
    boost::asio::ip::address                        GetNetworkAddress(const char* name, int MIN_PREFIX_ADDRESS, int MAX_PREFIX_ADDRESS, const char* default_address_string, int argc, const char* argv[]) noexcept;
    // Parse DNS server addresses
    void                                            GetDnsAddresses(ppp::vector<boost::asio::ip::address>& addresses, int argc, const char* argv[]) noexcept;
    // Initialize network environment
    bool                                            PreparedLoopbackEnvironment(const std::shared_ptr<NetworkInterface>& network_interface) noexcept;
    // Print current status and statistics
    bool                                            PrintEnvironmentInformation() noexcept;

private:
    // Start/stop periodic tick handler
    static bool                                     NextTickAlwaysTimeout(bool next) noexcept;
    void                                            ClearTickAlwaysTimeout() noexcept;

private:
    // Get traffic statistics
    bool                                            GetTransmissionStatistics(uint64_t& incoming_traffic, uint64_t& outgoing_traffic, std::shared_ptr<ppp::transmissions::ITransmissionStatistics>& statistics_snapshot) noexcept;

private:
    ConsoleForegroundWindowSize                     console_window_size_last_;       // Previous console size
    std::size_t                                     console_window_buff_size_   = 0; // Console buffer size
    bool                                            client_mode_                = false; // Current mode flag
    bool                                            quic_                       = false; // Original QUIC setting (Windows)
    std::shared_ptr<AppConfiguration>               configuration_;                    // Application configuration
    std::shared_ptr<VirtualEthernetSwitcher>        server_;                          // Server switcher
    std::shared_ptr<VEthernetNetworkSwitcher>       client_;                          // Client switcher
    ppp::string                                     configuration_path_;               // Configuration file path
    std::shared_ptr<NetworkInterface>               network_interface_;                // Network interface config
    std::shared_ptr<Timer>                          timeout_                    = 0;   // Periodic timer
    Stopwatch                                       stopwatch_;                        // Application uptime
    PreventReturn                                   prevent_rerun_;                    // Prevent multiple instances
    ppp::transmissions::ITransmissionStatistics     transmission_statistics_;          // Traffic statistics
};

File: main.cpp (L906-1000)

cpp 复制代码
// Initialize network environment
bool PppApplication::PreparedLoopbackEnvironment(const std::shared_ptr<NetworkInterface>& network_interface) noexcept
{
    std::shared_ptr<AppConfiguration> configuration = GetConfiguration();
    if (NULLPTR == configuration)
    {
        return false;
    }

    std::shared_ptr<boost::asio::io_context> context = Executors::GetDefault();
    if (NULLPTR == context)
    {
        return false;
    }
    else
    {
#if defined(_WIN32)
        // Configure Windows Firewall rules
        ppp::string executable_path = File::GetFullPath(File::RewritePath(ppp::GetFullExecutionFilePath().data()).data());

        ppp::win32::network::Fw::NetFirewallAddApplication(PPP_APPLICATION_NAME, executable_path.data());
        ppp::win32::network::Fw::NetFirewallAddAllApplication(PPP_APPLICATION_NAME, executable_path.data());

        // Client-specific Windows setup
        if (client_mode_)
        {
            // Install paper airplane plugin if needed
            if (network_interface->HostedNetwork && configuration->client.paper_airplane.tcp)
            {
                if (ppp::app::client::lsp::PaperAirplaneController::Install() < 0)
                {
                    return false;
                }
            }

            // Prevent problematic programs from loading LSPs
            ppp::app::client::lsp::PaperAirplaneController::NoLsp();

            // Reset paper airplane controller
            ppp::app::client::lsp::PaperAirplaneController::Reset();
        }
#endif
    }

    bool success = false;
    if (client_mode_)
    {
        std::shared_ptr<VEthernetNetworkSwitcher> ethernet = NULLPTR;
        std::shared_ptr<ITap> tap = NULLPTR;
        do
        {
            // Create TAP device
#if defined(_WIN32)
            tap = ITap::Create(context,
                network_interface->ComponentId,
                Ipep::ToAddressString<ppp::string>(network_interface->IPAddress),
                Ipep::ToAddressString<ppp::string>(network_interface->GatewayServer),
                Ipep::ToAddressString<ppp::string>(network_interface->SubmaskAddress),
                network_interface->LeaseTimeInSeconds,
                network_interface->HostedNetwork,
                Ipep::AddressesTransformToStrings(network_interface->DnsAddresses));
#else
            tap = ITap::Create(context,
                network_interface->ComponentId,
                Ipep::ToAddressString<ppp::string>(network_interface->IPAddress),
                Ipep::ToAddressString<ppp::string>(network_interface->GatewayServer),
                Ipep::ToAddressString<ppp::string>(network_interface->SubmaskAddress),
                network_interface->Promisc,
                network_interface->HostedNetwork,
                Ipep::AddressesTransformToStrings(network_interface->DnsAddresses));
#endif
            if (NULLPTR == tap)
            {
                fprintf(stdout, "%s\r\n", "Open tun/tap driver failure.");
                break;
            }
            else
            {
                fprintf(stdout, "%s\r\n", "Open tun/tap driver success.");
            }

            // Configure TAP device
            tap->BufferAllocator = configuration->GetBufferAllocator();
            if (!tap->Open())
            {
                fprintf(stdout, "%s\r\n", "Listen tun/tap driver failure.");
                break;
            }
            else
            {
                fprintf(stdout, "%s\r\n", "Listen tun/tap driver success.");
            }

            // Create client switcher
            ethernet = ppp::make_shared_object<VEthernetNetworkSwitcher>(context, network_interface->Lwip, network_interface->VNet, configuration->concurrent > 1, configuration);

File: ppp/app/protocol/VirtualEthernetLinklayer.h (L37-66)

text 复制代码
                typedef enum {
                    // INFO
                    PacketAction_INFO                                       = 0x7E,
                    PacketAction_KEEPALIVED                                 = 0x7F,

                    // FRP
                    PacketAction_FRP_ENTRY                                  = 0x20,
                    PacketAction_FRP_CONNECT                                = 0x21,
                    PacketAction_FRP_CONNECTOK                              = 0x22,
                    PacketAction_FRP_PUSH                                   = 0x23,
                    PacketAction_FRP_DISCONNECT                             = 0x24,
                    PacketAction_FRP_SENDTO                                 = 0x25,

                    // VNP
                    PacketAction_LAN                                        = 0x28,
                    PacketAction_NAT                                        = 0x29,
                    PacketAction_SYN                                        = 0x2A,
                    PacketAction_SYNOK                                      = 0x2B,
                    PacketAction_PSH                                        = 0x2C,
                    PacketAction_FIN                                        = 0x2D,
                    PacketAction_SENDTO                                     = 0x2E,
                    PacketAction_ECHO                                       = 0x2F,
                    PacketAction_ECHOACK                                    = 0x30,
                    PacketAction_STATIC                                     = 0x31,
                    PacketAction_STATICACK                                  = 0x32,

                    // MUX
                    PacketAction_MUX                                        = 0x35,
                    PacketAction_MUXON                                      = 0x36,
                }                                                           PacketAction;

File: ppp/app/protocol/VirtualEthernetLinklayer.h (L89-105)

text 复制代码
                virtual bool                                                Run(const ITransmissionPtr& transmission, YieldContext& y) noexcept;
                static int                                                  NewId() noexcept;

            public:
                virtual bool                                                DoLan(const ITransmissionPtr& transmission, uint32_t ip, uint32_t mask, YieldContext& y) noexcept;
                virtual bool                                                DoNat(const ITransmissionPtr& transmission, Byte* packet, int packet_length, YieldContext& y) noexcept;
                virtual bool                                                DoInformation(const ITransmissionPtr& transmission, const VirtualEthernetInformation& information, YieldContext& y) noexcept;
                virtual bool                                                DoPush(const ITransmissionPtr& transmission, int connection_id, Byte* packet, int packet_length, YieldContext& y) noexcept;
                virtual bool                                                DoConnect(const ITransmissionPtr& transmission, int connection_id, const ppp::string& hostname, int port, YieldContext& y) noexcept;
                virtual bool                                                DoConnect(const ITransmissionPtr& transmission, int connection_id, const boost::asio::ip::tcp::endpoint& destinationEP, YieldContext& y) noexcept;
                virtual bool                                                DoConnectOK(const ITransmissionPtr& transmission, int connection_id, Byte error_code, YieldContext& y) noexcept;
                virtual bool                                                DoDisconnect(const ITransmissionPtr& transmission, int connection_id, YieldContext& y) noexcept;
                virtual bool                                                DoEcho(const ITransmissionPtr& transmission, int ack_id, YieldContext& y) noexcept;
                virtual bool                                                DoEcho(const ITransmissionPtr& transmission, Byte* packet, int packet_length, YieldContext& y) noexcept;
                virtual bool                                                DoSendTo(const ITransmissionPtr& transmission, const boost::asio::ip::udp::endpoint& sourceEP, const boost::asio::ip::udp::endpoint& destinationEP, Byte* packet, int packet_length, YieldContext& y) noexcept;
                virtual bool                                                DoStatic(const ITransmissionPtr& transmission, YieldContext& y) noexcept;
                virtual bool                                                DoStatic(const ITransmissionPtr& transmission, Int128 fsid, int session_id, int remote_port, YieldContext& y) noexcept;

File: ppp/app/protocol/VirtualEthernetLinklayer.h (L108-113)

text 复制代码
                virtual bool                                                DoMux(const ITransmissionPtr& transmission, uint16_t vlan, uint16_t max_connections, bool acceleration, YieldContext& y) noexcept;
                virtual bool                                                DoMuxON(const ITransmissionPtr& transmission, uint16_t vlan, uint32_t seq, uint32_t ack, YieldContext& y) noexcept;

            protected:
                virtual bool                                                OnMux(const ITransmissionPtr& transmission, uint16_t vlan, uint16_t max_connections, bool acceleration, YieldContext& y) noexcept { return false; }
                virtual bool                                                OnMuxON(const ITransmissionPtr& transmission, uint16_t vlan, uint32_t seq, uint32_t ack, YieldContext& y) noexcept { return false; }

File: ppp/net/packet/IPFrame.h (L28-56)

text 复制代码
            class IPFrame final {
            public:
                typedef std::shared_ptr<IPFrame>                        IPFramePtr;

            public:
                AddressFamily                                           AddressesFamily;
                UInt32                                                  Destination;
                UInt32                                                  Source;
                Byte                                                    Ttl;
                UInt16                                                  Id;
                Byte                                                    Tos;
                Byte                                                    ProtocolType;
                IPFlags                                                 Flags;
                std::shared_ptr<BufferSegment>                          Payload;
                std::shared_ptr<BufferSegment>                          Options;

            public:
                IPFrame() noexcept
                    : AddressesFamily(AddressFamily::InterNetwork)
                    , Destination(0)
                    , Source(0)
                    , Ttl(IPFrame::DefaultTtl)
                    , Id(0)
                    , Tos(ppp::net::Socket::IsDefaultFlashTypeOfService() ? DefaultFlashTypeOfService() : 0)
                    , ProtocolType(0)
                    , Flags(IPFlags::IP_DF) {

                }

File: ppp/configurations/AppConfiguration.h (L10-161)

text 复制代码
        class AppConfiguration final {
        public:
            struct MappingConfiguration final {
                bool                                                        protocol_tcp_or_udp;
                ppp::string                                                 local_ip;
                int                                                         local_port;
                ppp::string                                                 remote_ip;
                int                                                         remote_port;
            };

            struct RouteConfiguration final {
#if defined(_LINUX)
                ppp::string                                                 nic;
#endif
                uint32_t                                                    ngw;
                ppp::string                                                 path;    
                ppp::string                                                 vbgp;                    
            };

        public:
            int                                                             concurrent;
            int                                                             cdn[2];
            struct {
                ppp::string                                                 public_;
                ppp::string                                                 interface_;
            }                                                               ip;
            struct {
                struct {
                    int                                                     timeout;
                }                                                           inactive;
                struct {
                    int                                                     timeout;
                    int                                                     ttl;
                    bool                                                    turbo;
                    bool                                                    cache;
                    ppp::string                                             redirect;
                }                                                           dns;
                struct {
                    int                                                     port;
                }                                                           listen;
                struct {
                    int                                                     keep_alived[2];
                    bool                                                    dns;
                    bool                                                    quic;
                    bool                                                    icmp;
                    int                                                     aggligator;
                    ppp::unordered_set<ppp::string>                         servers;
                }                                                           static_;
                int                                                         cwnd;
                int                                                         rwnd;
            }                                                               udp;
            struct {
                struct {
                    int                                                     timeout;
                }                                                           inactive;
                struct {
                    int                                                     timeout;
                    int                                                     nexcept;
                }                                                           connect;
                struct {
                    int                                                     port;
                }                                                           listen;
                bool                                                        turbo;
                int                                                         backlog;
                int                                                         cwnd;
                int                                                         rwnd;
                bool                                                        fast_open;
            }                                                               tcp;
            struct {
                struct {
                    int                                                     timeout;
                }                                                           inactive;
                struct {
                    int                                                     timeout;
                }                                                           connect;
                int                                                         congestions;
                int                                                         keep_alived[2];
            }                                                               mux;
            struct {
                struct {
                    int                                                     ws;
                    int                                                     wss;
                }                                                           listen;
                struct {
                    std::string                                             certificate_file;
                    std::string                                             certificate_key_file;
                    std::string                                             certificate_chain_file;
                    std::string                                             certificate_key_password;
                    std::string                                             ciphersuites;
                    bool                                                    verify_peer;
                }                                                           ssl;
                ppp::string                                                 host;
                ppp::string                                                 path;
                struct {
                    std::string                                             error;
                    ppp::map<ppp::string, ppp::string>                      request;
                    ppp::map<ppp::string, ppp::string>                      response;
                }                                                           http;
            }                                                               websocket;
            struct {
                int                                                         kf;
                int                                                         kh;
                int                                                         kl;
                int                                                         kx;
                int                                                         sb;
                ppp::string                                                 protocol;
                ppp::string                                                 protocol_key;
                ppp::string                                                 transport;
                ppp::string                                                 transport_key;
                bool                                                        masked;
                bool                                                        plaintext;
                bool                                                        delta_encode;
                bool                                                        shuffle_data;
            }                                                               key;
            struct {
                int64_t                                                     size;
                ppp::string                                                 path;
            }                                                               vmem;
            struct {
                int                                                         node;
                ppp::string                                                 log;
                bool                                                        subnet;
                bool                                                        mapping;
                ppp::string                                                 backend;
                ppp::string                                                 backend_key;
            }                                                               server;
            struct {
                ppp::string                                                 guid;
                ppp::string                                                 server;
                ppp::string                                                 server_proxy;
                int64_t                                                     bandwidth;
                struct {
                    int                                                     timeout;
                }                                                           reconnections;
#if defined(_WIN32)
                struct {
                    bool                                                    tcp;
                }                                                           paper_airplane;
#endif
                ppp::vector<MappingConfiguration>                           mappings;
                ppp::vector<RouteConfiguration>                             routes;
                struct {
                    int                                                     port;
                    ppp::string                                             bind;
                }                                                           http_proxy;
                struct {
                    int                                                     port;
                    ppp::string                                             bind;
                    ppp::string                                             username;
                    ppp::string                                             password;
                }                                                           socks_proxy;
            }                                                               client;
相关推荐
꧁Q༒ོγ꧂17 小时前
算法详解(一)--算法系列开篇:什么是算法?
开发语言·c++·算法
橘颂TA17 小时前
【剑斩OFFER】算法的暴力美学——力扣:1047 题:删除字符串中的所有相邻重复项
c++·算法·leetcode·职场和发展·结构于算法
汽车通信软件大头兵17 小时前
Autosar--ETAS Isolar能够自由学习啦!
网络·学习·安全·汽车·etas·uds·isoalr
牛老师讲GIS17 小时前
多边形简化讲解:从四大核心算法到 Mapshaper 自动化实战
网络·算法·自动化
早日退休!!!17 小时前
GCC与LLVM编译器深度解析:核心原理与差异对比(小白向)
c++·编辑器
阿钱真强道17 小时前
02-knx 使用 KNX Virtual 调试 调光灯
网络协议·tcp/ip
奋斗者1号17 小时前
SSL/TLS 证书在客户端-服务器通信中的详解
服务器·网络协议·ssl
阿巴~阿巴~17 小时前
帧长、MAC与ARP:解密局域网通信的底层逻辑与工程权衡
linux·服务器·网络·网络协议·tcp/ip·架构·以太网帧
Maggie_ssss_supp17 小时前
Linux-计算机网络
服务器·网络·计算机网络