private DebugBufferEntry(byte[] data, Flows flow) { var dt = (DateTime.Now - epoch); Timestamp = String.Format("{0}:{1}:{2}::{3}", dt.Hours, dt.Minutes, dt.Seconds, dt.Milliseconds); var now = DateTime.Now; RealTime = String.Format("{0}:{1}:{2}", dt.Minutes, dt.Seconds, dt.Milliseconds); Data = data; Flow = flow; if (Flow == Flows.Master) { DecodedData = MasterCodex.ToMasterMessage(data).ToString(); } else { DecodedData = SlaveCodex.ToSlaveMessage(data).ToString(); } }
/// <summary> /// The main parsing routine /// </summary> private void ReadAcceptorResp() { var data = PreviouslySentMasterMsg ?? GenerateNormalMessage(); // Attempt to write data to slave NotifySerialData(DebugBufferEntry.AsMaster(data)); WriteWrapper(data); // Blocks until all 11 bytes are read or we give up var resp = ReadWrapper(); // Extract only the states and events NotifySerialData(DebugBufferEntry.AsSlave(resp)); // No data was read, return!! if (resp.Length == 0) { // Do no toggle the ack return; } // Check that we have the same ACK # if (IsBadAckNumber(resp, data)) { PreviouslySentMasterMsg = data; return; } if (IsBadSlaveChecksumOk(resp)) { PreviouslySentMasterMsg = data; return; } // Otherwise we're all good - toggle ack and clear last sent message PreviouslySentMasterMsg = null; Ack ^= 1; // At this point we have sent our message and received a valid response. // Parse the response and act on any state or events that are reported. // Translate raw bytes into friendly enums var slaveMessage = SlaveCodex.ToSlaveMessage(resp); PreviousState = SlaveCodex.GetState(slaveMessage); // Raise a state changed notice for clients NotifyStateChange(PreviousState); // Multiple event may be reported at once var currentEvents = SlaveCodex.GetEvents(slaveMessage); foreach (Events e in Enum.GetValues(typeof(Events))) { // If flag is set in slave message, report event if ((currentEvents & e) == e) { NotifyEvent(e); } } // Check for cassette missing - reports every time cashbox is missing if (!SlaveCodex.IsCashboxPresent(slaveMessage)) { CashboxPresent = false; NotifyError(Errors.CashboxMissing); } // Only report the cashbox attached 1 time after it is re-attached else if (!CashboxPresent) { CashboxPresent = true; SafeEvent(OnCashboxAttached); } // Mask away rest of message to see if a note is in escrow. If this is the first // escrow message, start the escrow timeout clock if (!NoteIsEscrowed && PreviousState == States.Escrowed) { _escrowStart = DateTime.MinValue; } NoteIsEscrowed = PreviousState == States.Escrowed; // Credit bits are 3-5 of data byte 3 var value = SlaveCodex.GetCredit(slaveMessage); if (value > 0) { Credit = (byte)value; } // Per the spec, credit message is issued by master after stack event is // sent by the slave. If the previous event was stacked or returned, we // must clear the escrow command to completely release the note from // escrow state. // ReSharper disable once SwitchStatementMissingSomeEnumCasesNoDefault switch (PreviousEvents) { case Events.Stacked: NotifyCredit(Credit); // C# does not allow fallthrough so we will goto :) goto case Events.Returned; case Events.Returned: // Clear our the pending escrow command once we've stacked or returned the note EscrowCommand = EscrowCommands.None; Credit = 0; break; } // Update the events aster the check for check so as to not lose a credit message PreviousEvents = currentEvents; }
private DebugBufferEntry(byte[] data, Flows flow) { var dt = DateTime.Now - epoch; Timestamp = $"{dt.Hours}:{dt.Minutes}:{dt.Seconds}::{dt.Milliseconds}"; var now = DateTime.Now; RealTime = $"{dt.Minutes}:{dt.Seconds}:{dt.Milliseconds}"; Data = data; Flow = flow; DecodedData = Flow == Flows.Master ? MasterCodex.ToMasterMessage(data).ToString() : SlaveCodex.ToSlaveMessage(data).ToString(); }