/// <summary> /// Create a new LogDownloader /// </summary> /// <param name="isAsyncTransfer">Determines if this machine will be set up asyncronus transfers.</param> /// <param name="threadName">The name to report in closing operations for this binary socket.</param> /// <param name="closingWorker">The closing worker to add this binary socket too.</param> protected ThreadedTransferMachine(bool isAsyncTransfer, string threadName, ClosingWorker closingWorker) : base(threadName) { // add thread to the closing worker closingWorker?.AddThread(this); // initialize the StateMachine WorkerState = new StateDefinition(); if (isAsyncTransfer) { MachineFunctions.InitializeStates(WorkerStateMachine = new StepDefinition(threadName, true, WorkerState) { #region StateMachine SubSteps = new List <StepDefinition> { new StepDefinition("Transfer Packet") { Delegate = StateMachine_TransferPacket, DelayTimeMs = 500 }, new StepDefinition("Packet Timeout") { Delegate = StateMachine_PacketTimeout, DelayTimeMs = 0 }, new StepDefinition("Complete") { Delegate = StateMachine_Complete, DelayTimeMs = 200 } } #endregion // StateMachine }); } else { MachineFunctions.InitializeStates(WorkerStateMachine = new StepDefinition(threadName, true, WorkerState) { #region StateMachine SubSteps = new List <StepDefinition> { new StepDefinition("Transfer Packet") { Delegate = StateMachine_TransferPacket, DelayTimeMs = 0 }, new StepDefinition("Complete") { Delegate = StateMachine_Complete, DelayTimeMs = 200 } } #endregion // StateMachine }); } // start the StateMachine in the Complete state MachineFunctions.JumpToLast(WorkerStateMachine); // initialize ThreadingBase WorkerThreads = new List <ThreadInfo> { new ThreadInfo(new Thread(Worker), "State Machine", threadName, WorkerStateMachine) }; }
protected bool ProcessMissedPage(int page) { if (page == _missedPage) { _missedPageCount++; } else { _missedPage = page; _missedPageCount = 1; } // decide how to proceed if (_missedPageCount <= 5) { // request packet again MachineFunctions.JumpToStep("Transfer Packet", WorkerStateMachine); return(StepReturn.JumpCommandUsed); } // failed the upload, jump to end SetTransferState(TransferState.FailedLostPackets); MachineFunctions.JumpToLast(WorkerStateMachine); return(StepReturn.JumpCommandUsed); }
protected override bool StateMachine_TransferPacket(StepDefinition currentStep) { // check for connection if (!_comPortRef.IsConnected) { SetTransferState(TransferState.FailedConnection); MachineFunctions.JumpToLast(currentStep); return(StepReturn.JumpCommandUsed); } // update the users with % complete RunPercentUpdate(); var returnStrings = _comPortRef.SendCommand($"&@i{_currentPage}", 5000); // check for response if (returnStrings.Count > 0 && returnStrings[0].Contains($"&@i{_currentPage},")) { if (returnStrings[0].Contains($"&@i{_currentPage},MULTILINECOMPLETE")) { // ini downloaded SetTransferState(TransferState.Succeeded); // end the downloader MachineFunctions.JumpToLast(currentStep); return(StepReturn.JumpCommandUsed); } // we have data returnStrings[0] = returnStrings[0].Replace($"&@i{_currentPage},", ""); returnStrings.RemoveRange(returnStrings.Count - 2, 2); _fileText += string.Join("\r\n", returnStrings.ToArray()); _currentPage++; return(StepReturn.RepeatStep); } // deal with any errors switch (returnStrings[0]) { case "&@i!o": SetTransferState(_currentTransferState, "Buffer overflow!"); break; case "&@i!v": SetTransferState(_currentTransferState, "Invalid Page Number!"); break; default: break; } // we had a bad log, try again return(ProcessMissedPage(_currentPage)); }
protected override bool StateMachine_TransferPacket(StepDefinition currentStep) { // check for connection if (!_binarySocketRef.IsConnected) { SetTransferState(TransferState.FailedConnection); MachineFunctions.JumpToLast(currentStep); return(StepReturn.JumpCommandUsed); } // update the users with % complete RunPercentUpdate(); _binarySocketRef.SendBinaryCommand(CommandSets.Admin, (ushort)AdminCommands.AdminLogsRead, true, DataConversions.ConvertUInt16ToList(_currentPage)); return(StepReturn.ContinueToNext); }
protected override bool StateMachine_TransferPacket(StepDefinition currentStep) { // check for connection if (!_binarySocketRef.IsConnected) { SetTransferState(TransferState.FailedConnection); MachineFunctions.JumpToLast(currentStep); return(StepReturn.JumpCommandUsed); } // update the users with % complete RunPercentUpdate(); if (_pointer < _workingFile.Count) { if (_payloadPage != _currentPage) { // calculate read length _readLength = PageSize * PagesTransmitted; if (_pointer + _readLength > _workingFile.Count) { _readLength = _workingFile.Count - _pointer; } // load the array into a list with page information _payload.Clear(); _payload.AddRange(DataConversions.ConvertUInt16ToList(_currentPage)); _payload.AddRange(_workingFile.GetRange(_pointer, _readLength)); // update the housekeeping variables _payloadPage = _currentPage; } // send the data _binarySocketRef.SendBinaryCommand(CommandSets.Admin, (ushort)AdminCommands.AdminConfigImport, true, _payload); } else { _binarySocketRef.SendBinaryCommand(CommandSets.Admin, (ushort)AdminCommands.AdminConfigImportComplete, true); } // wait for packet return(StepReturn.ContinueToNext); }
protected override bool StateMachine_TransferPacket(StepDefinition currentStep) { // check for connection if (!_comPortRef.IsConnected) { SetTransferState(TransferState.FailedConnection); MachineFunctions.JumpToLast(currentStep); return(StepReturn.JumpCommandUsed); } // update the users with % complete RunPercentUpdate(); LogData log = null; if (_comPortRef.Protocol?.Diagnostics.GetLog(_currentPage, out log) == true) { if (log != null) { // good log, add to list _currentPage++; _logs.Add(log); } else { // all logs gathered SetTransferState(TransferState.Succeeded); // end the downloader MachineFunctions.JumpToLast(currentStep); return(StepReturn.JumpCommandUsed); } } // we had a bad log, try again return(ProcessMissedPage(_currentPage)); }
protected override bool StateMachine_TransferPacket(StepDefinition currentStep) { // check for connection if (!_comPortRef.IsConnected) { SetTransferState(TransferState.FailedConnection); MachineFunctions.JumpToLast(currentStep); return(StepReturn.JumpCommandUsed); } // update the users with % complete RunPercentUpdate(); if (_payloadPage != _currentPage) { // calculate read length _readLength = PageSize * PagesTransmitted; if (_pointer + _readLength > _workingFile.Count) { _readLength = _workingFile.Count - _pointer; } // load the array into a list with _page information _payload.Clear(); _payload.AddRange(DataConversions.ConvertUInt16ToList(_currentPage)); _payload.AddRange(_workingFile.GetRange(_pointer, _readLength)); _payload.AddRange(Checksums.Fletcher16(_payload)); // add escapes to the payload _payload.EscapeList(); // add the command to the front of the payload _payload.InsertRange(0, Encoding.ASCII.GetBytes(_command)); // update the housekeeping variables _payloadPage = _currentPage; } // send the data var returnString = _comPortRef.SendCommand(_payload, 1).FirstOrDefault(); if (returnString?.Contains($"{_command}{_currentPage},{_readLength}") == true) { // housekeeping variables _pointer += _readLength; _currentPage += PagesTransmitted; // we had a good transfer, determine next step if (_pointer == _workingFile.Count) { // we are at the end of the file, so tell the system we are done _payload.Clear(); _payload.AddRange(DataConversions.ConvertUInt16ToList(0xFFFF)); _payload.AddRange(Checksums.Fletcher16(_payload)); // add escapes to the payload _payload.EscapeList(); // add the command to the front of the payload _payload.InsertRange(0, Encoding.ASCII.GetBytes(_command)); // send command _comPortRef.SendCommand(_payload, 1); // let the user know SetTransferState(TransferState.Succeeded); // move to end MachineFunctions.JumpToLast(currentStep); return(StepReturn.JumpCommandUsed); } // not done with file, so send the next packet return(StepReturn.RepeatStep); } // switch to deal with packet error types switch (returnString) { case "&@f!c": // checksum error break; case "&@f!w": // flash write error break; case "&@f!r": // rebooting unit break; case "": // lost connection break; default: break; } // process the missed packet count return(ProcessMissedPage(_currentPage)); }
protected override bool StateMachine_TransferPacket(StepDefinition currentStep) { // check for connection if (!_comPortRef.IsConnected) { SetTransferState(TransferState.FailedConnection); MachineFunctions.JumpToLast(currentStep); return(StepReturn.JumpCommandUsed); } // update the users with % complete RunPercentUpdate(); var payloadLength = Math.Min(_workingFile.Count - _pointer, 1024); if (_payloadPage != _currentPage) { // calculate read length _readLength = PageSize * PagesTransmitted; if (_pointer + _readLength > _workingFile.Count) { _readLength = _workingFile.Count - _pointer; } // load the array into a list with _currentPage information _payload.Clear(); _payload.AddRange(DataConversions.ConvertUInt16ToList(_currentPage)); _payload.AddRange(_workingFile.GetRange(_pointer, _readLength)); _payload.AddRange(Checksums.Fletcher16(_payload)); // add escapes to the payload _payload.EscapeList(); // add the command to the front of the payload _payload.InsertRange(0, Encoding.ASCII.GetBytes(Command)); // update the housekeeping variables _payloadPage = _currentPage; } // send the data var returnString = _comPortRef.SendCommand(_payload, 1).FirstOrDefault(); if (returnString?.Contains($"{Command}{_currentPage},{payloadLength}") == true) { // housekeeping variables _pointer += payloadLength; _currentPage += PagesTransmitted; // we had a good transfer, determine next step if (_pointer == _workingFile.Count) { // we are at the end of the file, so tell the system we are done _payload.Clear(); _payload.AddRange(DataConversions.ConvertUInt16ToList(0xFFFF)); _payload.AddRange(Checksums.Fletcher16(_payload)); // add escapes to the payload _payload.EscapeList(); // add the command to the front of the payload _payload.InsertRange(0, Encoding.ASCII.GetBytes(Command)); // send command var returnStrings = _comPortRef.SendCommand(_payload, 5000); if (returnStrings.Count > 0) { if (returnStrings[0].Contains("&@us")) { // upload successfull SetTransferState(TransferState.Succeeded); // move to end MachineFunctions.JumpToLast(currentStep); return(StepReturn.JumpCommandUsed); } if (returnStrings[0].Contains("&@ue")) { // file error returnStrings[0] = returnStrings[0].Replace("&@ue", ""); returnStrings.RemoveRange(returnStrings.Count - 2, 2); var substring = string.Join("\r\n", returnStrings.ToArray()); SetTransferState(TransferState.FailedInvalidFile, $"INI Upload Failed! The INI file had the following errors:{Environment.NewLine}{substring}"); // move to end MachineFunctions.JumpToLast(currentStep); return(StepReturn.JumpCommandUsed); } } else { SetTransferState(TransferState.Failed, "Unable to parse INI file, unknown error!"); // move to end MachineFunctions.JumpToLast(currentStep); return(StepReturn.JumpCommandUsed); } } // next loop return(StepReturn.RepeatStep); } // switch to deal with packet error types switch (returnString) { case "&@u!c": SetTransferState(_currentTransferState, "Checksum Error!"); break; case "&@u!w": SetTransferState(_currentTransferState, "Data Processing Error"); break; case "&@u!s": SetTransferState(_currentTransferState, "Upload Complete"); break; case "&@u!e": SetTransferState(_currentTransferState, "Upload Error"); break; case "": SetTransferState(_currentTransferState, "Lost Connection"); break; default: break; } // process the missed packet count return(ProcessMissedPage(_currentPage)); }
/// <summary> /// Process Logs from the upload /// </summary> /// <param name="data"></param> public void ReceiveUploadLogs(List <byte> data) { SetTransferState(TransferState.FailedInvalidFile, $"INI Upload Failed! The INI file had the following errors:{Environment.NewLine}{System.Text.Encoding.UTF8.GetString(data.ToArray())}"); MachineFunctions.JumpToLast(WorkerStateMachine); }
/// <summary> /// Flag upload as successfull /// </summary> public void ReceiveUploadSuccess() { SetTransferState(TransferState.Succeeded); MachineFunctions.JumpToLast(WorkerStateMachine); }
private bool StateMachine_Searching(StepDefinition currentStep) { // get list of current system com ports var descriptions = ComPortInfo.GetDescriptions(); // clear out any old connections if (IsOpen) { IsConnected = false; CurrentConnection?.Disconnect(); } RunConnectionUpdate(); switch (TargetMode) { case ConnectionMode.AnyCom: CurrentConnection = AutoConnectComPort( descriptions.Select(s => s.Port).ToList(), ConnectionParameters); break; case ConnectionMode.SelectionRule: CurrentConnection = AutoConnectComPort( descriptions.Where(TargetSelectionRule).Select(s => s.Port).ToList(), ConnectionParameters); break; case ConnectionMode.PersistentPort: descriptions = descriptions.Where(TargetSelectionRule).ToList(); if (descriptions.Count == 1) { CurrentConnection = ConnectComPort( descriptions.Select(s => s.Port).First(), ConnectionParameters); CurrentConnection?.Connect(); if (CurrentConnection?.IsConnected != true) { CurrentConnection?.Disconnect(); CurrentConnection = null; } } else if (descriptions.Count > 1) { MachineFunctions.JumpToLast(currentStep); return(StepReturn.JumpCommandUsed); } break; default: break; } // if we didn't open a port, try again if (!IsOpen) { return(StepReturn.RepeatStep); } // we opened a port, so update the listeners ConnectionEventRegister(); RunConnectionUpdate(); // move to the next step return(StepReturn.ContinueToNext); }