ssp/types/
message_type.rs

1use crate::std::fmt;
2
3/// Type of command and response message.
4///
5/// Only command messages include the type of message in the message buffer itself.
6///
7/// Response types are inferred based on the type of command sent to the device.
8///
9/// The inference can fail. For example, if sending a command with the same
10/// [SequenceFlag](crate::SequenceFlag) value as the previous message, the device will return the
11/// response to the previous message. This happens regardless of the combination of message types.
12#[repr(u8)]
13#[derive(Clone, Copy, Debug, PartialEq, serde::Serialize, serde::Deserialize)]
14pub enum MessageType {
15    /// Resets the device.
16    Reset = 0x01,
17    /// Sets the note inhibits for the device. Establishes which notes are accepted.
18    SetInhibits = 0x02,
19    /// Single byte command turns on the bezel light when the unit is enabled.
20    DisplayOn = 0x03,
21    /// Single byte command turns off the bezel light when the unit is enabled.
22    DisplayOff = 0x04,
23    /// Single byte command to request the current setup configuration for the device.
24    SetupRequest = 0x05,
25    /// Host protocol version.
26    ///
27    /// Two byte command sets the unit to report events up to and including those found in the
28    /// specified protocol version. Please note that the highest protocol version that a unit will
29    /// support is determined by its firmware.
30    HostProtocolVersion = 0x06,
31    /// Standard polling command.
32    ///
33    /// Single byte command instructs the unit to report all the events that have occurred since the
34    /// last time a poll was sent to the unit.
35    ///
36    /// Also, represents a `Stack Note` command when a note is reported in escrow.
37    Poll = 0x07,
38    /// Returns the note to the bezel.
39    ///
40    /// Single byte command causes the validator to reject the current note
41    Reject = 0x08,
42    /// This single byte command disables the unit. This means the unit will enter its disabled state
43    /// and not execute any further commands or perform any other actions. A poll to the unit
44    /// while in this state will report disabled (0xE8).
45    Disable = 0x09,
46    /// Single byte command enables the unit. It will now respond to and execute commands.
47    Enable = 0x0a,
48    /// Starts the program firmware mode to install new firmware on the device.
49    ProgramFirmware = 0x0b,
50    /// Gets the device's serial number.
51    SerialNumber = 0x0c,
52    /// A more concise version of the [SetupRequest](Self::SetupRequest) command. Returns unit
53    /// information about the device.
54    UnitData = 0x0d,
55    /// Causes the validator to return the number of channels it is using, and the value for each
56    /// channel.
57    ChannelValueData = 0x0e,
58    /// This single byte command tells the unit that the next sequence ID will be 1. This is always
59    /// the first command sent to a unit, to prepare it to receive any further commands.
60    Synchronisation = 0x11,
61    /// Gets the last Reject Code issued by the device.
62    LastRejectCode = 0x17,
63    /// Keep the note in escrow position (for 5 seconds longer).
64    Hold = 0x18,
65    /// Gets the firmware version of the device.
66    FirmwareVersion = 0x20,
67    /// Gets the dataset version of the device.
68    DatasetVersion = 0x21,
69    /// Set the configuration status of any barcode readers present on the device.
70    SetBarcodeReaderConfiguration = 0x23,
71    /// Get the configuration status of any barcode readers present on the device.
72    GetBarcodeReaderConfiguration = 0x24,
73    /// Get the current barcode/currency mode settings.
74    GetBarcodeInhibit = 0x25,
75    /// Set the current barcode/currency mode settings.
76    SetBarcodeInhibit = 0x26,
77    /// Get the last valid barcode ticket data.
78    GetBarcodeData = 0x27,
79    /// Gets the manufacturer's extension of the device.
80    ManufacturerExtension = 0x30,
81    /// Causes the SMART Payout to empty all its stored notes to the cashbox.
82    Empty = 0x3f,
83    /// Payout notes to the customer by denomination.
84    PayoutByDenomination = 0x46,
85    /// Sets the eSSP generator prime (64-bits).
86    SetGenerator = 0x4a,
87    /// Sets the eSSP modulus (64-bits).
88    SetModulus = 0x4b,
89    /// Requests a Difie-Hellman key exchange to establish a shared secret for eSSP, i.e. the AES
90    /// key.
91    RequestKeyExchange = 0x4c,
92    /// Empty the stored notes from the device into the cash box, keeping track of the values.
93    SmartEmpty = 0x52,
94    /// Configure the bezel color for the device.
95    ConfigureBezel = 0x54,
96    /// Poll the device, requires host to ACK returned events.
97    PollWithAck = 0x56,
98    /// Causes the validator to continue processing after returning repeating
99    /// [PollWithAckResponse](crate::PollWithAckResponse) messages.
100    EventAck = 0x57,
101    /// Disables a device with an attached payout module.
102    DisablePayout = 0x5b,
103    /// Enables a device with an attached payout module to store/payout notes.
104    EnablePayout = 0x5c,
105    /// SSP Set Encryption Key - sets the fixed encryption key to the user-supplied value.
106    SetEncryptionKey = 0x60,
107    /// SSP Encryption Reset to Default - resets the fixed encryption key to the default value.
108    EncryptionReset = 0x61,
109    /// Encrypted (eSSP) message - an encrypted version of another message.
110    Encrypted = 0x7e,
111    /// Reserved for future use.
112    Reserved = 0xff,
113}
114
115impl MessageType {
116    /// Creates a new [MessageType].
117    pub const fn new() -> Self {
118        Self::Reserved
119    }
120}
121
122impl From<u8> for MessageType {
123    fn from(b: u8) -> Self {
124        match b {
125            0x01 => Self::Reset,
126            0x02 => Self::SetInhibits,
127            0x03 => Self::DisplayOn,
128            0x04 => Self::DisplayOff,
129            0x05 => Self::SetupRequest,
130            0x06 => Self::HostProtocolVersion,
131            0x07 => Self::Poll,
132            0x08 => Self::Reject,
133            0x09 => Self::Disable,
134            0x0a => Self::Enable,
135            0x0b => Self::ProgramFirmware,
136            0x0c => Self::SerialNumber,
137            0x0d => Self::UnitData,
138            0x0e => Self::ChannelValueData,
139            0x11 => Self::Synchronisation,
140            0x17 => Self::LastRejectCode,
141            0x18 => Self::Hold,
142            0x20 => Self::FirmwareVersion,
143            0x21 => Self::DatasetVersion,
144            0x23 => Self::SetBarcodeReaderConfiguration,
145            0x24 => Self::GetBarcodeReaderConfiguration,
146            0x25 => Self::GetBarcodeInhibit,
147            0x26 => Self::SetBarcodeInhibit,
148            0x27 => Self::GetBarcodeData,
149            0x30 => Self::ManufacturerExtension,
150            0x3f => Self::Empty,
151            0x46 => Self::PayoutByDenomination,
152            0x4a => Self::SetGenerator,
153            0x4b => Self::SetModulus,
154            0x4c => Self::RequestKeyExchange,
155            0x52 => Self::SmartEmpty,
156            0x54 => Self::ConfigureBezel,
157            0x56 => Self::PollWithAck,
158            0x57 => Self::EventAck,
159            0x5b => Self::DisablePayout,
160            0x5c => Self::EnablePayout,
161            0x60 => Self::SetEncryptionKey,
162            0x61 => Self::EncryptionReset,
163            0x7e => Self::Encrypted,
164            _ => Self::Reserved,
165        }
166    }
167}
168
169impl From<MessageType> for u8 {
170    fn from(m: MessageType) -> Self {
171        m as u8
172    }
173}
174
175impl From<&MessageType> for u8 {
176    fn from(m: &MessageType) -> Self {
177        (*m).into()
178    }
179}
180
181impl From<MessageType> for &'static str {
182    fn from(m: MessageType) -> Self {
183        match m {
184            MessageType::Reset => "Reset",
185            MessageType::SetInhibits => "SetInhibits",
186            MessageType::DisplayOn => "DisplayOn",
187            MessageType::DisplayOff => "DisplayOff",
188            MessageType::SetupRequest => "SetupRequest",
189            MessageType::HostProtocolVersion => "HostProtocolVersion",
190            MessageType::Poll => "Poll",
191            MessageType::Reject => "Reject",
192            MessageType::Disable => "Disable",
193            MessageType::Enable => "Enable",
194            MessageType::ProgramFirmware => "ProgramFirmware",
195            MessageType::SerialNumber => "SerialNumber",
196            MessageType::UnitData => "UnitData",
197            MessageType::ChannelValueData => "ChannelValueData",
198            MessageType::Synchronisation => "Synchronisation",
199            MessageType::LastRejectCode => "LastRejectCode",
200            MessageType::Hold => "Hold",
201            MessageType::FirmwareVersion => "FirmwareVersion",
202            MessageType::DatasetVersion => "DatasetVersion",
203            MessageType::SetBarcodeReaderConfiguration => "SetBarcodeReaderConfiguration",
204            MessageType::GetBarcodeReaderConfiguration => "GetBarcodeReaderConfiguration",
205            MessageType::GetBarcodeInhibit => "GetBarcodeInhibit",
206            MessageType::SetBarcodeInhibit => "SetBarcodeInhibit",
207            MessageType::GetBarcodeData => "GetBarcodeData",
208            MessageType::ManufacturerExtension => "ManufacturerExtension",
209            MessageType::Empty => "Empty",
210            MessageType::PayoutByDenomination => "PayoutByDenomination",
211            MessageType::SetGenerator => "SetGenerator",
212            MessageType::SetModulus => "SetModulus",
213            MessageType::RequestKeyExchange => "RequestKeyExchange",
214            MessageType::SmartEmpty => "SmartEmpty",
215            MessageType::ConfigureBezel => "ConfigureBezel",
216            MessageType::PollWithAck => "PollWithAck",
217            MessageType::EventAck => "EventAck",
218            MessageType::DisablePayout => "DisablePayout",
219            MessageType::EnablePayout => "EnablePayout",
220            MessageType::SetEncryptionKey => "SetEncryptionKey",
221            MessageType::EncryptionReset => "EncryptionReset",
222            MessageType::Encrypted => "Encrypted",
223            MessageType::Reserved => "Reserved",
224        }
225    }
226}
227
228impl From<&MessageType> for &'static str {
229    fn from(m: &MessageType) -> Self {
230        (*m).into()
231    }
232}
233
234impl fmt::Display for MessageType {
235    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
236        write!(f, "{}", <&str>::from(self))
237    }
238}
239
240impl_default!(MessageType);