Author: Ľubor Pačaj (xpacajl00)
Language: C (C17)
Assignment See ASSIGNMENT for details
License: GPL-3.0-only (see LICENSE)
This project implements a reliable, ordered byte-stream transfer protocol over UDP. It provides a single executable ipk-rdt that works as a client or server, supports IPv4 and IPv6, and is designed to tolerate loss, duplication, and reordering.
- Recommended: reference VM
x86_64-linuxwith the Nix devShellcor any pretty much any recent Unix/Unix-like system (Linux flavors, BSD flavors, macOS) with: - Standard build tools:
makeandgcc.
make NixDevShellName #prints dev shell name
nix develop --refresh "git+https://git.fit.vutbr.cz/NESFIT/dev-envs.git#c" #optional
make
This produces the executable ipk-rdt in the repository root.
./ipk-rdt -s -p PORT [-a ADDRESS] [-o OUTPUT] [-w TIMEOUT] [-h | --help]
./ipk-rdt -c -a HOST -p PORT [-i INPUT] [-w TIMEOUT] [-h | --help]
Examples:
./ipk-rdt -s -p 9000 -o output_file
./ipk-rdt -c -a 127.0.0.1 -p 9000 -i input_file
./ipk-rdt -s -p 6767
printf 'IPK\n' | ./ipk-rdt -c -a 127.0.0.1 -p 6767
The implementation has been tested and confirmed working on the following platforms:
| OS | Architecture |
|---|---|
| GNU/Linux Ubuntu 24.04 | x86-64, arm64 |
| GNU/Linux Debian 13 and Devuan 5 (university server Merlin) | x86-64 |
| FreeBSD 14.3 (university server Eva) | x86-64 |
| macOS Tahoe 26 | arm64 |
The implementation should work on most Unix and Unix-like operating systems. The code uses
standard POSIX socket APIs and avoids Linux-specific extensions. The only
Linux-specific feature is tc netem support in the automated tests — those tests are skipped
automatically on non-Linux systems.
- Loopback — client and server on the same machine (
127.0.0.1/::1) - Kolejnet — room-to-room transfer within the dormitory network (best tested speed: ~400Mb/s)
- Cloud to local — transfer between a cloud instance and a local device and vice versa
Custom header (packed), total 13 bytes:
| Field | Size | Description |
|---|---|---|
type |
1 B | Packet type (SYN, SYN_ACK, DATA, DATA_ACK, FIN, FIN_ACK) |
connect_id |
4 B | Connection identifier (random per session) |
seq_number |
4 B | Sequence number (per data segment) |
data_len |
2 B | Payload length in bytes |
checksum |
2 B | 16-bit checksum over header + payload |
Maximum UDP payload is 1200 bytes, so the data payload is up to 1187 bytes (UDP payload - Custom header)
- Client sends
SYN, server repliesSYN_ACKwithconnect_id. - Data transfer uses
DATAandDATA_ACK. - Client finishes with
FIN, server repliesFIN_ACK.
Mermaid sequence diagram:
sequenceDiagram
participant C as Client
participant S as Server
C->>S: SYN (connect_id)
S-->>C: SYN_ACK
loop Data transfer
C->>S: DATA(seq, payload)
S-->>C: DATA_ACK(seq)
end
C->>S: FIN
S-->>C: FIN_ACK
- Sliding window with size
WINDOW_SIZE(64 selected as sweet spot). - Selective-repeat style acknowledgements (per segment).
- Receiver buffers out-of-order segments within the window and writes in order.
- Duplicate segments are acknowledged and ignored.
-w TIMEOUTis the maximum inactivity interval before failure.- Internal retransmission interval is fixed (see
RETRANSMIT_T_MSin code). - Lack of protocol progress for
TIMEOUTseconds terminates the session.
- Selective acknowledgements: per-segment ACKs simplify loss handling and allow out-of-order arrival.
- Fixed MTU-friendly payload size: 1200 bytes total UDP payload to reduce fragmentation risk.
- Simple checksum: 16-bit checksum (adapted from real TCP protocol) over header and payload for corruption detection.
- Connection ID: random 32-bit ID avoids mixing packets between sessions.
- SYN_ACK FIN_ACK 10 time retransmissions: ensures better robustness against packet loss without excessive delay (just 9 more 13B UDP payload packets each discarded in optimal network conditions).
Automated tests are provided in tests/test.sh and are run via the Makefile targets:
make test
make test-long
make test-debug
make test-full #both long and debug
- What is tested: IPv4/IPv6 transfers, file/stdin/stdout combinations, 1B/1MB/10MB/empty inputs, invalid arguments, varios netem loss/delay/duplication scenarios and 1 server with 10 simultanious clients.
- Why: to verify ordering, reliability, correct CLI behavior, and proper timeout handling.
- How: each run compares SHA-256 of input vs output and checks non-zero exit codes for invalid arguments.
- Environment: Designed for Linux with
tcandroot privilagesavailable; on macOS, netem tests are skipped. - Inputs/Expected/Actual:
- Input: random 1B, 1MB, 10MB, and empty streams.
- Expected: output hash matches input; invalid args return non-zero exit code.
- Actual: test script prints test category and
PASS/FAILper test case with elapsed time of the test, for example:PASS ipv4_file_to_file_1m (1.235s)
- Single client per server run; no concurrent clients (tested that in this scenerao only one client is served).
- No congestion control or adaptive retransmission logic (not needed in assignment).
- Retransmission interval is fixed.
- Netem-based tests require Linux
tcand root privileges.
- UDP-only transport with custom reliability layer.
- IPv4 and IPv6 support.
- File and stdin/stdout transfers.
- Ordered, reliable delivery with per-segment acknowledgements.
- Explicit connection establishment and teardown.
- Checksums and connection identifiers.
- Graceful handling of
SIGINTandSIGTERMwith proper resource cleanup.
- The automated test suite and related test scripts were developed with assistance from an AI tool to maximize coverage and ensure reproducibility.
- The AI was used as a supplementary learning, explanation resource for networking concepts (for example, sliding window protocol design, function arguments, return values...) and as an advisor for suitability of my design choices (most of the time recommending me bad ones that I refused to use xd).
- AI contributed to drafting and polishing this README.
- Ľubor Pačaj: IPK-Project1 Source: https://git.fit.vutbr.cz/xpacajl00/IPK-Project1 (private) [Created 5 April 2026]
- RFC 793/RFC 9293 Transmission Control Protocol [Accessed 16 March 2026].
- Klassen, F. & Turner, A.: Checksum calculation logic adapted from
checksum.cin the tcpreplay project (GPL-3.0). Source: https://github.com/appneta/tcpreplay [Accessed 16 March 2026].