cobs_codec_rs 1.0.0

Consistent Overhead Byte Stuffing (COBS) and COBS/R codec: no_std, zero-dependency, for zero-free framing of serial and packet byte streams.
Documentation
  • Coverage
  • 100%
    34 out of 34 items documented4 out of 21 items with examples
  • Size
  • Source code size: 50.55 kB This is the summed size of all the files inside the crates.io package for this release.
  • Documentation size: 420.26 kB This is the summed size of all files generated by rustdoc for all configured targets
  • Ø build duration
  • this release: 2s Average build duration of successful builds.
  • all releases: 4s Average build duration of successful builds in releases after 2024-10-23.
  • Links
  • Homepage
  • firechip/cobs_codec_rs
    1 0 0
  • crates.io
  • Dependencies
  • Versions
  • Owners
  • ajsb85 github:firechip:packages

cobs_codec_rs

CI crates.io docs.rs License: MIT

#![no_std], dependency-free Consistent Overhead Byte Stuffing (COBS) and COBS/R for Rust — the Rust member of the Firechip COBS family (alongside the Dart cobs_codec and the Kotlin cobs_codec_kt), verified byte-identical against the shared conformance vectors.

COBS encodes an arbitrary byte sequence into one that contains no zero (0x00) byte, at a small and predictable cost: at most one extra byte per 254 bytes, plus one. That makes a single 0x00 a reliable packet delimiter for serial/UART, USB, TCP and other byte streams — ideal for embedded and robotics protocols.

Features

  • Basic COBS and COBS/R (Reduced) encode/decode.
  • no_std and zero dependencies — the core encode/decode work on caller-provided slices, allocating nothing.
  • alloc conveniences (*_to_vec) and a streaming FrameDecoder for 0x00-delimited serial links, behind the default std/alloc features.
  • const fn size helpers (max_encoded_len, encoding_overhead) for compile-time buffer sizing.

Install

[dependencies]
cobs_codec_rs = "1.0"

# no_std, no allocator:
# cobs_codec_rs = { version = "1.0", default-features = false }

Usage

use cobs_codec_rs::{cobs, cobsr};

// With alloc (default):
let encoded = cobs::encode_to_vec(&[0x11, 0x22, 0x00, 0x33]);
assert_eq!(encoded, [0x03, 0x11, 0x22, 0x02, 0x33]); // no 0x00
assert_eq!(cobs::decode_to_vec(&encoded).unwrap(), [0x11, 0x22, 0x00, 0x33]);

// COBS/R often saves the trailing overhead byte:
assert_eq!(cobsr::encode_to_vec(b"12345"), b"51234"); // same length as input

no_std, into a fixed buffer:

use cobs_codec_rs::{cobs, max_encoded_len};

let src = [0x11, 0x00, 0x22];
let mut buf = [0u8; max_encoded_len(3)];
let n = cobs::encode(&src, &mut buf);
assert_eq!(&buf[..n], &[0x02, 0x11, 0x02, 0x22]);

Reading a delimited serial stream (needs alloc):

use cobs_codec_rs::framing::{frame_to_vec, FrameDecoder};

let mut rx = FrameDecoder::new().max_frame_len(4096);
// `chunk` is any &[u8] read from the link; chunks need not align with frames.
# let chunk = frame_to_vec(&[0x01, 0x02]);
rx.push(&chunk, |frame| match frame {
    Ok(packet) => { /* handle packet */ }
    Err(err)   => { /* corrupt frame; keep receiving */ let _ = err; }
});

Overhead

COBS overhead is data-independent: at most ⌈n / 254⌉ extra bytes for n input bytes (and always ≥ 1). Compare escape-based schemes (PPP/SLIP), whose worst case doubles the packet.

Background

Stuart Cheshire and Mary Baker, "Consistent Overhead Byte Stuffing", IEEE/ACM Transactions on Networking, Vol. 7, No. 2, April 1999. COBS/R is a variant by Craig McQueen.

License

MIT © 2026 Alexander Salas Bastidas (Firechip). See LICENSE.