#network-communication #silkroad #packet #packets #networking #client-server

skrillax-packet

Packet definition to serialize and deserialize to and from frames for Silkroad Online packets

3 releases (breaking)

0.3.0 Oct 27, 2024
0.2.0 Jun 22, 2024
0.1.0 Apr 28, 2024

#1587 in Network programming

Download history 16/week @ 2024-09-14 31/week @ 2024-09-21 34/week @ 2024-09-28 3/week @ 2024-10-05 1/week @ 2024-10-12 160/week @ 2024-10-26 12/week @ 2024-11-02

173 downloads per month
Used in 2 crates

MIT license

105KB
1.5K SLoC

skrillax-packet

Crates.io Docs.rs

skrillax-packet is part of the skrillax-network family of crates for handling the network part of communication between a Silkroad Online client and/or server. This crate specifically deals with defining packets to be used in a connection, as well as going from / to individual frames.

Documentation

For documentation, please see the docs.rs page.

License

Like the rest of the skrillax-network crates, this crate is licensed under the MIT license.


lib.rs:

This crate mainly provides one trait: [Packet]. While you can implement it yourself, you might as well use the derive macro to derive it instead (which requires the derive feature).

#[derive(Packet)]
#[packet(opcode = 0x5001)]
struct MyPacket {
    content: String,
}

The rest of this crate focuses around converting a [Packet] into a [SilkroadFrame], or vice-versa. This currently takes a small detour through using either an [IncomingPacket] or [OutgoingPacket], depending on the direction. This is done because we often first need to apply some kind of transformation to the frames, before we can easily turn them into structs representing the packet. This would include combining multiple massive frames into one large buffer as well as decrypting the content of frames to figure out their opcodes. Thus, the chain goes something like this, in a simplified way. To turn a packet into frames: myPacket.serialize().as_frames(context) To turn frames into a packet: IncomingPacket::from_frames(frames, context).try_into_packet::<MyPacket>()

However, this does require a bit more than just the [Packet] implementation. Either you need to implement the [TryFromPacket] and [AsPacket] traits yourself, or you need to implement/derive skrillax_serde::Serialize, skrillax_serde::Deserialize, and skrillax_serde::ByteSize from the skrillax_serde crate. With these, [AsPacket] and [TryFromPacket] are automatically implemented for you. They are necessary to serialize/deserialize the packet content into bytes, which can be sent using the frames.

Derive

The derive macro currently has three options, for all the options the trait provides:

#[derive(Packet)]
#[packet(opcode = 0x5001, encrypted = true, massive = false)]
struct MyPacket {
    content: String,
}

encrypted and massive are false by default and are mutually exclusive. opcode is a required attribute, this is also considered the ID of a packet. The name is automatically considered to be the structure's name.

Dependencies

~1.2–2.1MB
~43K SLoC