nrf24l01_commands/
commands.rs

1//! Generate SPI byte sequences for nRF24L01 commands.
2//!
3//! ## Example with writing the [`CONFIG`][registers::Config] register
4//! ```rust
5//! use nrf24l01_commands::{registers, commands};
6//!
7//! let config = registers::Config::new()
8//!     .with_mask_rx_dr(true)
9//!     .with_mask_tx_ds(false)
10//!     .with_mask_max_rt(false)
11//!     .with_en_crc(false)
12//!     .with_crco(true)
13//!     .with_pwr_up(true)
14//!     .with_prim_rx(false);
15//! let write_command = commands::WRegister(config);
16//! let spi_bytes = write_command.bytes();
17//! assert_eq!(spi_bytes, [0b0010_0000, 0b0100_0110]);
18//! ```
19use crate::registers::{self, Register};
20use core::marker::PhantomData;
21
22/// A trait for nRF24L01 commands. Defines the command's _command word_.
23pub trait Command {
24    /// Command word.
25    const WORD: u8;
26}
27
28/// # R_REGISTER command
29/// Read a register.
30///
31/// #### Type Parameter `R`
32/// Register type.
33///
34/// ## Example
35/// ```rust
36/// use nrf24l01_commands::{registers, commands};
37///
38/// // Generate SPI byte sequence for R_REGISTER on FIFO_STATUS register.
39/// let bytes = commands::RRegister::<registers::FifoStatus>::bytes();
40/// assert_eq!(bytes, [0 | 0x17, 0]);
41/// ```
42pub struct RRegister<R>(PhantomData<R>);
43
44/// # W_REGISTER command
45/// Write a register.
46///
47/// ## Example
48/// ```rust
49/// use nrf24l01_commands::{registers, commands};
50///
51/// // Generate SPI byte sequence for W_REGISTER on RF_CH register.
52/// let rf_ch = registers::RfCh::new().with_rf_ch(85);
53/// let bytes = commands::WRegister(rf_ch).bytes();
54/// assert_eq!(bytes, [0b0010_0000 | 0x05, 85]);
55///
56/// // Generate SPI byte sequence for W_REGISTER on TX_ADDR register.
57/// let tx_addr = registers::TxAddr::<5>::new().with_tx_addr(0x61DE7C320B);
58/// let bytes = commands::WRegister(tx_addr).bytes();
59/// assert_eq!(bytes, [0b0010_0000 | 0x10, 0x0B, 0x32, 0x7C, 0xDE, 0x61]);
60/// ```
61pub struct WRegister<R>(
62    /// Register to write.
63    pub R,
64);
65
66/// # R_RX_PAYLOAD command
67/// Read RX payload.
68///
69/// #### Const Parameter `N`
70/// Width of RX payload.
71///
72/// <div class="warning">
73/// Must be 1 to 32 bytes.
74/// </div>
75///
76/// ## Example
77/// ```rust
78/// use nrf24l01_commands::commands;
79///
80/// // Generate SPI byte sequence for R_RX_PAYLOAD with 17 byte payload.
81/// let bytes = commands::RRxPayload::<17>::bytes();
82/// let mut expected_bytes = [0; 18];
83/// expected_bytes[0] = 0b0110_0001;
84/// assert_eq!(bytes, expected_bytes);
85/// ```
86pub struct RRxPayload<const N: usize>();
87
88/// # W_TX_PAYLOAD command
89/// Write TX payload. Payload byte-order is kept as MSByte first contrary to documentation.
90///
91/// ## Example
92/// ```rust
93/// use nrf24l01_commands::commands;
94///
95/// let payload = [1, 2, 3, 4, 5, 6, 7, 8, 9];
96/// let bytes = commands::WTxPayload(payload).bytes();
97/// assert_eq!(bytes, [0b1010_0000, 1, 2, 3, 4, 5, 6, 7, 8, 9]);
98/// ```
99pub struct WTxPayload<const N: usize>(
100    /// Payload to write.
101    /// <div class="warning">
102    /// Payload must be 1 to 32 bytes.
103    /// </div>
104    pub [u8; N],
105);
106
107/// # FLUSH_TX command
108/// Flush TX FIFO. Used in TX mode.
109///
110/// ## Example
111/// ```rust
112/// use nrf24l01_commands::commands::{self, Command};
113///
114/// assert_eq!(commands::FlushTx::WORD, 0b1110_0001);
115/// assert_eq!(commands::FlushTx::bytes(), [0b1110_0001]);
116/// ```
117pub struct FlushTx();
118
119/// # FLUSH_RX command
120/// Flush RX FIFO. Used in RX mode.
121///
122/// ## Example
123/// ```rust
124/// use nrf24l01_commands::commands::{self, Command};
125///
126/// assert_eq!(commands::FlushRx::WORD, 0b1110_0010);
127/// assert_eq!(commands::FlushRx::bytes(), [0b1110_0010]);
128/// ```
129pub struct FlushRx();
130
131/// # REUSE_TX_PL command
132/// Reuse last transmitted payload. Packets are repeatedly transmitted as long
133/// as CE is high. TX payload reuse is active until [`W_TX_PAYLOAD`][WTxPayload] or [`FLUSH_TX`][FlushTx]
134/// is executed.
135///
136/// ## Example
137/// ```rust
138/// use nrf24l01_commands::commands::{self, Command};
139///
140/// assert_eq!(commands::ReuseTxPl::WORD, 0b1110_0011);
141/// assert_eq!(commands::ReuseTxPl::bytes(), [0b1110_0011]);
142/// ```
143pub struct ReuseTxPl();
144
145/// # ACTIVATE command
146/// Activates the [`FEATURE`][registers::Feature] register.
147///
148/// ## Example
149/// ```rust
150/// use nrf24l01_commands::commands;
151///
152/// let bytes = commands::Activate::bytes();
153/// assert_eq!(bytes, [0b0101_0000, 0x73]);
154/// ```
155pub struct Activate();
156
157/// # R_RX_PL_WID command
158/// Read RX payload width for the top payload in RX FIFO.
159///
160/// ## Example
161/// ```rust
162/// use nrf24l01_commands::commands;
163///
164/// let bytes = commands::RRxPlWid::bytes();
165/// assert_eq!(bytes, [0b0110_0000, 0]);
166/// ```
167pub struct RRxPlWid();
168
169/// # W_ACK_PAYLOAD command
170/// Write payload to be transmitted with ACK packet on a data [`pipe`][WAckPayload::pipe]. Used in RX mode.
171/// Maximum three ACK packet payloads can be pending. Payloads with the same [`pipe`][WAckPayload::pipe]
172/// are handled first-in-first-out. Payload byte-order is kept as MSByte first contrary to documentation.
173///
174/// ## Example
175/// ```rust
176/// use nrf24l01_commands::commands;
177///
178/// let pipe = 4;
179/// let payload = [1, 2, 3, 4, 5, 6, 7, 8, 9];
180/// let bytes = commands::WAckPayload { pipe, payload }.bytes();
181/// assert_eq!(bytes, [0b1010_1000 | pipe, 1, 2, 3, 4, 5, 6, 7, 8, 9]);
182/// ```
183pub struct WAckPayload<const N: usize> {
184    /// Data pipe this ACK payload is designated to.
185    pub pipe: u8,
186    /// Payload to send with ACK.
187    /// <div class="warning">
188    /// Payload must be 1 to 32 bytes.
189    /// </div>
190    pub payload: [u8; N],
191}
192
193/// # W_TX_PAYLOAD_NOACK command
194/// Write TX payload with AUTOACK disabled. Payload byte-order is kept as MSByte first contrary to documentation.
195///
196/// ## Example
197/// ```rust
198/// use nrf24l01_commands::commands;
199///
200/// let payload = [1, 2, 3, 4, 5, 6, 7, 8, 9];
201/// let bytes = commands::WTxPayloadNoack(payload).bytes();
202/// assert_eq!(bytes, [0b1011_0000, 1, 2, 3, 4, 5, 6, 7, 8, 9]);
203/// ```
204pub struct WTxPayloadNoack<const N: usize>(
205    /// Payload to write.
206    /// <div class="warning">
207    /// Payload must be 1 to 32 bytes.
208    /// </div>
209    pub [u8; N],
210);
211
212/// # NOP command
213/// No operation. Used to read the status register.
214///
215/// ## Example
216/// ```rust
217/// use nrf24l01_commands::commands::{self, Command};
218///
219/// assert_eq!(commands::Nop::WORD, 0xFF);
220/// assert_eq!(commands::Nop::bytes(), [0xFF]);
221/// ```
222pub struct Nop();
223
224impl<R> Command for RRegister<R> {
225    const WORD: u8 = 0;
226}
227impl<R> Command for WRegister<R> {
228    const WORD: u8 = 0b0010_0000;
229}
230impl<const N: usize> Command for RRxPayload<N> {
231    const WORD: u8 = 0b0110_0001;
232}
233impl<const N: usize> Command for WTxPayload<N> {
234    const WORD: u8 = 0b1010_0000;
235}
236impl Command for FlushTx {
237    const WORD: u8 = 0b1110_0001;
238}
239impl Command for FlushRx {
240    const WORD: u8 = 0b1110_0010;
241}
242impl Command for ReuseTxPl {
243    const WORD: u8 = 0b1110_0011;
244}
245impl Command for Activate {
246    const WORD: u8 = 0b0101_0000;
247}
248impl Command for RRxPlWid {
249    const WORD: u8 = 0b0110_0000;
250}
251impl<const N: usize> Command for WAckPayload<N> {
252    const WORD: u8 = 0b1010_1000;
253}
254impl<const N: usize> Command for WTxPayloadNoack<N> {
255    const WORD: u8 = 0b1011_0000;
256}
257impl Command for Nop {
258    const WORD: u8 = 0b1111_1111;
259}
260
261impl RRegister<registers::Config> {
262    /// Get the command's _command word_.
263    pub const fn word() -> u8 {
264        Self::WORD | registers::Config::ADDRESS
265    }
266
267    /// Generate the command's SPI byte sequence.
268    pub const fn bytes() -> [u8; 2] {
269        [Self::word(), 0]
270    }
271}
272
273impl RRegister<registers::EnAa> {
274    /// Get the command's _command word_.
275    pub const fn word() -> u8 {
276        Self::WORD | registers::EnAa::ADDRESS
277    }
278
279    /// Generate the command's SPI byte sequence.
280    pub const fn bytes() -> [u8; 2] {
281        [Self::word(), 0]
282    }
283}
284
285impl RRegister<registers::EnRxaddr> {
286    /// Get the command's _command word_.
287    pub const fn word() -> u8 {
288        Self::WORD | registers::EnRxaddr::ADDRESS
289    }
290
291    /// Generate the command's SPI byte sequence.
292    pub const fn bytes() -> [u8; 2] {
293        [Self::word(), 0]
294    }
295}
296
297impl RRegister<registers::SetupAw> {
298    /// Get the command's _command word_.
299    pub const fn word() -> u8 {
300        Self::WORD | registers::SetupAw::ADDRESS
301    }
302
303    /// Generate the command's SPI byte sequence.
304    pub const fn bytes() -> [u8; 2] {
305        [Self::word(), 0]
306    }
307}
308
309impl RRegister<registers::SetupRetr> {
310    /// Get the command's _command word_.
311    pub const fn word() -> u8 {
312        Self::WORD | registers::SetupRetr::ADDRESS
313    }
314
315    /// Generate the command's SPI byte sequence.
316    pub const fn bytes() -> [u8; 2] {
317        [Self::word(), 0]
318    }
319}
320
321impl RRegister<registers::RfCh> {
322    /// Get the command's _command word_.
323    pub const fn word() -> u8 {
324        Self::WORD | registers::RfCh::ADDRESS
325    }
326
327    /// Generate the command's SPI byte sequence.
328    pub const fn bytes() -> [u8; 2] {
329        [Self::word(), 0]
330    }
331}
332
333impl RRegister<registers::RfSetup> {
334    /// Get the command's _command word_.
335    pub const fn word() -> u8 {
336        Self::WORD | registers::RfSetup::ADDRESS
337    }
338
339    /// Generate the command's SPI byte sequence.
340    pub const fn bytes() -> [u8; 2] {
341        [Self::word(), 0]
342    }
343}
344
345impl RRegister<registers::Status> {
346    /// Get the command's _command word_.
347    pub const fn word() -> u8 {
348        Self::WORD | registers::Status::ADDRESS
349    }
350
351    /// Generate the command's SPI byte sequence.
352    pub const fn bytes() -> [u8; 2] {
353        [Self::word(), 0]
354    }
355}
356
357impl RRegister<registers::ObserveTx> {
358    /// Get the command's _command word_.
359    pub const fn word() -> u8 {
360        Self::WORD | registers::ObserveTx::ADDRESS
361    }
362
363    /// Generate the command's SPI byte sequence.
364    pub const fn bytes() -> [u8; 2] {
365        [Self::word(), 0]
366    }
367}
368
369impl RRegister<registers::Cd> {
370    /// Get the command's _command word_.
371    pub const fn word() -> u8 {
372        Self::WORD | registers::Cd::ADDRESS
373    }
374
375    /// Generate the command's SPI byte sequence.
376    pub const fn bytes() -> [u8; 2] {
377        [Self::word(), 0]
378    }
379}
380
381impl<const N: usize> RRegister<registers::RxAddrP0<N>> {
382    /// Get the command's _command word_.
383    pub const fn word() -> u8 {
384        Self::WORD | registers::RxAddrP0::<N>::ADDRESS
385    }
386
387    /// Generate the command's SPI byte sequence.
388    pub const fn bytes() -> [u8; N + 1] {
389        let mut bytes = [0; N + 1];
390        bytes[0] = Self::word();
391        bytes
392    }
393}
394
395impl<const N: usize> RRegister<registers::RxAddrP1<N>> {
396    /// Get the command's _command word_.
397    pub const fn word() -> u8 {
398        Self::WORD | registers::RxAddrP1::<N>::ADDRESS
399    }
400
401    /// Generate the command's SPI byte sequence.
402    pub const fn bytes() -> [u8; N + 1] {
403        let mut bytes = [0; N + 1];
404        bytes[0] = Self::word();
405        bytes
406    }
407}
408
409impl RRegister<registers::RxAddrP2> {
410    /// Get the command's _command word_.
411    pub const fn word() -> u8 {
412        Self::WORD | registers::RxAddrP2::ADDRESS
413    }
414
415    /// Generate the command's SPI byte sequence.
416    pub const fn bytes() -> [u8; 2] {
417        [Self::word(), 0]
418    }
419}
420
421impl RRegister<registers::RxAddrP3> {
422    /// Get the command's _command word_.
423    pub const fn word() -> u8 {
424        Self::WORD | registers::RxAddrP3::ADDRESS
425    }
426
427    /// Generate the command's SPI byte sequence.
428    pub const fn bytes() -> [u8; 2] {
429        [Self::word(), 0]
430    }
431}
432
433impl RRegister<registers::RxAddrP4> {
434    /// Get the command's _command word_.
435    pub const fn word() -> u8 {
436        Self::WORD | registers::RxAddrP4::ADDRESS
437    }
438
439    /// Generate the command's SPI byte sequence.
440    pub const fn bytes() -> [u8; 2] {
441        [Self::word(), 0]
442    }
443}
444
445impl RRegister<registers::RxAddrP5> {
446    /// Get the command's _command word_.
447    pub const fn word() -> u8 {
448        Self::WORD | registers::RxAddrP5::ADDRESS
449    }
450
451    /// Generate the command's SPI byte sequence.
452    pub const fn bytes() -> [u8; 2] {
453        [Self::word(), 0]
454    }
455}
456
457impl<const N: usize> RRegister<registers::TxAddr<N>> {
458    /// Get the command's _command word_.
459    pub const fn word() -> u8 {
460        Self::WORD | registers::TxAddr::<N>::ADDRESS
461    }
462
463    /// Generate the command's SPI byte sequence.
464    pub const fn bytes() -> [u8; N + 1] {
465        let mut bytes = [0; N + 1];
466        bytes[0] = Self::word();
467        bytes
468    }
469}
470
471impl RRegister<registers::RxPwP0> {
472    /// Get the command's _command word_.
473    pub const fn word() -> u8 {
474        Self::WORD | registers::RxPwP0::ADDRESS
475    }
476
477    /// Generate the command's SPI byte sequence.
478    pub const fn bytes() -> [u8; 2] {
479        [Self::word(), 0]
480    }
481}
482
483impl RRegister<registers::RxPwP1> {
484    /// Get the command's _command word_.
485    pub const fn word() -> u8 {
486        Self::WORD | registers::RxPwP1::ADDRESS
487    }
488
489    /// Generate the command's SPI byte sequence.
490    pub const fn bytes() -> [u8; 2] {
491        [Self::word(), 0]
492    }
493}
494
495impl RRegister<registers::RxPwP2> {
496    /// Get the command's _command word_.
497    pub const fn word() -> u8 {
498        Self::WORD | registers::RxPwP2::ADDRESS
499    }
500
501    /// Generate the command's SPI byte sequence.
502    pub const fn bytes() -> [u8; 2] {
503        [Self::word(), 0]
504    }
505}
506
507impl RRegister<registers::RxPwP3> {
508    /// Get the command's _command word_.
509    pub const fn word() -> u8 {
510        Self::WORD | registers::RxPwP3::ADDRESS
511    }
512
513    /// Generate the command's SPI byte sequence.
514    pub const fn bytes() -> [u8; 2] {
515        [Self::word(), 0]
516    }
517}
518
519impl RRegister<registers::RxPwP4> {
520    /// Get the command's _command word_.
521    pub const fn word() -> u8 {
522        Self::WORD | registers::RxPwP4::ADDRESS
523    }
524
525    /// Generate the command's SPI byte sequence.
526    pub const fn bytes() -> [u8; 2] {
527        [Self::word(), 0]
528    }
529}
530
531impl RRegister<registers::RxPwP5> {
532    /// Get the command's _command word_.
533    pub const fn word() -> u8 {
534        Self::WORD | registers::RxPwP5::ADDRESS
535    }
536
537    /// Generate the command's SPI byte sequence.
538    pub const fn bytes() -> [u8; 2] {
539        [Self::word(), 0]
540    }
541}
542
543impl RRegister<registers::FifoStatus> {
544    /// Get the command's _command word_.
545    pub const fn word() -> u8 {
546        Self::WORD | registers::FifoStatus::ADDRESS
547    }
548
549    /// Generate the command's SPI byte sequence.
550    pub const fn bytes() -> [u8; 2] {
551        [Self::word(), 0]
552    }
553}
554
555impl RRegister<registers::Dynpd> {
556    /// Get the command's _command word_.
557    pub const fn word() -> u8 {
558        Self::WORD | registers::Dynpd::ADDRESS
559    }
560
561    /// Generate the command's SPI byte sequence.
562    pub const fn bytes() -> [u8; 2] {
563        [Self::word(), 0]
564    }
565}
566
567impl RRegister<registers::Feature> {
568    /// Get the command's _command word_.
569    pub const fn word() -> u8 {
570        Self::WORD | registers::Feature::ADDRESS
571    }
572
573    /// Generate the command's SPI byte sequence.
574    pub const fn bytes() -> [u8; 2] {
575        [Self::word(), 0]
576    }
577}
578
579impl WRegister<registers::Config> {
580    /// Get the command's _command word_.
581    pub const fn word() -> u8 {
582        Self::WORD | registers::Config::ADDRESS
583    }
584
585    /// Generate the command's SPI byte sequence.
586    pub const fn bytes(&self) -> [u8; 2] {
587        [Self::word(), self.0.into_bits()]
588    }
589}
590
591impl WRegister<registers::EnAa> {
592    /// Get the command's _command word_.
593    pub const fn word() -> u8 {
594        Self::WORD | registers::EnAa::ADDRESS
595    }
596
597    /// Generate the command's SPI byte sequence.
598    pub const fn bytes(&self) -> [u8; 2] {
599        [Self::word(), self.0.into_bits()]
600    }
601}
602
603impl WRegister<registers::EnRxaddr> {
604    /// Get the command's _command word_.
605    pub const fn word() -> u8 {
606        Self::WORD | registers::EnRxaddr::ADDRESS
607    }
608
609    /// Generate the command's SPI byte sequence.
610    pub const fn bytes(&self) -> [u8; 2] {
611        [Self::word(), self.0.into_bits()]
612    }
613}
614
615impl WRegister<registers::SetupAw> {
616    /// Get the command's _command word_.
617    pub const fn word() -> u8 {
618        Self::WORD | registers::SetupAw::ADDRESS
619    }
620
621    /// Generate the command's SPI byte sequence.
622    pub const fn bytes(&self) -> [u8; 2] {
623        [Self::word(), self.0.into_bits()]
624    }
625}
626
627impl WRegister<registers::SetupRetr> {
628    /// Get the command's _command word_.
629    pub const fn word() -> u8 {
630        Self::WORD | registers::SetupRetr::ADDRESS
631    }
632
633    /// Generate the command's SPI byte sequence.
634    pub const fn bytes(&self) -> [u8; 2] {
635        [Self::word(), self.0.into_bits()]
636    }
637}
638
639impl WRegister<registers::RfCh> {
640    /// Get the command's _command word_.
641    pub const fn word() -> u8 {
642        Self::WORD | registers::RfCh::ADDRESS
643    }
644
645    /// Generate the command's SPI byte sequence.
646    pub const fn bytes(&self) -> [u8; 2] {
647        [Self::word(), self.0.into_bits()]
648    }
649}
650
651impl WRegister<registers::RfSetup> {
652    /// Get the command's _command word_.
653    pub const fn word() -> u8 {
654        Self::WORD | registers::RfSetup::ADDRESS
655    }
656
657    /// Generate the command's SPI byte sequence.
658    pub const fn bytes(&self) -> [u8; 2] {
659        [Self::word(), self.0.into_bits()]
660    }
661}
662
663impl WRegister<registers::Status> {
664    /// Get the command's _command word_.
665    pub const fn word() -> u8 {
666        Self::WORD | registers::Status::ADDRESS
667    }
668
669    /// Generate the command's SPI byte sequence.
670    pub const fn bytes(&self) -> [u8; 2] {
671        [Self::word(), self.0.into_bits()]
672    }
673}
674
675impl WRegister<registers::ObserveTx> {
676    /// Get the command's _command word_.
677    pub const fn word() -> u8 {
678        Self::WORD | registers::ObserveTx::ADDRESS
679    }
680
681    /// Generate the command's SPI byte sequence.
682    pub const fn bytes(&self) -> [u8; 2] {
683        [Self::word(), self.0.into_bits()]
684    }
685}
686
687impl WRegister<registers::Cd> {
688    /// Get the command's _command word_.
689    pub const fn word() -> u8 {
690        Self::WORD | registers::Cd::ADDRESS
691    }
692
693    /// Generate the command's SPI byte sequence.
694    pub const fn bytes(&self) -> [u8; 2] {
695        [Self::word(), self.0.into_bits()]
696    }
697}
698
699/// Concatenate the command word and address bytes into an array.
700#[inline(always)]
701const fn concat_word_addr<const N: usize>(word: u8, addr: [u8; N]) -> [u8; N + 1] {
702    let mut bytes: [u8; N + 1] = [0; N + 1];
703    bytes[0] = word;
704    // Addr is already in little-endian byte-order
705    let mut i = 1;
706    while i < N + 1 {
707        bytes[i] = addr[i - 1];
708        i += 1;
709    }
710    bytes
711}
712
713impl<const N: usize> WRegister<registers::RxAddrP0<N>> {
714    /// Get the command's _command word_.
715    pub const fn word() -> u8 {
716        Self::WORD | registers::RxAddrP0::<N>::ADDRESS
717    }
718
719    /// Generate the command's SPI byte sequence.
720    pub const fn bytes(&self) -> [u8; N + 1] {
721        concat_word_addr(Self::word(), self.0.into_bytes())
722    }
723}
724
725impl<const N: usize> WRegister<registers::RxAddrP1<N>> {
726    /// Get the command's _command word_.
727    pub const fn word() -> u8 {
728        Self::WORD | registers::RxAddrP1::<N>::ADDRESS
729    }
730
731    /// Generate the command's SPI byte sequence.
732    pub const fn bytes(&self) -> [u8; N + 1] {
733        concat_word_addr(Self::word(), self.0.into_bytes())
734    }
735}
736
737impl WRegister<registers::RxAddrP2> {
738    /// Get the command's _command word_.
739    pub const fn word() -> u8 {
740        Self::WORD | registers::RxAddrP2::ADDRESS
741    }
742
743    /// Generate the command's SPI byte sequence.
744    pub const fn bytes(&self) -> [u8; 2] {
745        [Self::word(), self.0.into_bits()]
746    }
747}
748
749impl WRegister<registers::RxAddrP3> {
750    /// Get the command's _command word_.
751    pub const fn word() -> u8 {
752        Self::WORD | registers::RxAddrP3::ADDRESS
753    }
754
755    /// Generate the command's SPI byte sequence.
756    pub const fn bytes(&self) -> [u8; 2] {
757        [Self::word(), self.0.into_bits()]
758    }
759}
760
761impl WRegister<registers::RxAddrP4> {
762    /// Get the command's _command word_.
763    pub const fn word() -> u8 {
764        Self::WORD | registers::RxAddrP4::ADDRESS
765    }
766
767    /// Generate the command's SPI byte sequence.
768    pub const fn bytes(&self) -> [u8; 2] {
769        [Self::word(), self.0.into_bits()]
770    }
771}
772
773impl WRegister<registers::RxAddrP5> {
774    /// Get the command's _command word_.
775    pub const fn word() -> u8 {
776        Self::WORD | registers::RxAddrP5::ADDRESS
777    }
778
779    /// Generate the command's SPI byte sequence.
780    pub const fn bytes(&self) -> [u8; 2] {
781        [Self::word(), self.0.into_bits()]
782    }
783}
784
785impl<const N: usize> WRegister<registers::TxAddr<N>> {
786    /// Get the command's _command word_.
787    pub const fn word() -> u8 {
788        Self::WORD | registers::TxAddr::<N>::ADDRESS
789    }
790
791    /// Generate the command's SPI byte sequence.
792    pub const fn bytes(&self) -> [u8; N + 1] {
793        concat_word_addr(Self::word(), self.0.into_bytes())
794    }
795}
796
797impl WRegister<registers::RxPwP0> {
798    /// Get the command's _command word_.
799    pub const fn word() -> u8 {
800        Self::WORD | registers::RxPwP0::ADDRESS
801    }
802
803    /// Generate the command's SPI byte sequence.
804    pub const fn bytes(&self) -> [u8; 2] {
805        [Self::word(), self.0.into_bits()]
806    }
807}
808
809impl WRegister<registers::RxPwP1> {
810    /// Get the command's _command word_.
811    pub const fn word() -> u8 {
812        Self::WORD | registers::RxPwP1::ADDRESS
813    }
814
815    /// Generate the command's SPI byte sequence.
816    pub const fn bytes(&self) -> [u8; 2] {
817        [Self::word(), self.0.into_bits()]
818    }
819}
820
821impl WRegister<registers::RxPwP2> {
822    /// Get the command's _command word_.
823    pub const fn word() -> u8 {
824        Self::WORD | registers::RxPwP2::ADDRESS
825    }
826
827    /// Generate the command's SPI byte sequence.
828    pub const fn bytes(&self) -> [u8; 2] {
829        [Self::word(), self.0.into_bits()]
830    }
831}
832
833impl WRegister<registers::RxPwP3> {
834    /// Get the command's _command word_.
835    pub const fn word() -> u8 {
836        Self::WORD | registers::RxPwP3::ADDRESS
837    }
838
839    /// Generate the command's SPI byte sequence.
840    pub const fn bytes(&self) -> [u8; 2] {
841        [Self::word(), self.0.into_bits()]
842    }
843}
844
845impl WRegister<registers::RxPwP4> {
846    /// Get the command's _command word_.
847    pub const fn word() -> u8 {
848        Self::WORD | registers::RxPwP4::ADDRESS
849    }
850
851    /// Generate the command's SPI byte sequence.
852    pub const fn bytes(&self) -> [u8; 2] {
853        [Self::word(), self.0.into_bits()]
854    }
855}
856
857impl WRegister<registers::RxPwP5> {
858    /// Get the command's _command word_.
859    pub const fn word() -> u8 {
860        Self::WORD | registers::RxPwP5::ADDRESS
861    }
862
863    /// Generate the command's SPI byte sequence.
864    pub const fn bytes(&self) -> [u8; 2] {
865        [Self::word(), self.0.into_bits()]
866    }
867}
868
869impl WRegister<registers::FifoStatus> {
870    /// Get the command's _command word_.
871    pub const fn word() -> u8 {
872        Self::WORD | registers::FifoStatus::ADDRESS
873    }
874
875    /// Generate the command's SPI byte sequence.
876    pub const fn bytes(&self) -> [u8; 2] {
877        [Self::word(), self.0.into_bits()]
878    }
879}
880
881impl WRegister<registers::Dynpd> {
882    /// Get the command's _command word_.
883    pub const fn word() -> u8 {
884        Self::WORD | registers::Dynpd::ADDRESS
885    }
886
887    /// Generate the command's SPI byte sequence.
888    pub const fn bytes(&self) -> [u8; 2] {
889        [Self::word(), self.0.into_bits()]
890    }
891}
892
893impl WRegister<registers::Feature> {
894    /// Get the command's _command word_.
895    pub const fn word() -> u8 {
896        Self::WORD | registers::Feature::ADDRESS
897    }
898
899    /// Generate the command's SPI byte sequence.
900    pub const fn bytes(&self) -> [u8; 2] {
901        [Self::word(), self.0.into_bits()]
902    }
903}
904
905impl<const N: usize> RRxPayload<N> {
906    /// Generate the command's SPI byte sequence.
907    pub const fn bytes() -> [u8; N + 1] {
908        let mut bytes: [u8; N + 1] = [0; N + 1];
909        bytes[0] = Self::WORD;
910        bytes
911    }
912}
913
914/// Concatenate the command word and payload bytes into an array.
915#[inline(always)]
916const fn concat_word_payload<const N: usize>(word: u8, payload: [u8; N]) -> [u8; N + 1] {
917    let mut bytes: [u8; N + 1] = [0; N + 1];
918    bytes[0] = word;
919
920    let mut bytes_idx = 1;
921    while bytes_idx < N + 1 {
922        bytes[bytes_idx] = payload[bytes_idx - 1];
923        bytes_idx += 1;
924    }
925    bytes
926}
927
928impl<const N: usize> WTxPayload<N> {
929    /// Generate the command's SPI byte sequence.
930    pub const fn bytes(&self) -> [u8; N + 1] {
931        concat_word_payload(Self::WORD, self.0)
932    }
933}
934
935impl FlushTx {
936    /// Generate the command's SPI byte sequence.
937    pub const fn bytes() -> [u8; 1] {
938        [Self::WORD]
939    }
940}
941
942impl FlushRx {
943    /// Generate the command's SPI byte sequence.
944    pub const fn bytes() -> [u8; 1] {
945        [Self::WORD]
946    }
947}
948
949impl ReuseTxPl {
950    /// Generate the command's SPI byte sequence.
951    pub const fn bytes() -> [u8; 1] {
952        [Self::WORD]
953    }
954}
955
956impl Activate {
957    /// Generate the command's SPI byte sequence.
958    pub const fn bytes() -> [u8; 2] {
959        [Self::WORD, 0x73]
960    }
961}
962
963impl RRxPlWid {
964    /// Generate the command's SPI byte sequence.
965    pub const fn bytes() -> [u8; 2] {
966        [Self::WORD, 0]
967    }
968}
969
970impl<const N: usize> WAckPayload<N> {
971    /// Generate the command's SPI byte sequence.
972    pub const fn bytes(&self) -> [u8; N + 1] {
973        concat_word_payload(Self::WORD | self.pipe, self.payload)
974    }
975}
976
977impl<const N: usize> WTxPayloadNoack<N> {
978    /// Generate the command's SPI byte sequence.
979    pub const fn bytes(&self) -> [u8; N + 1] {
980        concat_word_payload(Self::WORD, self.0)
981    }
982}
983
984impl Nop {
985    /// Generate the command's SPI byte sequence.
986    pub const fn bytes() -> [u8; 1] {
987        [Self::WORD]
988    }
989}