Skip to content

Commit

Permalink
ci: run udp-attack tests
Browse files Browse the repository at this point in the history
  • Loading branch information
camshaft committed Jun 30, 2023
1 parent e7dfb0c commit bc92f73
Show file tree
Hide file tree
Showing 5 changed files with 141 additions and 0 deletions.
41 changes: 41 additions & 0 deletions .github/workflows/qns.yml
Original file line number Diff line number Diff line change
Expand Up @@ -667,3 +667,44 @@ jobs:
name: "perf / report"
status: "success"
url: "${{ steps.s3.outputs.URL }}"

attack:
runs-on: ubuntu-latest
needs: [s2n-quic-qns]
strategy:
matrix:
attack: ["udp"]

steps:
- uses: actions/checkout@v3

- uses: actions-rs/[email protected]
id: toolchain
with:
toolchain: stable
profile: minimal
override: true

- uses: actions/download-artifact@v3
with:
name: s2n-quic-qns-debug

- name: Run cargo build
working-directory: tools/${{ matrix.attack }}-attack
run: cargo build --release

- name: Start client
working-directory: tools/${{ matrix.attack }}-attack
run: |
./target/release/${{ matrix.attack }}-attack localhost:4433 &
- name: Start server
shell: bash
run: |
chmod +x ./s2n-quic-qns-debug
# disable exiting on errors to capture the timeout status
set +e
timeout 5m ./s2n-quic-qns-debug interop server --port 4433
set -e
# `timeout` exits with `124` if the time limit was reached
[[ "$?" == "124" ]] || exit 1
1 change: 1 addition & 0 deletions quic/s2n-quic-qns/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@ fn main() {
Ok(args) => {
if let Err(error) = args.run() {
eprintln!("Error: {error:?}");
std::process::exit(1);
}
}
Err(error) => {
Expand Down
13 changes: 13 additions & 0 deletions tools/udp-attack/Cargo.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
[package]
name = "udp-attack"
version = "0.1.0"
edition = "2021"
publish = false

[dependencies]
clap = { version = "4", features = ["derive"] }
tokio = { version = "1", features = ["full"] }
rand = "0.8"

[workspace]
members = ["."]
2 changes: 2 additions & 0 deletions tools/udp-attack/rust-toolchain
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
[toolchain]
channel = "1.68.0"
84 changes: 84 additions & 0 deletions tools/udp-attack/src/main.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
// SPDX-License-Identifier: Apache-2.0

use clap::Parser;
use core::time::Duration;
use rand::prelude::*;
use std::net::SocketAddr;
use tokio::{net::UdpSocket, task::JoinSet};

type Error = Box<dyn std::error::Error + Send + Sync + 'static>;
type Result<T = (), E = Error> = core::result::Result<T, E>;

fn main() -> Result {
Args::parse().run()
}

#[derive(Debug, Parser)]
struct Args {
/// The local address to bind the workers to
#[arg(long, default_value = "0.0.0.0:0")]
local_address: String,

/// The number of workers to run concurrently
#[arg(long, default_value_t = 100)]
workers: u16,

/// The maximum packet size to generate
#[arg(long, default_value_t = 1500)]
mtu: u16,

/// The target of the UDP endpoint
#[arg(default_value = "localhost:443")]
address: String,
}

impl Args {
#[tokio::main]
async fn run(self) -> Result {
let remote_address = tokio::net::lookup_host(&self.address)
.await?
.next()
.unwrap();

let local_address: SocketAddr = self.local_address.parse()?;

let mut set = JoinSet::new();

for _ in 0..self.workers {
set.spawn(worker(remote_address, local_address, self.mtu as _));
}

while set.join_next().await.is_some() {}

Ok(())
}
}

async fn sleep_rand() {
let ms = thread_rng().gen_range(0..50);
if ms > 0 {
tokio::time::sleep(Duration::from_millis(ms)).await;
}
}

async fn worker(remote_address: SocketAddr, local_address: SocketAddr, mtu: usize) -> Result<()> {
let socket = UdpSocket::bind(local_address).await?;

let mut payload = vec![];

loop {
let burst = thread_rng().gen_range(1..100);
for _ in 0..burst {
generate_payload(&mut payload, mtu);
let _ = socket.send_to(&payload, remote_address).await;
}
sleep_rand().await;
}
}

fn generate_payload(payload: &mut Vec<u8>, mtu: usize) {
let len = thread_rng().gen_range(0..=mtu);
payload.resize(len, 0);
thread_rng().fill_bytes(payload);
}

0 comments on commit bc92f73

Please sign in to comment.