diff --git a/rust/bt-bass/.gitignore b/rust/bt-bass/.gitignore
new file mode 100644
index 0000000..ada8be9
--- /dev/null
+++ b/rust/bt-bass/.gitignore
@@ -0,0 +1,14 @@
+# Generated by Cargo
+# will have compiled files and executables
+debug/
+target/
+
+# Remove Cargo.lock from gitignore if creating an executable, leave it for libraries
+# More information here https://doc.rust-lang.org/cargo/guide/cargo-toml-vs-cargo-lock.html
+Cargo.lock
+
+# These are backup files generated by rustfmt
+**/*.rs.bk
+
+# MSVC Windows builds of rustc generate these, which store debugging information
+*.pdb
\ No newline at end of file
diff --git a/rust/bt-bass/Cargo.toml b/rust/bt-bass/Cargo.toml
new file mode 100644
index 0000000..15d0ece
--- /dev/null
+++ b/rust/bt-bass/Cargo.toml
@@ -0,0 +1,11 @@
+[package]
+name = "bt-bass"
+version = "0.0.1"
+edition = "2021"
+license = "BSD-2-Clause"
+
+# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
+
+[dependencies]
+bt-common = { path = "../bt-common" }
+thiserror = "1.0"
\ No newline at end of file
diff --git a/rust/bt-bass/LICENSE b/rust/bt-bass/LICENSE
new file mode 100644
index 0000000..e5de3c8
--- /dev/null
+++ b/rust/bt-bass/LICENSE
@@ -0,0 +1,24 @@
+Copyright 2023 Google LLC
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+   * Redistributions of source code must retain the above copyright
+notice, this list of conditions and the following disclaimer.
+   * Redistributions in binary form must reproduce the above
+copyright notice, this list of conditions and the following disclaimer
+in the documentation and/or other materials provided with the
+distribution.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/rust/bt-bass/PATENTS b/rust/bt-bass/PATENTS
new file mode 100644
index 0000000..3a21f11
--- /dev/null
+++ b/rust/bt-bass/PATENTS
@@ -0,0 +1,22 @@
+Additional IP Rights Grant (Patents)
+
+"This implementation" means the copyrightable works distributed by
+Google as part of this crate
+
+Google hereby grants to you a perpetual, worldwide, non-exclusive,
+no-charge, royalty-free, irrevocable (except as stated in this
+section) patent license to make, have made, use, offer to sell, sell,
+import, transfer, and otherwise run, modify and propagate the contents
+of this implementation, where such license applies only to
+those patent claims, both currently owned by Google and acquired in
+the future, licensable by Google that are necessarily infringed by
+this implementation. This grant does not include claims that would be
+infringed only as a consequence of further modification of this
+implementation. If you or your agent or exclusive licensee institute
+or order or agree to the institution of patent litigation or any other
+patent enforcement activity against any entity (including a
+cross-claim or counterclaim in a lawsuit) alleging that this
+implementation constitutes direct or contributory patent
+infringement, or inducement of patent infringement, then any patent
+rights granted to you under this License for this implementation
+shall terminate as of the date such litigation is filed.
diff --git a/rust/bt-bass/src/lib.rs b/rust/bt-bass/src/lib.rs
new file mode 100644
index 0000000..b77366b
--- /dev/null
+++ b/rust/bt-bass/src/lib.rs
@@ -0,0 +1,5 @@
+// Copyright 2023 Google LLC
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+pub mod types;
diff --git a/rust/bt-bass/src/types.rs b/rust/bt-bass/src/types.rs
new file mode 100644
index 0000000..33dcb5f
--- /dev/null
+++ b/rust/bt-bass/src/types.rs
@@ -0,0 +1,1231 @@
+// Copyright 2023 Google LLC
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+use bt_common::packet_encoding::{Decodable, Encodable, Error as PacketError};
+use bt_common::generic_audio::metadata_ltv::*;
+use bt_common::core::{AdvertisingSetId, PaInterval};
+
+const ADDRESS_BYTE_SIZE: usize = 6;
+const NUM_SUBGROUPS_BYTE_SIZE: usize = 1;
+const PA_SYNC_BYTE_SIZE: usize = 1;
+const SOURCE_ID_BYTE_SIZE: usize = 1;
+
+type SourceId = u8;
+
+/// Broadcast_ID is a 3-byte data on the wire.
+/// See Broadcast Audio Scan Service (BASS) spec v1.0 Table 3.5 for details.
+#[derive(Debug, PartialEq)]
+pub struct BroadcastId(u32);
+
+impl BroadcastId {
+    // On the wire, Broadcast_ID is transported in 3 bytes.
+    const BYTE_SIZE: usize = 3;
+}
+
+impl TryFrom<u32> for BroadcastId {
+    type Error = PacketError;
+
+    fn try_from(value: u32) -> Result<Self, Self::Error> {
+        const MAX_VALUE: u32 = 0xFFFFFF;
+        if value > MAX_VALUE {
+            return Err(PacketError::InvalidParameter(format!("Broadcast ID cannot exceed 3 bytes")));
+        }
+        Ok(BroadcastId(value))
+    }
+}
+
+impl Decodable for BroadcastId {
+    type Error = PacketError;
+
+    fn decode(buf: &[u8]) -> core::result::Result<(Self, usize), Self::Error> {
+        if buf.len() != Self::BYTE_SIZE {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+
+        let padded_bytes = [buf[0], buf[1], buf[2], 0x00];
+        Ok((BroadcastId(u32::from_le_bytes(padded_bytes)), Self::BYTE_SIZE))
+    }
+}
+
+impl Encodable for BroadcastId {
+    type Error = PacketError;
+
+    fn encode(&self, buf: &mut [u8]) -> core::result::Result<(), Self::Error> {
+        if buf.len() < self.encoded_len() {
+            return Err(PacketError::BufferTooSmall);
+        }
+        // Since 3-byte value is being fit into u32, we ignore the most significant byte.
+        buf[0..3].copy_from_slice(&self.0.to_le_bytes()[0..3]);
+        Ok(())
+    }
+
+    fn encoded_len(&self) -> core::primitive::usize {
+        Self::BYTE_SIZE
+    }
+}
+
+/// Broadcast Audio Scan Control Point characteristic opcode as defined in
+/// Broadcast Audio Scan Service spec v1.0 Section 3.1.
+#[repr(u8)]
+#[derive(Debug, PartialEq)]
+pub enum ControlPointOpcode {
+    RemoteScanStopped = 0x00,
+    RemoteScanStarted = 0x01,
+    AddSource = 0x02,
+    ModifySource = 0x03,
+    SetBroadcastCode = 0x04,
+    RemoveSource = 0x05,
+}
+
+impl ControlPointOpcode {
+    const BYTE_SIZE: usize = 1;
+}
+
+impl TryFrom<u8> for ControlPointOpcode {
+    type Error = PacketError;
+
+    fn try_from(value: u8) -> Result<Self, Self::Error> {
+        let val = match value {
+            0x00 => Self::RemoteScanStopped,
+            0x01 => Self::RemoteScanStarted,
+            0x02 => Self::AddSource,
+            0x03 => Self::ModifySource,
+            0x04 => Self::SetBroadcastCode,
+            0x05 => Self::RemoveSource,
+            _ => return Err(PacketError::OutOfRange),
+        };
+        Ok(val)
+    }
+}
+
+/// Trait for objects that represent a Broadcast Audio Scan Control Point characteristic.
+/// When written by a client, the Broadcast Audio Scan Control Point characteristic is defined as an
+/// 8-bit enumerated value, known as the opcode, followed by zero or more parameter octets.
+/// The opcode represents the operation that would be performed in the Broadcast Audio Scan Service server.
+/// See BASS spec v1.0 Section 3.1 for details.
+pub trait ControlPointOperation {
+    // Returns the expected opcode for this operation.
+    fn opcode() -> ControlPointOpcode;
+
+    // Given the raw encoded value of the opcode, verifies it and returns the equivalent ControlPointOpcode object.
+    fn check_opcode(raw_value: u8) -> Result<ControlPointOpcode, PacketError> {
+        let expected = Self::opcode();
+        let got = ControlPointOpcode::try_from(raw_value)?;
+        if got != expected {
+            return Err(PacketError::InvalidParameter(format!("got opcode {got:?}, expected {expected:?}")));
+        }
+        Ok(got)
+    }
+}
+
+/// See BASS spec v1.0 Section 3.1.1.2 for details.
+#[derive(Debug, PartialEq)]
+pub struct RemoteScanStoppedOperation;
+
+impl ControlPointOperation for RemoteScanStoppedOperation {
+    fn opcode() -> ControlPointOpcode {
+        ControlPointOpcode::RemoteScanStopped
+    }
+}
+
+impl Decodable for RemoteScanStoppedOperation {
+    type Error = PacketError;
+
+    fn decode(buf: &[u8]) -> core::result::Result<(Self, usize), Self::Error> {
+        if buf.len() < ControlPointOpcode::BYTE_SIZE {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+        let _ = Self::check_opcode(buf[0])?;
+        Ok((RemoteScanStoppedOperation, ControlPointOpcode::BYTE_SIZE))
+    }
+}
+
+impl Encodable for RemoteScanStoppedOperation {
+    type Error = PacketError;
+
+    fn encode(&self, buf: &mut [u8]) -> core::result::Result<(), Self::Error> {
+        if buf.len() < self.encoded_len() {
+            return Err(PacketError::BufferTooSmall);
+        }
+        buf[0] = Self::opcode() as u8;
+        Ok(())
+    }
+
+    fn encoded_len(&self) -> core::primitive::usize {
+        ControlPointOpcode::BYTE_SIZE
+    }
+}
+
+/// See BASS spec v1.0 Section 3.1.1.3 for details.
+#[derive(Debug, PartialEq)]
+pub struct RemoteScanStartedOperation;
+
+impl ControlPointOperation for RemoteScanStartedOperation {
+    fn opcode() -> ControlPointOpcode {
+        ControlPointOpcode::RemoteScanStarted
+    }
+}
+
+impl Decodable for RemoteScanStartedOperation {
+    type Error = PacketError;
+
+    fn decode(buf: &[u8]) -> core::result::Result<(Self, usize), Self::Error> {
+        if buf.len() < ControlPointOpcode::BYTE_SIZE {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+        let _ = Self::check_opcode(buf[0])?;
+        Ok((RemoteScanStartedOperation, ControlPointOpcode::BYTE_SIZE))
+    }
+}
+
+impl Encodable for RemoteScanStartedOperation {
+    type Error = PacketError;
+
+    fn encode(&self, buf: &mut [u8]) -> core::result::Result<(), Self::Error> {
+        if buf.len() < self.encoded_len() {
+            return Err(PacketError::BufferTooSmall);
+        }
+        buf[0] = Self::opcode() as u8;
+        Ok(())
+    }
+
+    fn encoded_len(&self) -> core::primitive::usize {
+        ControlPointOpcode::BYTE_SIZE
+    }
+}
+
+/// See BASS spec v1.0 Section 3.1.1.4 for details.
+#[derive(Debug, PartialEq)]
+pub struct AddSourceOperation {
+    advertiser_address_type: AddressType,
+    // Address in little endian.
+    advertiser_address: [u8; ADDRESS_BYTE_SIZE],
+    advertising_sid: AdvertisingSetId,
+    broadcast_id: BroadcastId,
+    pa_sync: PaSync,
+    pa_interval: PaInterval,
+    subgroups: Vec<BigSubgroup>,
+}
+
+impl AddSourceOperation {
+    const MIN_PACKET_SIZE: usize = ControlPointOpcode::BYTE_SIZE + AddressType::BYTE_SIZE + ADDRESS_BYTE_SIZE + AdvertisingSetId::BYTE_SIZE +
+        BroadcastId::BYTE_SIZE + PA_SYNC_BYTE_SIZE + PaInterval::BYTE_SIZE + NUM_SUBGROUPS_BYTE_SIZE;
+
+    pub fn new(
+            address_type: AddressType,
+            advertiser_address: [u8; ADDRESS_BYTE_SIZE],
+            sid: u8,
+            broadcast_id: u32,
+            pa_sync: PaSync,
+            pa_interval: u16,
+            subgroups: Vec<BigSubgroup>,
+        ) -> Self {
+            AddSourceOperation {
+                advertiser_address_type: address_type,
+                advertiser_address,
+                advertising_sid: AdvertisingSetId(sid),
+                broadcast_id: BroadcastId(broadcast_id),
+                pa_sync,
+                pa_interval: PaInterval(pa_interval),
+                subgroups,
+            }
+        }
+}
+
+impl ControlPointOperation for AddSourceOperation {
+    fn opcode() -> ControlPointOpcode {
+        ControlPointOpcode::AddSource
+    }
+}
+
+impl Decodable for AddSourceOperation {
+    type Error = PacketError;
+
+    fn decode(buf: &[u8]) -> core::result::Result<(Self, usize), Self::Error> {
+        if buf.len() < Self::MIN_PACKET_SIZE {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+
+        let _ = Self::check_opcode(buf[0])?;
+        let advertiser_address_type = AddressType::try_from(buf[1])?;
+        let mut advertiser_address = [0; ADDRESS_BYTE_SIZE];
+        advertiser_address.clone_from_slice(&buf[2..8]);
+        let advertising_sid = AdvertisingSetId(buf[8]);
+        let broadcast_id = BroadcastId::decode(&buf[9..12])?.0;
+        let pa_sync = PaSync::try_from(buf[12])?;
+        let pa_interval = PaInterval(u16::from_le_bytes(buf[13..15].try_into().unwrap()));
+        let num_subgroups = buf[15] as usize;
+        let mut subgroups = Vec::new();
+
+        let mut idx: usize = 16;
+        for _i in 0..num_subgroups {
+            if buf.len() <= idx {
+                return Err(PacketError::UnexpectedDataLength);
+            }
+            let decoded = BigSubgroup::decode(&buf[idx..])?;
+            subgroups.push(decoded.0);
+            idx += decoded.1;
+        }
+        Ok((Self{
+            advertiser_address_type,
+            advertiser_address,
+            advertising_sid,
+            broadcast_id,
+            pa_sync,
+            pa_interval,
+            subgroups,
+        }, idx))
+    }
+}
+
+impl Encodable for AddSourceOperation {
+    type Error = PacketError;
+
+    fn encode(&self, buf: &mut [u8]) -> core::result::Result<(), Self::Error> {
+        if buf.len() < self.encoded_len() {
+            return Err(PacketError::BufferTooSmall);
+        }
+
+        buf[0] = Self::opcode() as u8;
+        buf[1] = self.advertiser_address_type as u8;
+        buf[2..8].copy_from_slice(&self.advertiser_address);
+        buf[8] = self.advertising_sid.0;
+        self.broadcast_id.encode(&mut buf[9..12])?;
+        buf[12] = self.pa_sync as u8;
+        buf[13..15].copy_from_slice(&self.pa_interval.0.to_le_bytes());
+        buf[15] = self
+            .subgroups
+            .len()
+            .try_into()
+            .map_err(|_| PacketError::InvalidParameter("Num_Subgroups".to_string()))?;
+        let mut idx = 16;
+        for s in &self.subgroups {
+            s.encode(&mut buf[idx..])?;
+            idx += s.encoded_len();
+        }
+        Ok(())
+    }
+
+    fn encoded_len(&self) -> core::primitive::usize {
+        Self::MIN_PACKET_SIZE + self
+            .subgroups
+            .iter()
+            .fold(0, |acc, g| acc + g.encoded_len())
+    }
+}
+
+/// See Broadcast Audio Scan Service spec v1.0 Section 3.1.1.5 for details.
+#[derive(Debug, PartialEq)]
+pub struct ModifySourceOperation {
+    source_id: SourceId,
+    pa_sync: PaSync,
+    pa_interval: PaInterval,
+    subgroups: Vec<BigSubgroup>,
+}
+
+impl ModifySourceOperation {
+    const MIN_PACKET_SIZE: usize = ControlPointOpcode::BYTE_SIZE + SOURCE_ID_BYTE_SIZE + PA_SYNC_BYTE_SIZE + PaInterval::BYTE_SIZE + NUM_SUBGROUPS_BYTE_SIZE;
+
+    pub fn new(
+        source_id: SourceId,
+        pa_sync: PaSync,
+        pa_interval: u16,
+        subgroups: Vec<BigSubgroup>,
+    ) -> Self {
+        ModifySourceOperation {
+            source_id,
+            pa_sync,
+            pa_interval: PaInterval(pa_interval),
+            subgroups,
+        }
+    }
+}
+
+impl ControlPointOperation for ModifySourceOperation {
+    fn opcode() -> ControlPointOpcode {
+        ControlPointOpcode::ModifySource
+    }
+}
+
+impl Decodable for ModifySourceOperation {
+    type Error = PacketError;
+
+    // Min size includes Source_ID, PA_Sync, PA_Interval, and Num_Subgroups params.
+    fn decode(buf: &[u8]) -> core::result::Result<(Self, usize), Self::Error> {
+        if buf.len() < Self::MIN_PACKET_SIZE {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+        let _ = Self::check_opcode(buf[0])?;
+        let source_id = buf[1];
+        let pa_sync = PaSync::try_from(buf[2])?;
+        let pa_interval = PaInterval(u16::from_le_bytes(buf[3..5].try_into().unwrap()));
+        let num_subgroups = buf[5] as usize;
+        let mut subgroups = Vec::new();
+
+        let mut idx = 6;
+        for _i in 0..num_subgroups {
+            if buf.len() < idx + BigSubgroup::MIN_PACKET_SIZE {
+                return Err(PacketError::UnexpectedDataLength);
+            }
+            let decoded = BigSubgroup::decode(&buf[idx..])?;
+            subgroups.push(decoded.0);
+            idx += decoded.1;
+        }
+        Ok((Self{
+            source_id,
+            pa_sync,
+            pa_interval,
+            subgroups,
+        }, idx))
+    }
+}
+
+impl Encodable for ModifySourceOperation {
+    type Error = PacketError;
+
+    fn encode(&self, buf: &mut [u8]) -> core::result::Result<(), Self::Error> {
+        if buf.len() < self.encoded_len() {
+            return Err(PacketError::BufferTooSmall);
+        }
+
+        buf[0] = Self::opcode() as u8;
+        buf[1] = self.source_id;
+        buf[2] = self.pa_sync as u8;
+        buf[3..5].copy_from_slice(&self.pa_interval.0.to_le_bytes());
+        buf[5] = self
+            .subgroups
+            .len()
+            .try_into()
+            .map_err(|_| PacketError::InvalidParameter("Num_Subgroups".to_string()))?;
+        let mut idx = 6;
+        for s in &self.subgroups {
+            s.encode(&mut buf[idx..])?;
+            idx += s.encoded_len();
+        }
+        Ok(())
+    }
+
+    fn encoded_len(&self) -> core::primitive::usize {
+        Self::MIN_PACKET_SIZE +
+            self
+                .subgroups
+                .iter()
+                .fold(0, |acc, g| acc + g.encoded_len())
+    }
+}
+
+/// See Broadcast Audio Scan Service spec v1.0 Section 3.1.1.6 for details.
+#[derive(Debug, PartialEq)]
+pub struct SetBroadcastCodeOperation {
+    source_id: SourceId,
+    broadcast_code: [u8; 16],
+}
+
+impl SetBroadcastCodeOperation {
+    const BROADCAST_CODE_LEN: usize = 16;
+    const PACKET_SIZE: usize = ControlPointOpcode::BYTE_SIZE + SOURCE_ID_BYTE_SIZE + Self::BROADCAST_CODE_LEN;
+
+    pub fn new(source_id: SourceId, broadcast_code: [u8; 16]) -> Self {
+        SetBroadcastCodeOperation{ source_id, broadcast_code }
+    }
+}
+
+impl ControlPointOperation for SetBroadcastCodeOperation {
+    fn opcode() -> ControlPointOpcode {
+        ControlPointOpcode::SetBroadcastCode
+    }
+}
+
+impl Decodable for SetBroadcastCodeOperation {
+    type Error = PacketError;
+
+    // Min size includes Source_ID, PA_Sync, PA_Interval, and Num_Subgroups params.
+    fn decode(buf: &[u8]) -> core::result::Result<(Self, usize), Self::Error> {
+        if buf.len() < Self::PACKET_SIZE {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+        let _ = Self::check_opcode(buf[0])?;
+        let source_id = buf[1];
+        let mut broadcast_code = [0; Self::BROADCAST_CODE_LEN];
+        broadcast_code.copy_from_slice(&buf[2..2+Self::BROADCAST_CODE_LEN]);
+        Ok((Self{
+            source_id,
+            broadcast_code,
+        }, Self::PACKET_SIZE))
+    }
+}
+
+impl Encodable for SetBroadcastCodeOperation {
+    type Error = PacketError;
+
+    fn encode(&self, buf: &mut [u8]) -> core::result::Result<(), Self::Error> {
+        if buf.len() < self.encoded_len() {
+            return Err(PacketError::BufferTooSmall);
+        }
+
+        buf[0] = Self::opcode() as u8;
+        buf[1] = self.source_id;
+        buf[2..2+Self::BROADCAST_CODE_LEN].copy_from_slice(&self.broadcast_code);
+        Ok(())
+    }
+
+    fn encoded_len(&self) -> core::primitive::usize {
+        Self::PACKET_SIZE
+    }
+}
+
+/// See Broadcast Audio Scan Service spec v1.0 Section 3.1.1.7 for details.
+#[derive(Debug, PartialEq)]
+pub struct RemoveSourceOperation(SourceId);
+
+impl RemoveSourceOperation {
+    const PACKET_SIZE: usize = ControlPointOpcode::BYTE_SIZE + SOURCE_ID_BYTE_SIZE;
+
+    pub fn new(source_id: SourceId) -> Self {
+        RemoveSourceOperation(source_id)
+    }
+}
+
+impl ControlPointOperation for RemoveSourceOperation {
+    fn opcode() -> ControlPointOpcode {
+        ControlPointOpcode::RemoveSource
+    }
+}
+
+impl Decodable for RemoveSourceOperation {
+    type Error = PacketError;
+
+    // Min size includes Source_ID, PA_Sync, PA_Interval, and Num_Subgroups params.
+    fn decode(buf: &[u8]) -> core::result::Result<(Self, usize), Self::Error> {
+        if buf.len() < Self::PACKET_SIZE {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+        let _ = Self::check_opcode(buf[0])?;
+        let source_id = buf[1];
+        Ok((RemoveSourceOperation(source_id), Self::PACKET_SIZE))
+    }
+}
+
+impl Encodable for RemoveSourceOperation {
+    type Error = PacketError;
+
+    fn encode(&self, buf: &mut [u8]) -> core::result::Result<(), Self::Error> {
+        if buf.len() < self.encoded_len() {
+            return Err(PacketError::BufferTooSmall);
+        }
+
+        buf[0] = Self::opcode() as u8;
+        buf[1] = self.0;
+        Ok(())
+    }
+
+    fn encoded_len(&self) -> core::primitive::usize {
+        Self::PACKET_SIZE
+    }
+}
+
+#[repr(u8)]
+#[derive(Clone, Copy, Debug, PartialEq)]
+pub enum PaSync {
+    DoNotSync = 0x00,
+    SyncPastAvailable = 0x01,
+    SyncPastUnavailable = 0x02,
+}
+
+impl TryFrom<u8> for PaSync {
+    type Error = PacketError;
+
+    fn try_from(value: u8) -> Result<Self, Self::Error> {
+        match value {
+            0x00 => Ok(Self::DoNotSync),
+            0x01 => Ok(Self::SyncPastAvailable),
+            0x02 => Ok(Self::SyncPastUnavailable),
+            _ => Err(PacketError::OutOfRange),
+        }
+    }
+}
+
+#[derive(Debug, PartialEq)]
+pub struct BigSubgroup {
+    // 4-octet bitfield. Bit 0-30 = BIS_index[1-31]
+    // 0x00000000: 0b0 = Do not synchronize to BIS_index[x]
+    // 0xxxxxxxxx: 0b1 = Synchronize to BIS_index[x]
+    // 0xFFFFFFFF: means No preference if used in BroadcastAudioScanControlPoint,
+    //             Failed to sync if used in BroadcastReceiveState.
+    bis_sync_bitfield: u32,
+    metadata: Metadata,
+}
+
+impl BigSubgroup {
+    const BIS_SYNC_BYTE_SIZE: usize = 4;
+    const METADATA_LENGTH_BYTE_SIZE: usize = 1;
+
+    const MIN_PACKET_SIZE: usize = Self::BIS_SYNC_BYTE_SIZE + Self::METADATA_LENGTH_BYTE_SIZE;
+    const BIS_SYNC_NO_PREFERENCE: u32 = 0xFFFFFFFF;
+
+    pub fn new(bis_sync_bitfield: Option<u32>) -> Self {
+        Self {
+            bis_sync_bitfield: bis_sync_bitfield.unwrap_or(Self::BIS_SYNC_NO_PREFERENCE),
+            metadata: vec![],
+        }
+    }
+
+    pub fn with_metadata(self, metadata: Metadata) -> Self {
+        Self {
+            bis_sync_bitfield: self.bis_sync_bitfield,
+            metadata,
+        }
+    }
+}
+
+impl Decodable for BigSubgroup {
+    type Error = PacketError;
+
+    fn decode(buf: &[u8]) -> core::result::Result<(Self, usize), Self::Error> {
+        if buf.len() < BigSubgroup::MIN_PACKET_SIZE {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+        let bis_sync = u32::from_le_bytes(buf[0..4].try_into().unwrap());
+        let metadata_len = buf[4] as usize;
+        let mut metadata = Vec::new();
+
+        let mut start_idx = 5;
+        if buf.len() < start_idx + metadata_len {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+
+        while start_idx < 5 + metadata_len {
+            let (data, len) = Metadatum::decode(&buf[start_idx..]).map_err(|e| PacketError::InvalidParameter(format!("{e}")))?;
+            metadata.push(data);
+            start_idx += len;
+        }
+        if start_idx != 5 + metadata_len {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+        Ok((BigSubgroup { bis_sync_bitfield: bis_sync, metadata }, start_idx))
+    }
+}
+
+impl Encodable for BigSubgroup {
+    type Error = PacketError;
+
+    fn encode(&self, buf: &mut [u8]) -> core::result::Result<(), Self::Error> {
+        if buf.len() < self.encoded_len() {
+            return Err(PacketError::BufferTooSmall);
+        }
+
+        buf[0..4].copy_from_slice(&self.bis_sync_bitfield.to_le_bytes());
+        let metadata_len = self
+            .metadata
+            .iter()
+            .fold(0, |acc, m| acc + m.encoded_len())
+            .try_into()
+            .map_err(|_| PacketError::InvalidParameter("Metadata".to_string()))?;
+        buf[4] = metadata_len;
+        let mut next_idx = 5;
+        for m in &self.metadata {
+            m.encode(&mut buf[next_idx..]).map_err(|e| PacketError::InvalidParameter(format!("{e}")))?;
+            next_idx += m.encoded_len();
+        }
+        Ok(())
+    }
+
+    fn encoded_len(&self) -> core::primitive::usize {
+        Self::MIN_PACKET_SIZE + self.metadata.iter().map(Encodable::encoded_len).sum::<usize>()
+    }
+}
+
+/// See Broadcast Audio Scan Service spec v1.0 Table 3.5 for details.
+#[repr(u8)]
+#[derive(Clone, Copy, Debug, PartialEq)]
+pub enum AddressType {
+    // Public Device Address or Public Identity Address.
+    Public = 0x00,
+    // Random Device Address or Random (static) Identity Address.
+    Random = 0x01,
+}
+
+impl AddressType {
+    const BYTE_SIZE: usize = 1;
+}
+
+impl TryFrom<u8> for AddressType {
+    type Error = PacketError;
+
+    fn try_from(value: u8) -> Result<Self, Self::Error> {
+        match value {
+            0x00 => Ok(Self::Public),
+            0x01 => Ok(Self::Random),
+            _ => Err(PacketError::OutOfRange),
+        }
+    }
+}
+
+/// Broadcast Receive State characteristic as defined in
+/// Broadcast Audio Scan Service spec v1.0 Section 3.2.
+/// The Broadcast Receive State characteristic is used by the server to expose information
+/// about a Broadcast Source.
+#[derive(Debug, PartialEq)]
+pub struct BroadcastReceiveState {
+    source_id: SourceId,
+    source_address_type: AddressType,
+    // Address in little endian.
+    source_address: [u8; ADDRESS_BYTE_SIZE],
+    source_adv_sid: AdvertisingSetId,
+    broadcast_id: BroadcastId,
+    pa_sync_state: PaSyncState,
+    // Represents BIG_Encryption param with optional Bad_Code param.
+    big_encryption: EncryptionStatus,
+    subgroups: Vec<BigSubgroup>,
+}
+
+impl BroadcastReceiveState {
+    const MIN_PACKET_SIZE: usize = SOURCE_ID_BYTE_SIZE + AddressType::BYTE_SIZE + ADDRESS_BYTE_SIZE + AdvertisingSetId::BYTE_SIZE +
+        BroadcastId::BYTE_SIZE + PA_SYNC_BYTE_SIZE + EncryptionStatus::MIN_PACKET_SIZE + NUM_SUBGROUPS_BYTE_SIZE;
+}
+
+impl Decodable for BroadcastReceiveState {
+    type Error = PacketError;
+
+    fn decode(buf: &[u8]) -> core::result::Result<(Self, usize), Self::Error> {
+        if buf.len() < Self::MIN_PACKET_SIZE {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+
+        let source_id = buf[0];
+        let source_address_type = AddressType::try_from(buf[1])?;
+        let mut source_address = [0; ADDRESS_BYTE_SIZE];
+        source_address.clone_from_slice(&buf[2..8]);
+        let source_adv_sid = AdvertisingSetId(buf[8]);
+        let broadcast_id = BroadcastId::decode(&buf[9..12])?.0;
+        let pa_sync_state = PaSyncState::try_from(buf[12])?;
+
+        let decoded = EncryptionStatus::decode(&buf[13..])?;
+        let big_encryption = decoded.0;
+        let mut idx = 13 + decoded.1;
+        if buf.len() <= idx {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+        let num_subgroups = buf[idx] as usize;
+        let mut subgroups = Vec::new();
+        idx += 1;
+        for _i in 0..num_subgroups {
+            if buf.len() <= idx {
+                return Err(PacketError::UnexpectedDataLength);
+            }
+            let (subgroup, consumed) = BigSubgroup::decode(&buf[idx..])?;
+            subgroups.push(subgroup);
+            idx += consumed;
+        }
+        Ok((BroadcastReceiveState{
+            source_id,
+            source_address_type,
+            source_address,
+            source_adv_sid,
+            broadcast_id,
+            pa_sync_state,
+            big_encryption,
+            subgroups,
+        }, idx))
+    }
+}
+
+impl Encodable for BroadcastReceiveState {
+    type Error = PacketError;
+
+    fn encode(&self, buf: &mut [u8]) -> core::result::Result<(), Self::Error> {
+        if buf.len() < self.encoded_len() {
+            return Err(PacketError::BufferTooSmall);
+        }
+
+        buf[0] = self.source_id;
+        buf[1] = self.source_address_type as u8;
+        buf[2..8].copy_from_slice(&self.source_address);
+        buf[8] = self.source_adv_sid.0;
+        self.broadcast_id.encode(&mut buf[9..12])?;
+        buf[12] = self.pa_sync_state as u8;
+        let mut idx = 13 + self.big_encryption.encoded_len();
+        self.big_encryption.encode(&mut buf[13..idx])?;
+        buf[idx] = self
+            .subgroups
+            .len()
+            .try_into()
+            .map_err(|_| PacketError::InvalidParameter("Metadata".to_string()))?;
+        idx += 1;
+        for s in &self.subgroups {
+            s.encode(&mut buf[idx..])?;
+            idx += s.encoded_len();
+        }
+        Ok(())
+    }
+
+    fn encoded_len(&self) -> core::primitive::usize {
+        // Length including Source_ID, Source_Address_Type, Source_Address, Source_Adv_SID, Broadcast_ID, PA_Sync_State, BIG_Encryption, Bad_Code,
+        // Num_Subgroups and subgroup-related params.
+        SOURCE_ID_BYTE_SIZE + AddressType::BYTE_SIZE
+            + self.source_address.len()
+            + AdvertisingSetId::BYTE_SIZE
+            + self.broadcast_id.encoded_len()
+            + PA_SYNC_BYTE_SIZE
+            + self.big_encryption.encoded_len()
+            + NUM_SUBGROUPS_BYTE_SIZE
+            + self
+                .subgroups
+                .iter()
+                .map(Encodable::encoded_len).sum::<usize>()
+    }
+}
+
+#[derive(Clone, Copy, Debug, PartialEq)]
+#[repr(u8)]
+pub enum PaSyncState {
+    NotSynced = 0x00,
+    SyncInfoRequest = 0x01,
+    Synced = 0x02,
+    FailedToSync = 0x03,
+    NoPast = 0x04,
+}
+
+impl TryFrom<u8> for PaSyncState {
+    type Error = PacketError;
+
+    fn try_from(value: u8) -> Result<Self, Self::Error> {
+        match value {
+            0x00 => Ok(Self::NotSynced),
+            0x01 => Ok(Self::SyncInfoRequest),
+            0x02 => Ok(Self::Synced),
+            0x03 => Ok(Self::FailedToSync),
+            0x04 => Ok(Self::NoPast),
+            _ => Err(PacketError::OutOfRange),
+        }
+    }
+}
+
+/// Represents BIG_Encryption and Bad_Code params from BASS spec v.1.0 Table 3.9.
+#[derive(Clone, Copy, Debug, PartialEq)]
+pub enum EncryptionStatus {
+    NotEncrypted,
+    BroadcastCodeRequired,
+    Decrypting,
+    BadCode([u8; 16]),
+}
+
+impl EncryptionStatus {
+    // Should at least include the BIG_Encryption enum value which is 1 byte long.
+    const MIN_PACKET_SIZE: usize = 1;
+
+    // Returns the u8 value that represents the status of encryption
+    // as described for BIG_Encryption parameter.
+    fn raw_value(self) -> u8 {
+        match self {
+            EncryptionStatus::NotEncrypted => 0x00,
+            EncryptionStatus::BroadcastCodeRequired => 0x01,
+            EncryptionStatus::Decrypting => 0x02,
+            EncryptionStatus::BadCode(_) => 0x03,
+        }
+    }
+}
+
+impl Decodable for EncryptionStatus {
+    type Error = PacketError;
+
+    fn decode(buf: &[u8]) -> core::result::Result<(Self, usize), Self::Error> {
+        if buf.len() < 1 {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+        match buf[0] {
+            0x00 => Ok((Self::NotEncrypted, 1)),
+            0x01 => Ok((Self::BroadcastCodeRequired, 1)),
+            0x02 => Ok((Self::Decrypting, 1)),
+            0x03 => {
+                if buf.len() < 17 {
+                    return Err(PacketError::UnexpectedDataLength);
+                }
+                Ok((Self::BadCode(buf[1..17].try_into().unwrap()), 17))
+            }
+            _ => Err(PacketError::OutOfRange),
+        }
+    }
+}
+
+impl Encodable for EncryptionStatus {
+    type Error = PacketError;
+
+    fn encode(&self, buf: &mut [u8]) -> core::result::Result<(), Self::Error> {
+        if buf.len() < self.encoded_len() {
+            return Err(PacketError::BufferTooSmall);
+        }
+
+        buf[0] = self.raw_value();
+        match self {
+            EncryptionStatus::BadCode(code) => buf[1..17].copy_from_slice(code),
+            _ => {}
+        }
+        Ok(())
+    }
+
+    fn encoded_len(&self) -> core::primitive::usize {
+        match self {
+            // For Bad_Code value, we also have to encrypt the incorrect
+            // 16-octet Broadcast_Code. See BASS spec Table 3.9.
+            EncryptionStatus::BadCode(_) => 1 + 16,
+            _ => 1,
+        }
+    }
+}
+
+#[cfg(test)]
+mod tests {
+    use super::*;
+
+    #[test]
+    fn broadcast_id() {
+        let id = BroadcastId(0x000A0B0C);
+
+        assert_eq!(id.encoded_len(), 3);
+        let mut buf = vec![0; id.encoded_len()];
+        let _ = id.encode(&mut buf[..]).expect("should have succeeded");
+
+        let bytes = vec![0x0C, 0x0B, 0x0A];
+        assert_eq!(buf, bytes);
+
+        let (got, bytes) = BroadcastId::decode(&bytes).expect("should succeed");
+        assert_eq!(got, id);
+        assert_eq!(bytes, BroadcastId::BYTE_SIZE);
+        let got = BroadcastId::try_from(u32::from_le_bytes([0x0C, 0x0B, 0x0A, 0x00])).expect("should succeed");
+        assert_eq!(got, id);
+    }
+
+    #[test]
+    fn encryption_status_enum() {
+        let not_encrypted = EncryptionStatus::NotEncrypted;
+        let encrypted = EncryptionStatus::BroadcastCodeRequired;
+        let decrypting = EncryptionStatus::Decrypting;
+        let bad_code = EncryptionStatus::BadCode([
+            0x16, 0x15, 0x14, 0x13, 0x12, 0x11, 0x10, 0x09, 0x08, 0x07, 0x06, 0x05, 0x04, 0x03,
+            0x02, 0x01,
+        ]);
+
+        assert_eq!(0x00, not_encrypted.raw_value());
+        assert_eq!(0x01, encrypted.raw_value());
+        assert_eq!(0x02, decrypting.raw_value());
+        assert_eq!(0x03, bad_code.raw_value());
+    }
+
+    #[test]
+    fn encryption_status() {
+        // Encoding not encrypted status.
+        let not_encrypted = EncryptionStatus::NotEncrypted;
+        assert_eq!(not_encrypted.encoded_len(), 1);
+        let mut buf = vec![0; not_encrypted.encoded_len()];
+        let _ = not_encrypted.encode(&mut buf[..]).expect("should not fail");
+
+        let bytes = vec![0x00];
+        assert_eq!(buf, bytes);
+
+        // Decoding not encrypted.
+        let decoded = EncryptionStatus::decode(&bytes).expect("should succeed");
+        assert_eq!(decoded.0, not_encrypted);
+        assert_eq!(decoded.1 ,1);
+
+        // Encoding bad code status with code.
+        let bad_code = EncryptionStatus::BadCode([
+            0x16, 0x15, 0x14, 0x13, 0x12, 0x11, 0x10, 0x09, 0x08, 0x07, 0x06, 0x05, 0x04, 0x03,
+            0x02, 0x01,
+        ]);
+        assert_eq!(bad_code.encoded_len(), 17);
+        let mut buf = vec![0; bad_code.encoded_len()];
+        let _ = bad_code.encode(&mut buf[..]).expect("should not fail");
+
+        let bytes = vec![
+            0x03, 0x16, 0x15, 0x14, 0x13, 0x12, 0x11, 0x10, 0x09, 0x08, 0x07, 0x06, 0x05, 0x04,
+            0x03, 0x02, 0x01
+        ];
+        assert_eq!(buf, bytes);
+
+        // Deocoding bad code statsu with code.
+        let decoded = EncryptionStatus::decode(&bytes).expect("should succeed");
+        assert_eq!(decoded.0, bad_code);
+        assert_eq!(decoded.1 ,17);
+    }
+
+    #[test]
+    fn invalid_encryption_status() {
+        // Cannot encode into empty buffer.
+        let not_encrypted = EncryptionStatus::NotEncrypted;
+        let mut buf = vec![];
+        let _ = not_encrypted.encode(&mut buf[..]).expect_err("should fail");
+
+        // Not enough buffer space for encoding.
+        let bad_code = EncryptionStatus::BadCode([
+            0x16, 0x15, 0x14, 0x13, 0x12, 0x11, 0x10, 0x09, 0x08, 0x07, 0x06, 0x05, 0x04, 0x03,
+            0x02, 0x01,
+        ]);
+        let mut buf = vec![0; 1];
+        let _ = bad_code.encode(&mut buf[..]).expect_err("should fail");
+
+        // Cannot decode empty buffer.
+        let buf = vec![];
+        let _ = EncryptionStatus::decode(&buf).expect_err("should fail");
+
+        // Bad code status with no code.
+        let buf = vec![0x03];
+        let _ = EncryptionStatus::decode(&buf).expect_err("should fail");
+    }
+
+    #[test]
+    fn remote_scan_stopped() {
+        // Encoding remote scan stopped.
+        let stopped = RemoteScanStoppedOperation;
+        assert_eq!(stopped.encoded_len(), 1);
+        let mut buf = vec![0u8; stopped.encoded_len()];
+        stopped.encode(&mut buf[..]).expect("shoud succeed");
+
+        let bytes = vec![0x00];
+        assert_eq!(buf, bytes);
+
+        // Decoding remote scan stopped.
+        let decoded = RemoteScanStoppedOperation::decode(&bytes).expect("should succeed");
+        assert_eq!(decoded.0, stopped);
+        assert_eq!(decoded.1 ,1);
+    }
+
+    #[test]
+    fn remote_scan_started() {
+        // Encoding remote scan started.
+        let started = RemoteScanStartedOperation;
+        assert_eq!(started.encoded_len(), 1);
+        let mut buf = vec![0u8; started.encoded_len()];
+        started.encode(&mut buf[..]).expect("shoud succeed");
+
+        let bytes = vec![0x01];
+        assert_eq!(buf, vec![0x01]);
+
+        // Decoding remote scan started.
+        let decoded = RemoteScanStartedOperation::decode(&bytes).expect("should succeed");
+        assert_eq!(decoded.0, started);
+        assert_eq!(decoded.1 ,1);
+    }
+
+    #[test]
+    fn add_source_without_subgroups() {
+        // Encoding operation with no subgroups.
+        let op = AddSourceOperation::new(
+            AddressType::Public,
+            [0x04, 0x10, 0x00, 0x00, 0x00, 0x00],
+            1,
+            0x11,
+            PaSync::DoNotSync,
+            PaInterval::UNKNOWN_VALUE,
+            vec![],
+        );
+        assert_eq!(op.encoded_len(), 16);
+        let mut buf = vec![0u8; op.encoded_len()];
+        op.encode(&mut buf[..]).expect("shoud succeed");
+
+        let bytes = vec![
+            0x02, 0x00, 0x04, 0x10, 0x00, 0x00, 0x00, 0x00,
+            0x01, 0x11, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x00,
+        ];
+        assert_eq!(buf, bytes);
+
+        // Decoding operation with no subgroups.
+        let decoded = AddSourceOperation::decode(&bytes).expect("should succeed");
+        assert_eq!(decoded.0, op);
+        assert_eq!(decoded.1 ,16);
+    }
+
+    #[test]
+    fn add_source_with_subgroups() {
+        // Encoding operation with subgroups.
+        let subgroups = vec![BigSubgroup::new(None).with_metadata(vec![
+            Metadatum::PreferredAudioContexts(ContextType::MEDIA | ContextType::GAME), // encoded_len = 4
+            Metadatum::ProgramInfo("test".to_string()), // encoded_len = 6
+        ])];
+        let op = AddSourceOperation::new(
+            AddressType::Random,
+            [0x04, 0x10, 0x00, 0x00, 0x00, 0x00],
+            1,
+            0x11,
+            PaSync::SyncPastAvailable,
+            PaInterval::UNKNOWN_VALUE,
+            subgroups,
+        );
+        assert_eq!(op.encoded_len(), 31); // 16 for minimum params and params 15 for the subgroup.
+        let mut buf = vec![0u8; op.encoded_len()];
+        op.encode(&mut buf[..]).expect("shoud succeed");
+
+        let bytes = vec![
+            0x02, 0x01, 0x04, 0x10, 0x00, 0x00, 0x00, 0x00, 0x01, 0x11, 0x00, 0x00, 0x01, 0xFF, 0xFF, 0x01,
+            0xFF, 0xFF, 0xFF, 0xFF, 0x0A, // BIS_Sync, Metdata_Length
+            0x03, 0x01, 0x0C, 0x00, // Preferred_Audio_Contexts metdataum
+            0x05, 0x03, 0x74, 0x65, 0x73, 0x074, // Program_Info metadatum
+        ];
+        assert_eq!(buf, bytes);
+
+        // Decoding operation with subgroups.
+        let decoded = AddSourceOperation::decode(&bytes).expect("should succeed");
+        assert_eq!(decoded.0, op);
+        assert_eq!(decoded.1, 31);
+    }
+
+    #[test]
+    fn modify_source_without_subgroups() {
+        // Encoding operation with no subgroups.
+        let op = ModifySourceOperation::new(
+            0x0A,
+            PaSync::SyncPastAvailable,
+            0x1004,
+            vec![],
+        );
+        assert_eq!(op.encoded_len(), 6);
+        let mut buf = vec![0u8; op.encoded_len()];
+        op.encode(&mut buf[..]).expect("shoud succeed");
+
+        let bytes = vec![0x03, 0x0A, 0x01, 0x04, 0x10, 0x00];
+        assert_eq!(buf, bytes);
+
+        // Decoding operation with no subgroups.
+        let decoded = ModifySourceOperation::decode(&bytes).expect("should succeed");
+        assert_eq!(decoded.0, op);
+        assert_eq!(decoded.1, 6);
+    }
+
+    #[test]
+    fn modify_source_with_subgroups() {
+        // Encoding operation with subgroups.
+        let subgroups = vec![
+            BigSubgroup::new(None).with_metadata(vec![Metadatum::ParentalRating(Rating::AllAge)]), // encoded_len = 8
+            BigSubgroup::new(Some(0x000000FE))
+                .with_metadata(vec![Metadatum::BroadcastAudioImmediateRenderingFlag]), // encoded_len = 7
+        ];
+        let op = ModifySourceOperation::new(
+            0x0B,
+            PaSync::DoNotSync,
+            PaInterval::UNKNOWN_VALUE,
+            subgroups,
+        );
+        assert_eq!(op.encoded_len(), 21); // 6 for minimum params and params 15 for two subgroups.
+        let mut buf = vec![0u8; op.encoded_len()];
+        op.encode(&mut buf[..]).expect("shoud succeed");
+
+        let bytes = vec![
+            0x03, 0x0B, 0x00, 0xFF, 0xFF, 0x02,
+            0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0x02, 0x06, 0x01, // First subgroup.
+            0xFE, 0x00, 0x00, 0x00, 0x02, 0x01, 0x09, // Second subgroup.
+        ];
+        assert_eq!(buf, bytes);
+
+        // Decoding operation with subgroups.
+        let decoded = ModifySourceOperation::decode(&bytes).expect("should succeed");
+        assert_eq!(decoded.0, op);
+        assert_eq!(decoded.1, 21);
+    }
+
+    #[test]
+    fn set_broadcast_code() {
+        // Encoding.
+        let op = SetBroadcastCodeOperation::new(
+            0x0A,
+            [
+                0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x10, 0x11, 0x12, 0x13, 0x14,
+                0x15, 0x16,
+            ],
+        );
+        assert_eq!(op.encoded_len(), 18);
+        let mut buf = vec![0; op.encoded_len()];
+        op.encode(&mut buf[..]).expect("should succeed");
+
+        let bytes = vec![
+            0x04, 0x0A, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x10, 0x11, 0x12,
+            0x13, 0x14, 0x15, 0x16
+        ];
+        assert_eq!(buf, bytes);
+
+        // Decoding.
+        let decoded = SetBroadcastCodeOperation::decode(&bytes).expect("should succeed");
+        assert_eq!(decoded.0, op);
+        assert_eq!(decoded.1, 18);
+    }
+
+    #[test]
+    fn remove_source() {
+        // Encoding.
+        let op = RemoveSourceOperation::new(0x0A);
+        assert_eq!(op.encoded_len(), 2);
+        let mut buf = vec![0; op.encoded_len()];
+        op.encode(&mut buf[..]).expect("should succeed");
+
+        let bytes = vec![0x05, 0x0A];
+        assert_eq!(buf, bytes);
+
+        // Decoding.
+        let decoded = RemoveSourceOperation::decode(&bytes).expect("should succeed");
+        assert_eq!(decoded.0, op);
+        assert_eq!(decoded.1, 2);
+    }
+
+    #[test]
+    fn broadcast_receive_state_without_subgroups() {
+        // Encoding.
+        let state = BroadcastReceiveState {
+            source_id: 0x01,
+            source_address_type: AddressType::Public,
+            source_address: [0x0F, 0x0E, 0x0D, 0x0C, 0x0B, 0x0A],
+            source_adv_sid: AdvertisingSetId(0x01),
+            broadcast_id: BroadcastId(0x00010203),
+            pa_sync_state: PaSyncState::Synced,
+            big_encryption: EncryptionStatus::BadCode([0x16, 0x15, 0x14, 0x13, 0x12, 0x11, 0x10, 0x09, 0x08, 0x7, 0x06, 0x05, 0x04, 0x03, 0x02, 0x01]),
+            subgroups: vec![],
+        };
+        assert_eq!(state.encoded_len(), 31);
+        let mut buf = vec![0; state.encoded_len()];
+        state.encode(&mut buf[..]).expect("should succeed");
+
+        let bytes = vec![
+            0x01, 0x00, 0x0F, 0x0E, 0x0D, 0x0C, 0x0B, 0x0A, 0x01, 0x03, 0x02, 0x01, 0x02,
+            0x03, 0x16, 0x15, 0x14, 0x13, 0x12, 0x11, 0x10, 0x09, 0x08, 0x07, 0x06, 0x05, 0x04, 0x03, 0x02, 0x01,  // Bad_Code with the code.
+            0x00,
+        ];
+        assert_eq!(buf, bytes);
+
+        // Decoding.
+        let decoded = BroadcastReceiveState::decode(&bytes).expect("should succeed");
+        assert_eq!(decoded.0, state);
+        assert_eq!(decoded.1, 31);
+    }
+
+    #[test]
+    fn broadcast_receive_state_with_subgroups() {
+        // Encoding
+        let state = BroadcastReceiveState {
+            source_id: 0x01,
+            source_address_type: AddressType::Random,
+            source_address: [0x0F, 0x0E, 0x0D, 0x0C, 0x0B, 0x0A],
+            source_adv_sid: AdvertisingSetId(0x01),
+            broadcast_id: BroadcastId(0x00010203),
+            pa_sync_state: PaSyncState::NotSynced,
+            big_encryption: EncryptionStatus::NotEncrypted,
+            subgroups: vec![
+                BigSubgroup::new(None).with_metadata(vec![Metadatum::ParentalRating(Rating::AllAge)]), // encoded_len = 8
+            ],
+        };
+        assert_eq!(state.encoded_len(), 23);
+        let mut buf = vec![0; state.encoded_len()];
+        state.encode(&mut buf[..]).expect("should succeed");
+
+        let bytes = vec![
+            0x01, 0x01, 0x0F, 0x0E, 0x0D, 0x0C, 0x0B, 0x0A, 0x01, 0x03, 0x02, 0x01, 0x00,
+            0x00, 0x01,  // 1 Subgroup.
+            0xFF, 0xFF, 0xFF, 0xFF, 0x03, 0x02, 0x06, 0x01, // Subgroup.
+        ];
+        assert_eq!(buf, bytes);
+
+        // Decoding.
+        let decoded = BroadcastReceiveState::decode(&bytes).expect("should succeed");
+        assert_eq!(decoded.0, state);
+        assert_eq!(decoded.1, 23);
+
+    }
+}
diff --git a/rust/bt-common/Cargo.toml b/rust/bt-common/Cargo.toml
index 0e131a5..0b1c788 100644
--- a/rust/bt-common/Cargo.toml
+++ b/rust/bt-common/Cargo.toml
@@ -7,3 +7,7 @@
 [dependencies.uuid]
 version = "1.4.1"
 features = ["macro-diagnostics"]
+
+[dependencies]
+bitflags = "2.4.0"
+thiserror = "1.0"
diff --git a/rust/bt-common/src/core.rs b/rust/bt-common/src/core.rs
new file mode 100644
index 0000000..16bb6ec
--- /dev/null
+++ b/rust/bt-common/src/core.rs
@@ -0,0 +1,68 @@
+// Copyright 2023 Google LLC
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+use crate::packet_encoding::{Encodable, Error as PacketError};
+
+/// Represents the Advertising Set ID which is 1 byte long.
+/// Follows little endian encoding.
+#[derive(Debug, Clone, Copy, PartialEq)]
+pub struct AdvertisingSetId(pub u8);
+
+impl AdvertisingSetId {
+    // Byte size if this is to be encoded.
+    pub const BYTE_SIZE: usize = 1;
+}
+
+/// Represents the SyncInfo Interval value which is 2 bytes long.
+/// Follows little endian encoding.
+#[derive(Debug, Clone, Copy, PartialEq)]
+pub struct PaInterval(pub u16);
+
+impl PaInterval {
+    pub const BYTE_SIZE: usize = 2;
+    pub const UNKNOWN_VALUE: u16 = 0xFFFF;
+
+    pub const fn unknown() -> Self {
+        Self(Self::UNKNOWN_VALUE)
+    }
+}
+
+impl Encodable for PaInterval {
+    type Error = PacketError;
+
+    /// Encodees the PaInterval to 2 byte value using little endian encoding.
+    fn encode(&self, buf: &mut [u8]) -> core::result::Result<(), Self::Error> {
+        if buf.len() < Self::BYTE_SIZE {
+            return Err(PacketError::BufferTooSmall);
+        }
+        buf[0..Self::BYTE_SIZE].copy_from_slice(&self.0.to_le_bytes());
+        Ok(())
+    }
+
+    fn encoded_len(&self) -> core::primitive::usize {
+        Self::BYTE_SIZE
+    }
+}
+
+#[cfg(test)]
+mod tests {
+    use super::*;
+
+    #[test]
+    fn encode_pa_interval() {
+        let mut buf = [0; PaInterval::BYTE_SIZE];
+        let interval = PaInterval(0x1004);
+
+        interval.encode(&mut buf[..]).expect("should succeed");
+        assert_eq!(buf, [0x04, 0x10]);
+    }
+
+    #[test]
+    fn encode_pa_interval_fails() {
+        let mut buf = [0; 1];  // Not enough buffer space.
+        let interval = PaInterval(0x1004);
+
+        interval.encode(&mut buf[..]).expect_err("should fail");
+    }
+}
diff --git a/rust/bt-common/src/generic_audio.rs b/rust/bt-common/src/generic_audio.rs
new file mode 100644
index 0000000..904506c
--- /dev/null
+++ b/rust/bt-common/src/generic_audio.rs
@@ -0,0 +1,5 @@
+// Copyright 2023 Google LLC
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+pub mod metadata_ltv;
diff --git a/rust/bt-common/src/generic_audio/metadata_ltv.rs b/rust/bt-common/src/generic_audio/metadata_ltv.rs
new file mode 100644
index 0000000..e29b636
--- /dev/null
+++ b/rust/bt-common/src/generic_audio/metadata_ltv.rs
@@ -0,0 +1,588 @@
+// Copyright 2023 Google LLC
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+use bitflags::bitflags;
+
+use crate::packet_encoding::{Decodable, Encodable, Error as PacketError};
+
+pub type Metadata = Vec<Metadatum>;
+
+#[derive(Debug, PartialEq)]
+#[repr(u8)]
+pub enum Type {
+    PreferredAudioContexts = 0x01,
+    StreamingAudioContexts = 0x02,
+    ProgramInfo = 0x03,
+    Language = 0x04,
+    CCIDList = 0x05,
+    ParentalRating = 0x06,
+    ProgramInfoURI = 0x07,
+    ExtendedMetadata = 0xfe,
+    VendorSpecific = 0xff,
+    AudioActiveState = 0x08,
+    BroadcastAudioImmediateRenderingFlag = 0x09,
+}
+
+impl Type {
+    fn length_check(&self, provided: usize) -> Result<(), PacketError> {
+        if self.total_size_range().contains(&provided) {
+            Ok(())
+        } else {
+            Err(PacketError::UnexpectedDataLength)
+        }
+     }
+
+     // Total size range including all Length, Type, and Value parameters.
+     fn total_size_range(&self) -> std::ops::Range<usize> {
+        match self {
+            Type::PreferredAudioContexts | Type::StreamingAudioContexts => 4..5,
+            Type::ProgramInfo | Type::CCIDList | Type::ProgramInfoURI => 2..usize::MAX,
+            Type::Language => 5..6,
+            Type::ParentalRating => 3..4,
+            Type::ExtendedMetadata | Type::VendorSpecific => 4..256,
+            Type::AudioActiveState => 3..4,
+            Type::BroadcastAudioImmediateRenderingFlag => 2..3,
+        }
+     }
+}
+
+impl TryFrom<u8> for Type {
+    type Error = PacketError;
+
+    fn try_from(value: u8) -> Result<Self, Self::Error> {
+        let t = match value {
+            0x01 => Type::PreferredAudioContexts,
+            0x02 => Type::StreamingAudioContexts,
+            0x03 => Type::ProgramInfo,
+            0x04 => Type::Language,
+            0x05 => Type::CCIDList,
+            0x06 => Type::ParentalRating,
+            0x07 => Type::ProgramInfoURI,
+            0xFE => Type::ExtendedMetadata,
+            0xFF => Type::VendorSpecific,
+            0x08 => Type::AudioActiveState,
+            0x09 => Type::BroadcastAudioImmediateRenderingFlag,
+            _ => return Err(PacketError::OutOfRange),
+        };
+        Ok(t)
+    }
+}
+
+#[derive(Debug, PartialEq)]
+pub enum Metadatum {
+    PreferredAudioContexts(ContextType),
+    StreamingAudioContexts(ContextType),
+    ProgramInfo(String),
+    /// 3 byte, lower case language code as defined in ISO 639-­3
+    LanguageCode(String),
+    CCIDList(Vec<u8>),
+    ParentalRating(Rating),
+    ProgramInfoURI(String),
+    ExtendedMetadata {
+        type_: u16,
+        metadata: Vec<u8>,
+    },
+    VendorSpecific {
+        company_id: u16,
+        metadata: Vec<u8>,
+    },
+    AudioActiveState(bool),
+    // Flag for Broadcast Audio Immediate Rendering.
+    BroadcastAudioImmediateRenderingFlag,
+}
+
+
+impl Metadatum {
+    const LENGTH_BYTE_SIZE: usize = 1;
+    const TYPE_BYTE_SIZE: usize = 1;
+    const MIN_PACKET_SIZE: usize = Self::LENGTH_BYTE_SIZE + Self::TYPE_BYTE_SIZE;
+
+    // Size of this metadatum's Value parameter. Does not include the Length or Type size.
+    pub fn value_encoded_len(&self) -> usize {
+        match self {
+            Metadatum::PreferredAudioContexts(_) => 2,
+            Metadatum::StreamingAudioContexts(_) => 2,
+            Metadatum::ProgramInfo(value) => value.len(),
+            Metadatum::LanguageCode(_) => 3,
+            Metadatum::CCIDList(ccids) => ccids.len(),
+            Metadatum::ParentalRating(_) => 1,
+            Metadatum::ProgramInfoURI(uri) => uri.len(),
+            Metadatum::ExtendedMetadata { type_: _, metadata } => 2 + metadata.len(),
+            Metadatum::VendorSpecific { company_id: _, metadata } => 2 + metadata.len(),
+            Metadatum::AudioActiveState(_) => 1,
+            Metadatum::BroadcastAudioImmediateRenderingFlag => 0,
+        }
+    }
+
+    pub fn type_(&self) -> Type {
+        match self {
+            Metadatum::PreferredAudioContexts(_) => Type::PreferredAudioContexts,
+            Metadatum::StreamingAudioContexts(_) => Type::StreamingAudioContexts,
+            Metadatum::ProgramInfo(_) => Type::ProgramInfo,
+            Metadatum::LanguageCode(_) => Type::Language,
+            Metadatum::CCIDList(_) => Type::CCIDList,
+            Metadatum::ParentalRating(_) => Type::ParentalRating,
+            Metadatum::ProgramInfoURI(_) => Type::ProgramInfoURI,
+            Metadatum::ExtendedMetadata{..} => Type::ExtendedMetadata,
+            Metadatum::VendorSpecific{..} => Type::VendorSpecific,
+            Metadatum::AudioActiveState(_) => Type::AudioActiveState,
+            Metadatum::BroadcastAudioImmediateRenderingFlag => Type::BroadcastAudioImmediateRenderingFlag,
+        }
+    }
+}
+
+impl Decodable for Metadatum {
+    type Error = PacketError;
+
+    fn decode(buf: &[u8]) -> core::result::Result<(Self, usize), Self::Error> {
+        if buf.len() < Self::MIN_PACKET_SIZE {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+        // Total length of the buffer including all Length, Type, and Value parameters.
+        let total_len = 1 + buf[0] as usize;
+        if buf.len() < total_len {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+        let type_ = Type::try_from(buf[1])?;
+        let _ = type_.length_check(total_len)?;
+        let m: Metadatum = match type_ {
+            Type::PreferredAudioContexts | Type::StreamingAudioContexts => {
+                let context_type = ContextType::try_from(u16::from_le_bytes(buf[2..4].try_into().unwrap()))?;
+                if type_ == Type::PreferredAudioContexts {
+                    Self::PreferredAudioContexts(context_type)
+                }  else {
+                    Self::StreamingAudioContexts(context_type)
+                }
+            },
+            Type::ProgramInfo | Type::ProgramInfoURI => {
+                let value = String::from_utf8(buf[2..total_len].to_vec()).map_err(|e| PacketError::InvalidParameter(format!("{e}")))?;
+                if type_ == Type::ProgramInfo {
+                    Self::ProgramInfo(value)
+                } else {
+                    Self::ProgramInfoURI(value)
+                }
+            }
+            Type::Language => {
+                let code = String::from_utf8(buf[2..total_len].to_vec()).map_err(|e| PacketError::InvalidParameter(format!("{e}")))?;
+                Self::LanguageCode(code)
+            },
+            Type::CCIDList => Self::CCIDList(buf[2..total_len].to_vec()),
+            Type::ParentalRating => {
+                Self::ParentalRating(Rating::decode(&buf[2..3])?.0)
+            },
+            Type::ExtendedMetadata | Type::VendorSpecific => {
+                let type_or_id = u16::from_le_bytes(buf[2..4].try_into().unwrap());
+                let data = if buf.len() >= 5 {
+                    buf[4..total_len].to_vec()
+                } else {
+                    vec![]
+                };
+                if type_ == Type::ExtendedMetadata {
+                    Self::ExtendedMetadata{
+                        type_: type_or_id,
+                        metadata: data,
+                    }
+                } else {
+                    Self::VendorSpecific{
+                        company_id: type_or_id,
+                        metadata: data,
+                    }
+                }
+            },
+            Type::AudioActiveState => {
+                if buf[2] > 1 {
+                    return Err(PacketError::UnexpectedDataLength);
+                }
+                Self::AudioActiveState(buf[2] != 0)
+            },
+            Type::BroadcastAudioImmediateRenderingFlag => Self::BroadcastAudioImmediateRenderingFlag,
+        };
+        return Ok((m, total_len))
+    }
+}
+
+impl Encodable for Metadatum {
+    type Error = PacketError;
+
+    /// Encodes the object into a provided buffer in a Metadata LTV structure. Bytes are in LSO.
+    // See Assigned Numbers section 6.12.6 for details about Metadata LTV structures.
+    fn encode(&self, buf: &mut [u8]) -> core::result::Result<(), Self::Error> {
+        if buf.len() < self.encoded_len() {
+            return Err(PacketError::BufferTooSmall);
+        }
+
+        // Length parameter value excludes the length of Length parameter itself (which is 1 byte).
+        buf[0] = (self.encoded_len() - 1)
+            .try_into()
+            .map_err(|_| PacketError::InvalidParameter("Metadata too big".to_string()))?;
+        buf[1] = self.type_() as u8;
+
+        match self {
+            Self::PreferredAudioContexts(type_) | Self::StreamingAudioContexts(type_) => {
+                buf[2..4].copy_from_slice(&type_.bits().to_le_bytes())
+            }
+            Self::ProgramInfo(value) | Self::ProgramInfoURI(value) => {
+                buf[2..2 + value.len()].copy_from_slice(value.as_bytes())
+            }
+            Self::LanguageCode(value) if value.len() != 3 => {
+                return Err(PacketError::InvalidParameter(format!("{self}")));
+            }
+            Self::LanguageCode(value) => buf[2..5].copy_from_slice(&value.as_bytes()[..3]),
+            Self::CCIDList(value) => buf[2..2 + value.len()].copy_from_slice(&value.as_slice()),
+            Self::ParentalRating(value) => buf[2] = value.into(),
+            Self::ExtendedMetadata{type_, metadata} => {
+                buf[2..4].copy_from_slice(&type_.to_le_bytes());
+                buf[4..4 + metadata.len()].copy_from_slice(&metadata.as_slice());
+            }
+            Self::VendorSpecific { company_id, metadata } => {
+                buf[2..4].copy_from_slice(&company_id.to_le_bytes());
+                buf[4..4 + metadata.len()].copy_from_slice(&metadata.as_slice());
+            }
+            Self::AudioActiveState(value) => buf[2] = *value as u8,
+            Self::BroadcastAudioImmediateRenderingFlag => {}
+        }
+        Ok(())
+    }
+
+    fn encoded_len(&self) -> core::primitive::usize {
+        Self::MIN_PACKET_SIZE + self.value_encoded_len()
+    }
+}
+
+impl std::fmt::Display for Metadatum {
+    fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
+        match self {
+            // TODO(b/308483171): Consider using the Display for the inner fields instead of Debug.
+            Metadatum::PreferredAudioContexts(v) => write!(f, "Preferred Audio Contexts: {v:?}"),
+            Metadatum::StreamingAudioContexts(v) => write!(f, "Streaming Audio Contexts: {v:?}"),
+            Metadatum::ProgramInfo(v) => write!(f, "Progaam Info: {v:?}"),
+            Metadatum::LanguageCode(v) => write!(f, "Language: {v:?}"),
+            Metadatum::CCIDList(v) => write!(f, "CCID List: {v:?}"),
+            Metadatum::ParentalRating(v) => write!(f, "Parental Rating: {v:?}"),
+            Metadatum::ProgramInfoURI(v) => write!(f, "Program Info URI: {v:?}"),
+            Metadatum::ExtendedMetadata{type_, metadata} => {
+                write!(f, "Extended Metadata: type(0x{type_:02x}) metadata({metadata:?})")
+            }
+            Metadatum::VendorSpecific { company_id, metadata } => {
+                write!(f, "Vendor Specific: company(0x{company_id:02x}) metadata({metadata:?})")
+            }
+            Metadatum::AudioActiveState(v) => write!(f, "Audio Active State: {v}"),
+            Metadatum::BroadcastAudioImmediateRenderingFlag => {
+                write!(f, "Broadcast Audio Immediate Rendering Flag")
+            }
+        }
+    }
+}
+
+bitflags! {
+    #[derive(Clone, Copy, Debug, PartialEq)]
+    pub struct ContextType: u16 {
+        // 0x0000 value is prohibited.
+        const UNSPECIFIED      = 0x0001;
+        const CONVERSATIONAL   = 0x0002;
+        const MEDIA            = 0x0004;
+        const GAME             = 0x0008;
+        const INSTRUCTIONAL    = 0x0010;
+        const VOICE_ASSISTANTS = 0x0020;
+        const LIVE             = 0x0040;
+        const SOUND_EFFECTS    = 0x0080;
+        const NOTIFICATIONS    = 0x0100;
+        const RINGTONE         = 0x0200;
+        const ALERT            = 0x0400;
+        const EMERGENCY_ALARM  = 0x0800;
+    }
+}
+
+impl TryFrom<u16> for ContextType {
+    type Error = PacketError;
+
+    fn try_from(value: u16) -> Result<Self, Self::Error> {
+        if u16::count_ones(value) == 0 {
+            return Err(PacketError::InvalidParameter(format!("ContextType 0x0000 is prohibited")));
+        }
+        Ok(ContextType::from_bits_truncate(value))
+    }
+
+}
+
+/// Represents recommended minimum age of the viewer.
+/// The numbering scheme aligns with Annex F of EN 300 707 v1.2.1
+/// published by ETSI.
+#[derive(Clone, Copy, Debug, PartialEq)]
+pub enum Rating {
+    NoRating,
+    AllAge,
+    // Recommended for listeners of age x years, where x is the
+    // value of u8 that's greater than or equal to 5.
+    Age(u8),
+}
+
+impl Rating {
+    // Minimum age that can be recommended.
+    const MIN_RECOMMENDED_AGE: u8 = 5;
+
+    // When recommending for listeners of age Y years,
+    // Subtract 3 from the recommended age to get the encoded value.
+    // E.g., to indicate recommended age of 8 years or older, encode 5.
+    const AGE_OFFSET: u8 = 3;
+
+    const fn no_rating() -> Self {
+        Self::NoRating
+    }
+
+    const fn all_age() -> Self {
+        Self::AllAge
+    }
+
+    pub fn min_recommended(age: u8) -> Result<Self, PacketError> {
+        if age < Self::MIN_RECOMMENDED_AGE {
+            return Err(PacketError::InvalidParameter(format!("minimum recommended age must be at least 5. Got {age}")));
+        }
+        Ok(Rating::Age(age))
+    }
+}
+
+impl From<&Rating> for u8 {
+    fn from(value: &Rating) -> Self {
+        match value {
+            Rating::NoRating => 0x00,
+            Rating::AllAge => 0x01,
+            Rating::Age(a) => a - Rating::AGE_OFFSET,
+        }
+    }
+}
+
+impl Decodable for Rating {
+    type Error = PacketError;
+
+    fn decode(buf: &[u8]) -> core::result::Result<(Self, usize), Self::Error> {
+        if buf.len() == 0 {
+            return Err(PacketError::UnexpectedDataLength);
+        }
+        let rating = match buf[0] {
+            0x00 => Rating::NoRating,
+            0x01 => Rating::AllAge,
+            value => {
+                let age = value.checked_add(Self::AGE_OFFSET)
+                    .ok_or(PacketError::OutOfRange)?;
+                Rating::min_recommended(age).unwrap()
+            },
+        };
+        Ok((rating, 1))
+    }
+}
+
+#[cfg(test)]
+mod tests {
+    use super::*;
+
+    #[test]
+    fn metadataum_preferred_audio_contexts() {
+        // Encoding.
+        let test = Metadatum::PreferredAudioContexts(ContextType::CONVERSATIONAL);
+        assert_eq!(test.encoded_len(), 4);
+        let mut buf = vec![0; test.encoded_len()];
+        let _ = test.encode(&mut buf[..]).expect("should not fail");
+
+        let bytes = vec![0x03, 0x01, 0x02, 0x00];
+        assert_eq!(buf, bytes);
+
+        // Decoding.
+        let decoded = Metadatum::decode(&buf).expect("should succeed");
+        assert_eq!(decoded.0, test);
+        assert_eq!(decoded.1, 4);
+    }
+
+    #[test]
+    fn metadatum_streaming_audio_contexts() {
+        // Encoding.
+        let test = Metadatum::StreamingAudioContexts(ContextType::RINGTONE | ContextType::ALERT);
+        assert_eq!(test.encoded_len(), 4);
+        let mut buf = vec![0; test.encoded_len()];
+        let _ = test.encode(&mut buf[..]).expect("should not fail");
+
+        let bytes = vec![0x03, 0x02, 0x00, 0x06];
+        assert_eq!(buf, bytes);
+
+        // Decoding.
+        let decoded = Metadatum::decode(&buf).expect("should succeed");
+        assert_eq!(decoded.0, test);
+        assert_eq!(decoded.1, 4);
+    }
+
+    #[test]
+    fn metadatum_program_info() {
+        // Encoding.
+        let test = Metadatum::ProgramInfo("a".to_string());
+        assert_eq!(test.encoded_len(), 3);
+        let mut buf = vec![0; test.encoded_len()];
+        let _ = test.encode(&mut buf[..]).expect("should not fail");
+
+        let bytes = vec![0x02, 0x03, 0x61];
+        assert_eq!(buf, bytes);
+
+        // Decoding.
+        let decoded = Metadatum::decode(&buf).expect("should succeed");
+        assert_eq!(decoded.0, test);
+        assert_eq!(decoded.1, 3);
+    }
+
+    #[test]
+    fn metadatum_language_code() {
+        // Encoding.
+        let test = Metadatum::LanguageCode("eng".to_string());
+        assert_eq!(test.encoded_len(), 5);
+        let mut buf = vec![0; test.encoded_len()];
+        let _ = test.encode(&mut buf[..]).expect("should not fail");
+
+        let bytes = vec![0x04, 0x04, 0x65, 0x6E, 0x67];
+        assert_eq!(buf, bytes);
+
+        // Decoding.
+        let decoded = Metadatum::decode(&buf).expect("should succeed");
+        assert_eq!(decoded.0, test);
+        assert_eq!(decoded.1, 5);
+    }
+
+    #[test]
+    fn metadatum_ccid_list() {
+        // Encoding.
+        let test = Metadatum::CCIDList(vec![0x01, 0x02]);
+        assert_eq!(test.encoded_len(), 4);
+        let mut buf = vec![0; test.encoded_len()];
+        let _ = test.encode(&mut buf[..]).expect("should not fail");
+
+        let bytes = vec![0x03, 0x05, 0x01, 0x02];
+        assert_eq!(buf, bytes);
+
+        // Decoding.
+        let decoded = Metadatum::decode(&buf).expect("should succeed");
+        assert_eq!(decoded.0, test);
+        assert_eq!(decoded.1, 4);
+    }
+
+    #[test]
+    fn metadatum_parental_rating() {
+        // Encding.
+        let test = Metadatum::ParentalRating(Rating::Age(8));
+        assert_eq!(test.encoded_len(), 0x03);
+        let mut buf = vec![0; test.encoded_len()];
+        let _ = test.encode(&mut buf[..]).expect("should not fail");
+
+        let bytes = vec![0x02, 0x06, 0x05];
+        assert_eq!(buf, bytes);
+
+        // Decoding.
+        let decoded = Metadatum::decode(&buf).expect("should succeed");
+        assert_eq!(decoded.0, test);
+        assert_eq!(decoded.1, 3);
+    }
+
+    #[test]
+    fn metadatum_vendor_specific() {
+        // Encoding.
+        let test = Metadatum::VendorSpecific{company_id: 0x00E0, metadata: vec![0x01, 0x02]};
+        assert_eq!(test.encoded_len(), 0x06);
+        let mut buf = vec![0; test.encoded_len()];
+        let _ = test.encode(&mut buf[..]).expect("should not fail");
+
+        let bytes = vec![0x05, 0xFF, 0xE0, 0x00, 0x01, 0x02];
+        assert_eq!(buf, bytes);
+
+        // Decoding.
+        let decoded = Metadatum::decode(&buf).expect("should succeed");
+        assert_eq!(decoded.0, test);
+        assert_eq!(decoded.1, 6);
+    }
+
+    #[test]
+    fn metadatum_audio_active_state() {
+        // Encoding.
+        let test = Metadatum::AudioActiveState(true);
+        assert_eq!(test.encoded_len(), 0x03);
+        let mut buf = vec![0; test.encoded_len()];
+        let _ = test.encode(&mut buf[..]).expect("should not fail");
+
+        let bytes = vec![0x02, 0x08, 0x01];
+        assert_eq!(buf, bytes);
+
+        // Decoding.
+        let decoded = Metadatum::decode(&buf).expect("should succeed");
+        assert_eq!(decoded.0, test);
+        assert_eq!(decoded.1, 3);
+    }
+
+    #[test]
+    fn metadatum_broadcast_audio_immediate_rendering() {
+        // Encoding.
+        let test = Metadatum::BroadcastAudioImmediateRenderingFlag;
+        assert_eq!(test.encoded_len(), 0x02);
+        let mut buf = vec![0; test.encoded_len()];
+        let _ = test.encode(&mut buf[..]).expect("should not fail");
+
+        let bytes = vec![0x01, 0x09];
+        assert_eq!(buf, bytes);
+
+        // Decoding.
+        let decoded = Metadatum::decode(&buf).expect("should succeed");
+        assert_eq!(decoded.0, test);
+        assert_eq!(decoded.1, 2);
+    }
+
+    #[test]
+    fn invalid_metadataum() {
+        // Language code must be 3-lettered.
+        let test = Metadatum::LanguageCode("illegal".to_string());
+        let mut buf = vec![0; test.encoded_len()];
+        let _ = test.encode(&mut buf[..]).expect_err("should fail");
+
+        // Not enough length for Length and Type for decoding.
+        let buf = vec![0x03];
+        let _ = Metadatum::decode(&buf).expect_err("should fail");
+
+        // Not enough length for Value field for decoding.
+        let buf = vec![0x02, 0x01, 0x02];
+        let _ = Metadatum::decode(&buf).expect_err("should fail");
+
+        // Buffer length does not match Length value for decoding.
+        let buf = vec![0x03, 0x03, 0x61];
+        let _ = Metadatum::decode(&buf).expect_err("should fail");
+    }
+
+    #[test]
+    fn rating() {
+        let no_rating = Rating::no_rating();
+        let all_age = Rating::all_age();
+        let for_age = Rating::min_recommended(5).expect("should succeed");
+
+        assert_eq!(<&Rating as Into<u8>>::into(&no_rating), 0x00);
+        assert_eq!(<&Rating as Into<u8>>::into(&all_age), 0x01);
+        assert_eq!(<&Rating as Into<u8>>::into(&for_age), 0x02);
+    }
+
+    #[test]
+    fn decode_rating() {
+        let res = Rating::decode(&[0]).expect("should not fail");
+        assert_eq!(res.0, Rating::NoRating);
+        assert_eq!(res.1, 1);
+
+        let res = Rating::decode(&[1]).expect("should not fail");
+        assert_eq!(res.0, Rating::AllAge);
+        assert_eq!(res.1, 1);
+
+        let res = Rating::decode(&[2]).expect("should not fail");
+        assert_eq!(res.0, Rating::Age(5));
+        assert_eq!(res.1, 1);
+
+        let res = Rating::decode(&[10]).expect("should not fail");
+        assert_eq!(res.0, Rating::Age(13));
+        assert_eq!(res.1, 1);
+    }
+
+    #[test]
+    fn invalid_rating() {
+        let _ = Rating::min_recommended(4).expect_err("should have failed");
+        let _ = Rating::decode(&[255]).expect_err("should fail");
+    }
+}
diff --git a/rust/bt-common/src/lib.rs b/rust/bt-common/src/lib.rs
index 58828f4..67e9360 100644
--- a/rust/bt-common/src/lib.rs
+++ b/rust/bt-common/src/lib.rs
@@ -2,6 +2,8 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
+extern crate core as rust_core;
+
 /// Peers are identified by ids, which should be treated as opaque by service libraries.
 /// Stack implementations should ensure that each PeerId identifies a single peer over a single
 /// instance of the stack - a [`bt_gatt::Central::connect`] should always attempt to connect to the
@@ -10,11 +12,14 @@
 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
 pub struct PeerId(pub u64);
 
-impl core::fmt::Display for PeerId {
-    fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> std::result::Result<(), std::fmt::Error> {
+impl rust_core::fmt::Display for PeerId {
+    fn fmt(&self, f: &mut rust_core::fmt::Formatter<'_>) -> std::result::Result<(), std::fmt::Error> {
         write!(f, "{:x}", self.0)
     }
 }
 
+pub mod core;
+pub mod generic_audio;
+pub mod packet_encoding;
 pub mod uuid;
 pub use crate::uuid::Uuid;
diff --git a/rust/bt-common/src/packet_encoding.rs b/rust/bt-common/src/packet_encoding.rs
new file mode 100644
index 0000000..fa01309
--- /dev/null
+++ b/rust/bt-common/src/packet_encoding.rs
@@ -0,0 +1,41 @@
+// Copyright 2023 Google LLC
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+use thiserror::Error;
+
+/// A decodable type can be created from a byte buffer.
+/// The type returned is separate (copied) from the buffer once decoded.
+pub trait Decodable: ::core::marker::Sized {
+    type Error;
+
+    /// Decodes into a new object with the number of bytes that were decoded, or returns an error.
+    fn decode(buf: &[u8]) -> ::core::result::Result<(Self, usize), Self::Error>;
+}
+
+/// An encodable type can write itself into a byte buffer.
+pub trait Encodable: ::core::marker::Sized {
+    type Error;
+
+    /// Returns the number of bytes necessary to encode |self|.
+    fn encoded_len(&self) -> ::core::primitive::usize;
+
+    /// Writes the encoded version of |self| at the start of |buf|.
+    /// |buf| must be at least |self.encoded_len()| length.
+    fn encode(&self, buf: &mut [u8]) -> ::core::result::Result<(), Self::Error>;
+}
+
+#[derive(Error, Debug, PartialEq)]
+pub enum Error {
+    #[error("Parameter is not valid: {0}")]
+    InvalidParameter(String),
+
+    #[error("Out-of-range enum value")]
+    OutOfRange,
+
+    #[error("Encoding buffer is too small")]
+    BufferTooSmall,
+
+    #[error("Buffer being decoded is invalid length")]
+    UnexpectedDataLength,
+}
