byteable_derive 0.12.0

Custom derive macros for the byteable crate.
Documentation
# `byteable_derive`

This crate provides custom `derive` macros for the [`byteable`](https://crates.io/crates/byteable) crate.

## Available Derives

### `#[derive(Byteable)]`

The main derive macro that automatically implements byte conversion traits for your types. Supports:

- **Structs** (named, tuple, and unit structs)
- **Enums** (C-like enums with explicit discriminants)
- **Endianness control** via field and type-level attributes
- **Nested byteable types** via `transparent` and `try_transparent` attributes

## Struct Support

### Basic Struct

```rust
use byteable::Byteable;

#[derive(Byteable, Clone, Copy)]
struct Point {
    x: i32,
    y: i32,
}
```

### Struct with Endianness

```rust
use byteable::Byteable;

#[derive(Byteable, Clone, Copy)]
struct NetworkPacket {
    version: u8,
    #[byteable(big_endian)]
    length: u16,
    #[byteable(little_endian)]
    checksum: u32,
}
```

### Field Attributes

- `#[byteable(big_endian)]` - Store field in big-endian byte order
- `#[byteable(little_endian)]` - Store field in little-endian byte order
- `#[byteable(transparent)]` - Use field's raw representation (for nested `Byteable` types)
- `#[byteable(try_transparent)]` - Use field's raw representation with fallible conversion

## Enum Support

The `#[derive(Byteable)]` macro supports C-like enums with explicit discriminants.

### Basic Enum

```rust
use byteable::Byteable;

#[derive(Byteable, Debug, Clone, Copy, PartialEq)]
#[repr(u8)]
enum Status {
    Idle = 0,
    Running = 1,
    Completed = 2,
    Failed = 3,
}
```

### Enum with Endianness

Enums support type-level endianness attributes:

```rust
use byteable::Byteable;

// Little-endian (for file formats)
#[derive(Byteable, Debug, Clone, Copy, PartialEq)]
#[repr(u16)]
#[byteable(little_endian)]
enum FileType {
    Text = 0x1000,
    Binary = 0x2000,
    Archive = 0x3000,
}

// Big-endian (for network protocols)
#[derive(Byteable, Debug, Clone, Copy, PartialEq)]
#[repr(u32)]
#[byteable(big_endian)]
enum HttpStatus {
    Ok = 200,
    NotFound = 404,
    InternalError = 500,
}
```

### Enum Requirements

When deriving `Byteable` for enums, you **must**:

1. Use an explicit repr type: `#[repr(u8)]`, `#[repr(u16)]`, `#[repr(u32)]`, `#[repr(u64)]`,
   `#[repr(i8)]`, `#[repr(i16)]`, `#[repr(i32)]`, or `#[repr(i64)]`
2. Have only unit variants (no fields)
3. Provide explicit discriminant values for all variants
4. Use `TryFromByteArray` for deserialization (returns `EnumFromBytesError` for invalid discriminants)

### Type-Level Attributes for Enums

- `#[byteable(big_endian)]` - Store enum discriminant in big-endian byte order
- `#[byteable(little_endian)]` - Store enum discriminant in little-endian byte order
- No attribute - Use native endianness

### Error Handling

Enums use fallible conversion because not all byte patterns represent valid enum variants:

```rust
use byteable::{Byteable, TryFromByteArray};

#[derive(Byteable, Debug, Clone, Copy, PartialEq)]
#[repr(u8)]
enum Command {
    Start = 1,
    Stop = 2,
}

fn example() -> Result<(), byteable::EnumFromBytesError> {
    // Valid conversion
    let bytes = [1];
    let cmd = Command::try_from_byte_array(bytes)?;
    assert_eq!(cmd, Command::Start);

    // Invalid discriminant returns error
    let invalid = [255];
    let result = Command::try_from_byte_array(invalid);
    assert!(result.is_err());

    Ok(())
}
```

## Advanced Usage

### Nested Structs with Enums

```rust
use byteable::Byteable;

#[derive(Byteable, Debug, Clone, Copy, PartialEq)]
#[repr(u8)]
enum MessageType {
    Data = 1,
    Control = 2,
    Error = 3,
}

#[derive(Byteable, Clone, Copy)]
struct Message {
    #[byteable(try_transparent)]
    msg_type: MessageType,
    #[byteable(big_endian)]
    sequence: u32,
    payload: [u8; 16],
}
```

### Sparse Discriminants

Enums with non-sequential discriminants work perfectly:

```rust
use byteable::Byteable;

#[derive(Byteable, Debug, Clone, Copy, PartialEq)]
#[repr(u8)]
enum Priority {
    Low = 1,
    Medium = 5,
    High = 10,
    Critical = 100,
}

// Only defined discriminants (1, 5, 10, 100) are valid
// All other values return errors during conversion
```

## See Also

For comprehensive documentation and examples, see the main [`byteable` crate documentation](https://docs.rs/byteable).