//----------------------------------------------------------------------------
//
// Copyright © 2009-2014, Intel Corporation. All rights reserved.
//
// File: LogicLayer.cs
//
//----------------------------------------------------------------------------
using System;
using UCT.Forms;
using UCT.Utils;
using System.Text;
using System.Timers;
using System.Windows.Forms;
using System.Collections.Generic;
using System.Threading;
namespace UCT
{
///
/// The main class - hold the logic behind the operations
///
public class LogicLayer : IUserConsentFlow, IDisposable
{
#region - Dictionaries -
// OptInService Functions Statuses
Dictionary StatusCodes = new Dictionary()
{
{0, "Success"},
{1, "Internal error"},
{2, "Invalid state"},
{3, "Operation is blocked"},
{2066, "Invalid credentials"}
};
// Power state change return values
Dictionary PowerStatusCode = new Dictionary()
{
{0, "succuess"},
{1, "Operation is not supported"},
{2, "Unknown or unspecified error"},
{3, "Operation cannot be completed within timeout period"},
{4, "Operation failed"},
{5, "Invalid parameter"},
{6, "In use"},
{4099, "Invalid power transition"},
{4096, "Reserved"}
};
#endregion
#region - Consts -
// Hold the time (in minutes) required for detecting if sprite is supported
private const int SPRITE_SUPPORTED_TIMEOUT = 15;
#endregion
#region - Private Members -
// The GUI instance
private UserInterface _UI;
// The target system instance
private TargetSystem _targetSystem;
// Indicates if 15 seconds has elapsed when establishing if sprite is supported.
private bool _timeHadElapsed = false;
// Indicate if Sprite is suppported on the remote system
private bool _spriteIsSupported = false;
// Indicates if power operation was successful
private bool _powerOperationSucceed = false;
// Indicates if the previous optInState was 'in-session'.
private bool _isLastStateInSession;
// Reflects the result of the graceful shutdown
private bool _gracfulResult = false;
// Indicate whether the user cancel the progress bar
private bool _userCancel;
// Holds the optInState after connection was established.
// This is used for the code timer settings.
private int _firstStateUpdateAfterConnect = 0;
// Indicate whether the opt in state was changed
private bool _statusChanged = false;
// Indicate whether to reboot after shutdown or just log off
private bool _rebootAfterShutdown;
// Power operations timers
private System.Timers.Timer _timer, _timerBoot, _timerGraceful;
int _spriteCounter = 0, _bootCounter = 0;
// Hold the system power state
private PowerState _powerState;
#endregion
#region - Timer Events -
///
/// Timer that running when executing graceful shutdown
///
///
///
void timerGraceful_Elapsed(object sender, ElapsedEventArgs e)
{
_timerGraceful.Enabled = false;
if (_rebootAfterShutdown)
{
WriteLog(LogLevel.BASIC, string.Format(Properties.Resources.EXECUTE_GRACEFUL_RESET_MESSAGE, Configuration.BasicSettings.GetInstance().AmtHost), LogInteraction.Information);
}
else
{
WriteLog(LogLevel.BASIC, string.Format(Properties.Resources.EXECUTE_GRACEFUL_SHUTDOWN_MESSAGE, Configuration.BasicSettings.GetInstance().AmtHost), LogInteraction.Information);
}
if (_targetSystem.PerfomGracefulShutDown(_rebootAfterShutdown))
{
_gracfulResult = true;
_UI.stopProgress = true;
_timerGraceful.Stop();
_timerGraceful.Close();
}
else
{
_UI.stopProgress = true;
_gracfulResult = false;
_timerGraceful.Stop();
_timerGraceful.Close();
}
}
///
/// Timer that running when detecting if sprite is supported
///
///
///
private void OnShortTimedEvent(object source, ElapsedEventArgs e)
{
if (_spriteCounter < SPRITE_SUPPORTED_TIMEOUT)
{
_spriteCounter++;
OptInState state = _targetSystem.GetOptInState();
if (state == OptInState.Displayed)
{
WriteLog(LogLevel.DETAILED, string.Format(Properties.Resources.GETTING_OPT_IN_STATE_MESSAGE, state.ToString()), LogInteraction.FWOperation);
// Disable the timers
_spriteIsSupported = true;
_UI.stopProgress = true;
_timer.Stop();
_timer.Close();
}
}
else
{
_timeHadElapsed = true;
_UI.stopProgress = true;
_timer.Stop();
_timer.Close();
}
}
///
/// Timer that running when performing AMT reboot
///
///
///
void timerBoot_Elapsed(object sender, ElapsedEventArgs e)
{
_bootCounter++;
// Check if time had elapsed, or state was changed to the desired one.
if ((_bootCounter >= SPRITE_SUPPORTED_TIMEOUT) || (_targetSystem.GetPowerState() == _powerState))
{
_UI.stopProgress = true;
_timerBoot.Stop();
_timerBoot.Close();
}
}
public uint GetOptInTimeOut()
{
return _targetSystem.UctOperation.GetOptInTimeout();
}
public bool CheckOptInTimeoutSupport()
{
return (_targetSystem.UctOperation.CheckOptInTimeoutSupport());
}
public bool Check3DisplaysSupport()
{
return (_targetSystem.UctOperation.CheckThirdScreenSupport());
}
public bool CheckLinkProtectionSupport()
{
return (_targetSystem.WirelessOperation.CheckLinkProtectionSupport());
}
public void SetOptInTimeOut(uint time)
{
try
{
UpdateGUIMessages(LogLevel.BASIC, "Settings the Opt-In timeout to: " + time + "seconds",
LogInteraction.UserOperation, "Setting the Opt-In timeout to: " + time + " seconds");
_targetSystem.SetOptInTimeout(time);
_UI.DisplayStatusBar("Opt-In timeout was set successfully");
}
catch (UCTException ex)
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite),
LogInteraction.Error, "Failed to set the Opt-In timeout");
_UI.DisplayMessage("Set Opt-In timeout failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
catch (Exception ex)
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite),
LogInteraction.Error, "Failed to set the Opt-In timeout");
_UI.DisplayMessage("Set Opt-In timeout failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
}
#endregion
#region - Constructors and Design pattern methods -
///
/// Constructor
///
public LogicLayer()
{
_timer = new System.Timers.Timer();
_timerBoot = new System.Timers.Timer();
_timerGraceful = new System.Timers.Timer();
_timerBoot.Elapsed += new ElapsedEventHandler(timerBoot_Elapsed);
_timerGraceful.Elapsed += new ElapsedEventHandler(timerGraceful_Elapsed);
_timer.Elapsed += new ElapsedEventHandler(OnShortTimedEvent);
_timerBoot.Interval = 1000;
_timer.Interval = 1000; // Set the Interval to 1 second
_isLastStateInSession = false;
}
///
/// Register the GUI layer
///
///
public void RegisterUI(UserInterface ui)
{
_UI = ui;
}
///
/// Register the target system layer
///
///
public void RegisterTargetSystem(TargetSystem trs)
{
_targetSystem = trs;
}
#endregion
#region - Methods -
#region - Main Methods Flow -
///
/// Canceling user consent
///
///
public void CancelConsent()
{
try
{
// Writing relevant messages to log and status bar
UpdateGUIMessages(LogLevel.BASIC, Properties.Resources.CANCELING_USER_CONSENT_LOG_MESSAGE,
LogInteraction.UserOperation, Properties.Resources.CANCELING_USER_CONSENT_STATUS_BAR_MESSAGE);
// Check if cancel is allowed: i.e. if there is no Redirection of KVM open session.
OptInState oiState = _targetSystem.GetOptInState();
if (oiState == OptInState.InSession)
{
_UI.DisplayMessage(Properties.Resources.CANCEL_USER_CONSENT_IN_SESSION_MESSAGE, Properties.Resources.CANCEL_USER_CONSENT_PROGRESS_BAR_MESSAGE, MessageType.ERROR);
UpdateGUIMessages(LogLevel.BASIC, Properties.Resources.CANCEL_USER_CONSNET_IN_SESSION_ERROR_MESSAGE,
LogInteraction.Error, "Cancel opertion failed");
return;
}
if (oiState == OptInState.NotStarted)
{
UpdateGUIMessages(LogLevel.DETAILED, "Invoking cancel consent is not required since the User Consent state is already 'NotStarted'",
LogInteraction.Information, "Cancel opertion completed successfully");
return;
}
CancelUserConsentProcess();
}
catch (UCTException ex)
{
_UI.changeMouse(Cursors.Default);
_UI.DisplayMessage(string.Format(Properties.Resources.OPERATION_FAILED_ERROR_MESSAGE, ex.Message), Properties.Resources.OPERATION_FAILED, MessageType.ERROR);
UpdateGUIMessages(LogLevel.BASIC, string.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()),
LogInteraction.Error, Properties.Resources.CANCEL_USER_CONSENT_FAILURE);
}
catch (Exception ex)
{
_UI.changeMouse(Cursors.Default);
_UI.DisplayMessage(ex.Message, Properties.Resources.OPERATION_FAILED, MessageType.ERROR);
UpdateGUIMessages(LogLevel.BASIC, string.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()),
LogInteraction.Error, Properties.Resources.CANCEL_USER_CONSENT_FAILURE);
}
}
///
/// Canceling the user consent (include just the FW call, without the state checking)
///
private void CancelUserConsentProcess()
{
_UI.changeMouse(Cursors.WaitCursor);
// Performing the cancel operation
uint res = _targetSystem.CancelConsent();
_UI.changeMouse(Cursors.Default);
if (res != 0)
{
_UI.DisplayMessage("Cancel consent operation failed with error code: " + res + " - " + StatusCodes[res], Properties.Resources.CANCEL_USER_CONSENT_FAILURE, MessageType.ERROR);
UpdateGUIMessages(LogLevel.BASIC, string.Format(Properties.Resources.CANCEL_USER_CONSENT_FAILURE_ERROR_CODE, res),
LogInteraction.Error, "Cancel operation failed");
}
else
{
_UI.DisplayStatusBar("Cancel operation completed successfully");
}
}
///
/// Start user consent flow
///
public void StartConsent()
{
try
{
_UI.changeMouse(Cursors.WaitCursor);
RunFullFlow();
_UI.changeMouse(Cursors.Default);
}
catch (UCTException ex)
{
_UI.changeMouse(Cursors.Default);
_UI.DisplayMessage(string.Format(Properties.Resources.OPERATION_FAILED_ERROR_MESSAGE, ex.Message), Properties.Resources.OPERATION_FAILED, MessageType.ERROR);
UpdateGUIMessages(LogLevel.BASIC, string.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite),
LogInteraction.Error, Properties.Resources.STARTING_CONSNET_FAILED);
}
catch (Exception ex)
{
_UI.changeMouse(Cursors.Default);
_UI.DisplayMessage(Properties.Resources.UNKNOWN_ERROR, Properties.Resources.OPERATION_FAILED, MessageType.ERROR);
UpdateGUIMessages(LogLevel.BASIC, string.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite),
LogInteraction.Error, Properties.Resources.STARTING_CONSNET_FAILED);
}
}
///
/// Sent the OptIn code
///
///
public void SendCode(uint code)
{
try
{
UpdateGUIMessages(LogLevel.BASIC, "Sending the optInCode",
LogInteraction.UserOperation, "Sending the consent code...");
uint res = _targetSystem.SendCode(code);
if (res != 0)
{
UpdateGUIMessages(LogLevel.BASIC, "Send User Consent code failed with error code: " + res,
LogInteraction.FWOperation, "Send consent code operation failed");
_UI.DisplayMessage("Send Code operation failed with error code: " + res + ", " + StatusCodes[res], "Operation Failed", MessageType.ERROR);
return;
}
else
{
UpdateGUIMessages(LogLevel.BASIC, "Code was sent successfully, consent was obtained",
LogInteraction.FWOperation, "Code was sent successfully, consent was obtained");
_UI.DisplayMessage("Code was submitted successfully, consent was obtained.\nOperations that require consent can be performed.", "", MessageType.INFO);
}
}
catch (UCTException ex)
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite),
LogInteraction.Error, "Failed to send the consent code");
_UI.DisplayMessage("Send consent code failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
catch (Exception ex)
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()),
LogInteraction.Error, "Failed to send the consent code");
_UI.DisplayMessage("Send consent code failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
}
#endregion
#region - Boot Methods -
///
/// This method try to reboot the system, first gracefully (via OS), if failed - try AMT shutdown
///
private void RebootSystem(LinkInterface linkInterface)
{
// Perform graceful shutdown just if the user ask for
if (Properties.Settings.Default.USE_GRACFUL_SHUTDOWN_BEFORE_AMT_REBOOT)
{
if (!PerformGracefulShutdown())
return;
// If we are connected over wireless interface, we must set the link preference to
// ME before reboot the system (otherwise, connection will lost), but because that graceful shutdown
// is a WinAPI command in order this command to success the link must be 'Host'.
// So we first send the graceful shutdown command and then start the loop of SetLinkPrefernce
if (linkInterface == LinkInterface.Wireless)
_targetSystem.StartLinkPreferenceThread(true);
// If the graceful operation failed - ask user if to reboot with AMT.
if (!_gracfulResult)
{
UpdateGUIMessages(LogLevel.BASIC, Properties.Resources.GRACEFUL_SHUTDOWN_FAILED,
LogInteraction.Error, "Graceful reboot operation failed");
if (_UI.DisplayMessage(Properties.Resources.GRACEFUL_SHUTDOWN_MESSAGE_BOX_MESSAGE,
Properties.Resources.OPERATION_FAILED, MessageType.QUESTION) == DialogResult.Yes)
{
// Perform AMT Shutdown
if (!PerformAMTShutDown(PowerState.MasterBusReset))
return;
}
}
else
{
UpdateGUIMessages(LogLevel.DETAILED, "Graceful reboot operation completed successfully",
LogInteraction.FWOperation, "Graceful reboot operation completed successfully");
}
}
else
{
// Reboot when interface is wireless required set link preference to ME before executing the operation.
if (linkInterface == LinkInterface.Wireless)
_targetSystem.StartLinkPreferenceThread(true);
// Perform AMT Shutdown
if (!PerformAMTShutDown(PowerState.MasterBusReset))
return;
}
}
///
/// Execute graceful shutdown on the target system
///
/// Indicate if the progress bar has 'Cancel' option, this button is used for cancel
/// the consent flow (e.g. reset the opt in state to NotStarted)
/// true - continue the flow, false - abort the flow
public bool PerformGracefulShutdown(bool hasCancel, bool hasSkip, bool hasReboot)
{
try
{
// Indicate whether we need reboot after or not.
_rebootAfterShutdown = hasReboot;
// Update status bar and log
if (hasReboot)
UpdateGUIMessages(LogLevel.BASIC, Properties.Resources.GRACEFUL_REBOOT_LOG_MESSAGE,
LogInteraction.UserOperation, Properties.Resources.GRACEFUL_REBOOT_STATUS_BAR_MESSAGE);
else
UpdateGUIMessages(LogLevel.BASIC, Properties.Resources.GRACEFUL_SHUTDOWN_LOG_MESSAGE,
LogInteraction.UserOperation, Properties.Resources.GRACEFUL_SHUTDOWN_STATUS_BAR_MESSAGE);
// Reset all the progress bar properties to their default values
_UI.stopProgress = _gracfulResult = false;
// Start the graceful shutdown timer
_timerGraceful.Start();
DialogResult dResult;
if (hasReboot)
dResult = _UI.RunProgressBar(Properties.Resources.GRACEFUL_REBOOT_PROGRESS_BAR,
Properties.Resources.GRACEFUL_REBOOT_HEADER, hasCancel, hasSkip);
else
dResult = _UI.RunProgressBar(Properties.Resources.GRACEFUL_SHUTDOWN_PROGRESS_BAR,
Properties.Resources.GRACEFUL_SHUTDOWN_HEADER, hasCancel, hasSkip);
if (dResult != DialogResult.Cancel)
{
_timerGraceful.Stop();
_timerGraceful.Enabled = false;
UpdateGUIMessages(LogLevel.BASIC, "Reboot operation was canceled by the user",
LogInteraction.UserOperation, "Power operation was aborted");
_UI.stopProgress = true;
// Choosing 'Cancel' in the progress bar will cancel the flow (Skip - for stop the flow at this point)
if (dResult == DialogResult.Ignore)
{
CancelUserConsentProcess();
return false;
}
_UI.RefreshScreen();
}
if (!_gracfulResult)
{
_UI.DisplayStatusBar(hasReboot ? "Graceful reset failed" : "Graceful shutdown failed");
}
else
{
// Indicate the grageful shutdown succeed
if (hasReboot)
UpdateGUIMessages(LogLevel.BASIC, "Graceful reset completed successfully", LogInteraction.Information, "Graceful reset completed successfully");
else
UpdateGUIMessages(LogLevel.BASIC, "Graceful shutdown completed successfully", LogInteraction.Information, "Graceful shutdown completed successfully");
}
return true;
}
catch (UCTException ex)
{
if (hasReboot)
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()),
LogInteraction.Error, "Graceful reset failed");
_UI.DisplayMessage("Graceful reset failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
else
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()),
LogInteraction.Error, "Graceful shutdown failed");
_UI.DisplayMessage("Graceful shutdown failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
}
catch (Exception ex)
{
if (hasReboot)
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()),
LogInteraction.Error, "Graceful reset failed");
_UI.DisplayMessage("Graceful reset failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
else
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()),
LogInteraction.Error, "Graceful shutdown failed");
_UI.DisplayMessage("Graceful shutdown failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
}
return false;
}
///
/// Execute AMT shutdown on the target system
///
/// Indicate if the progress bar has 'Cancel' option, this button is used for cancel
/// the consent flow (e.g. reset the opt in state to NotStarted)
/// true - continue the flow, false - abort the flow
public bool PerformAMTShutDown(PowerState state, bool hasCancel, bool hasSkip)
{
try
{
// Update status bar and log
UpdateGUIMessages(LogLevel.BASIC, string.Format(Properties.Resources.PERFORMING_POWER_OPERATION_LOG, state.ToString()),
LogInteraction.UserOperation, Properties.Resources.PERFORMING_POWER_OPERATION_STATUS_BAR);
// Reset all parameters to default values
_powerOperationSucceed = false;
_bootCounter = 0;
_powerState = state;
DialogResult dResult = DialogResult.Cancel;
Thread _thread = new Thread(new ThreadStart(()=>{
UserInterface _UI1 = new UserInterface();
// Display a progress bar until power state is changed, or 15 seconds had elapsed.
_timerBoot.Start();
_UI1.stopProgress = false;
dResult = _UI1.RunProgressBar("Performing power operation on the remote system...",
"Power Operation in progress", false, false);
}));
//end
_thread.Start();
// Execute the power operation
WriteLog(LogLevel.DETAILED, "AMT_AssociatedPoweManagerService.ChnagePowerState was executed", LogInteraction.FWOperation);
uint res = _targetSystem.ChangePowerState(state);
_powerOperationSucceed = res == 0 ? true : false;
_thread.Abort();
if (dResult != DialogResult.Cancel)
{
_timerBoot.Stop();
_timerBoot.Enabled = false;
_UI.stopProgress = true;
UpdateGUIMessages(LogLevel.BASIC, "Power operation was canceled by the user",
LogInteraction.UserOperation, "Power operation was aborted");
// Choosing 'Cancel' in the progress bar will cancel the flow (Skip - for stop the flow at this point)
if (dResult == DialogResult.Ignore)
{
CancelUserConsentProcess();
return false;
}
}
// Check if power operation failed
if (_powerOperationSucceed)
{
UpdateGUIMessages(LogLevel.BASIC, "Power Operation: " + state.ToString() + " completed successfully",
LogInteraction.FWOperation, "Power operation completed successfully");
}
else
{
_UI.DisplayMessage("Power Operation failed with error code: " + res + ", " +
(PowerStatusCode.ContainsKey(res) ? PowerStatusCode[res] : PowerStatusCode[2]),
"Power Operation Failed", MessageType.ERROR);
}
}
catch (UCTException ex)
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()),
LogInteraction.Error, "Graceful shutdown failed");
_UI.DisplayMessage("Power operation failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
catch (Exception ex)
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()),
LogInteraction.Error, "Graceful shutdown failed");
_UI.DisplayMessage("Power operation failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
_UI.RefreshScreen();
return true;
}
#endregion
#region - Utils Methods
///
/// Change the connection address (used when changing the host name via the combo box)
///
///
internal bool ChangeConnectionAddress()
{
try
{
// Update log and status bar
UpdateGUIMessages(LogLevel.BASIC, "Connecting to: " + Configuration.GetInstance().Basic.AmtHost,
LogInteraction.UserOperation, "Connecting to the remote system...");
// Try to establish connection
if (Configuration.GetInstance().InitWSManClient() != UCT.ConnectionStatus.Connected)
return false;
if (CertificateUtils.ValidateCertificate())
{
SetDefaultValues();
return true;
}
return false;
}
// Connection failed
catch (Exception e)
{
// Update log and status bar
UpdateGUIMessages(LogLevel.BASIC, "Exception was thrown: " + e.Message,
LogInteraction.Error, "Failed to connect to the remote system");
_targetSystem.StartPolling(false);
SetApplicationToUnknown();
_UI.DisplayMessage(e.Message, "Failed to connect to the remote system", MessageType.ERROR);
_UI.connectionState = ConnectionState.DISCONNECTED;
_UI.ChangeGuiToDisconnect(ConnectionState.DISCONNECTED);
_UI.RefreshScreen();
}
return false;
}
///
/// Set the application to its default values
///
public void SetDefaultValues()
{
try
{
_targetSystem.SetDefaultOptInState();
_targetSystem.SetDefaultPowerState();
_isLastStateInSession = false;
_targetSystem.StartPolling(true);
_firstStateUpdateAfterConnect = 0;
UpdateGUIMessages(LogLevel.BASIC, "Successfully Connected to: " + Configuration.GetInstance().Basic.AmtHost,
LogInteraction.Connection, "Connected to the remote system");
_UI.connectionState = ConnectionState.CONNECTED;
_UI.ChangeGuiToDisconnect(ConnectionState.CONNECTED);
}
catch (Exception ex)
{
WriteLog(LogLevel.DETAILED, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()),
LogInteraction.Error);
}
}
///
/// Get the statistics tab information
///
///
public Dictionary GetStatisticsParams()
{
WriteLog(LogLevel.BASIC, "Getting connection parameters", LogInteraction.FWOperation);
return _targetSystem.GetConnectionParameters();
}
///
/// Open the log file (in notepad)
///
public void ViewLog()
{
try
{
LogManager.GetInstance().ViewLogFile();
}
catch (UCTException e)
{
_UI.DisplayMessage(e.Message, "Failed to open the Log", MessageType.ERROR);
}
}
///
/// Write a line to the log
///
///
///
///
public void WriteLog(LogLevel level, string message, LogInteraction interaction)
{
try
{
// Adding the operation details to the log file
StringBuilder line = LogManager.WriteOperation(level, message, interaction);
if (line.ToString() != String.Empty)
{
// Adding the operation details to the log viewer
_UI.WriteToLog(line.ToString(), interaction);
}
}
catch (Exception) { }
}
///
/// Update the GUI - write the current operation to the log and status bar
///
///
///
///
///
private void UpdateGUIMessages(LogLevel logLevel, string logMessage, LogInteraction logInteraction, string statusbarMessage)
{
WriteLog(logLevel, logMessage, logInteraction);
_UI.DisplayStatusBar(statusbarMessage);
}
///
/// Check if meanwhile, the consent state changed to disconnect
///
///
private bool EnsureRelevantState()
{
if (_targetSystem.GetOptInState() == OptInState.Displayed)
{
_UI.DisplayMessage("This operation is not necessary since the consent state already changed to display.\nOperation aborted", "Information", MessageType.INFO);
return false;
}
return true;
}
#endregion
#region - Polling Methods -
///
/// This is the main function - once the opt in state property is changed, this method is called
///
///
public void UpdateOptInState(OptInState state)
{
try
{
_UI.SetOptInState(state);
// The first state is not 'NotStarted' - the timer should be disable (Display warning?)
if (_firstStateUpdateAfterConnect++ == 0 && (state == OptInState.Received || state == OptInState.Displayed || state == OptInState.Requested))
{
// The first machine state is Display/Recieve/Requested
_UI.SetTimerState(TimerStatus.DISABLE);
_UI.ChangeTimerNote("The Timer cannot be set at this state");
}
else
{
switch (state)
{
case OptInState.Unknown:
{
_UI.SetTimerState(TimerStatus.DISABLE);
_UI.ChangeTimerNote(string.Empty);
break;
}
case OptInState.NotStarted:
{
_UI.SetTimerState(TimerStatus.DISABLE);
_UI.ChangeTimerNote("Timer is activated once the consent code is recieved");
break;
}
case OptInState.Requested:
{
_UI.ChangeTimerNote("Consent code expiration timeout started");
break;
}
case OptInState.Displayed:
{
_UI.ChangeTimerNote("Consent code expiration timeout started");
break;
}
case OptInState.InSession:
{
// Time is not running but its value is 15
_UI.SetTimerState(TimerStatus.FREEZE);
_UI.ChangeTimerNote("Timer is reset when a session is opened");
break;
}
case OptInState.Received:
{
// If the previous state was "InSession" - timer is start for the beginning
_UI.SetTimerState(TimerStatus.RUN);
_UI.ChangeTimerNote(string.Empty);
break;
}
}
}
switch (state)
{
case OptInState.Unknown:
SetApplicationToUnknown();
break;
case OptInState.InSession:
SetApplicationToInSession();
break;
case OptInState.NotStarted:
SetApplicationToNotStarted();
break;
case OptInState.Requested:
SetApplicationToRequested();
break;
case OptInState.Displayed:
SetApplicationToDisplayed();
break;
case OptInState.Received:
SetApplicationToRecieved();
break;
}
// Update this value to indicate if last state was in-session. this is used to setup the code timer.
_isLastStateInSession = (state == OptInState.InSession) ? true : false;
}
catch (UCTException ex)
{
_UI.SetPowerState(PowerState.Unknown);
_UI.DisplayMessage(ex.Message, "Operation Failed", MessageType.ERROR);
WriteLog(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()), LogInteraction.FWOperation);
}
catch (Exception ex)
{
WriteLog(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()), LogInteraction.FWOperation);
_UI.DisplayMessage(ex.Message, "Operation Failed", MessageType.ERROR);
}
}
///
/// Set the tool to 'Unknown' state
///
public void SetApplicationToUnknown()
{
if (!_statusChanged)
{
_UI.DisplayStatusBar("Not Connected");
WriteLog(LogLevel.BASIC, "Connection to: " + Configuration.BasicSettings.GetInstance().AmtHost + " was lost", LogInteraction.Error);
// Stop the polling properties
_targetSystem.StartPolling(false);
// Change statistics to 'Not - Available'
_UI.InitStatisticsTab(false);
// Changed the connection icon indication
_UI.ChangeConnectionIcon(false);
// Disable tab operations
_UI.InitOperationTab(false);
// Disable start / cancel buttons
_UI.ChangeMainButtonsStatus(false);
// Disable advance tab
_UI.InitAdvancedTab(false);
// Change the power state label
_UI.ChangePowerStateLabel(false);
// Stop the timer
_UI.SetTimerState(TimerStatus.DISABLE);
// Change the GUI to indicate disconnection
_UI.ChangeGuiToDisconnect(ConnectionState.DISCONNECTED);
_UI.SetConnectioDetailsToUnknown(false);
_statusChanged = true;
}
}
///
/// Set the tool to 'Not Started' state
///
private void SetApplicationToNotStarted()
{
WriteLog(LogLevel.DETAILED, "OptInState was Changed to 'Not Started'", LogInteraction.FWOperation);
// Enable the main button
_UI.SetStartCancelButtonState(true);
// Enable start / cancel buttons
_UI.ChangeMainButtonsStatus(true);
// Start the polling properties
_targetSystem.StartPolling(true);
// Update statistics
_UI.InitStatisticsTab(true);
// Changed the connection icon indication
_UI.ChangeConnectionIcon(true);
// Disable tab operations
_UI.InitOperationTab(false);
// Enable advance tab
_UI.InitAdvancedTab(true);
// Change the GUI controls to indicate connection
_UI.ChangeGuiToDisconnect(ConnectionState.CONNECTED);
// Stop the link preference polling
_targetSystem.StartLinkPreferenceThread(false);
_statusChanged = false;
}
///
/// Set the tool to 'Displayed' state
///
private void SetApplicationToDisplayed()
{
WriteLog(LogLevel.DETAILED, "OptInState was Changed to 'Requested'", LogInteraction.FWOperation);
// Start polling
_targetSystem.StartPolling(true);
// Set the main button to 'Cancel'
_UI.SetStartCancelButtonState(false);
// Update statistics
_UI.InitStatisticsTab(true);
// Init operation tab
_UI.InitOperationTab(true);
// Move the focus to the code control
_UI.MoveFocousToCodeFrame();
// Changed the connection icon indication
_UI.ChangeConnectionIcon(true);
// Enable start / cancel buttons
_UI.ChangeMainButtonsStatus(true);
// Enable advance tab
_UI.InitAdvancedTab(true);
// Change the GUI to indicate connection
_UI.ChangeGuiToDisconnect(ConnectionState.CONNECTED);
_statusChanged = false;
}
///
/// Set the tool to 'Requested' state
///
private void SetApplicationToRequested()
{
WriteLog(LogLevel.DETAILED, "OptInState was Changed to 'Requested'", LogInteraction.FWOperation);
// Start (continue...) the polling
_targetSystem.StartPolling(true);
// Change the main button to cancel
_UI.SetStartCancelButtonState(false);
// Update statistics
_UI.InitStatisticsTab(true);
// Changed the connection icon indication
_UI.ChangeConnectionIcon(true);
// Disable tab operations
_UI.InitOperationTab(false);
// Enable start / cancel buttons
_UI.ChangeMainButtonsStatus(true);
// Enable advance tab
_UI.InitAdvancedTab(true);
// Change the GUI to indiacte connection
_UI.ChangeGuiToDisconnect(ConnectionState.CONNECTED);
_statusChanged = false;
}
///
/// Set the tool to 'Recieved' state
///
private void SetApplicationToRecieved()
{
WriteLog(LogLevel.DETAILED, "OptInState was Changed to 'Received'", LogInteraction.FWOperation);
// Start the polling
_targetSystem.StartPolling(true);
// Set the main button to cancel
_UI.SetStartCancelButtonState(false);
// Update statistics
_UI.InitStatisticsTab(true);
// Changed the connection icon indication
_UI.ChangeConnectionIcon(true);
// Disable tab operations
_UI.ChangeSendCodeStatus(false);
// Enable start / cancel buttons
_UI.ChangeMainButtonsStatus(true);
// Enable advanced tab
_UI.InitAdvancedTab(true);
// Change the GUI to indicate connection
_UI.ChangeGuiToDisconnect(ConnectionState.CONNECTED);
_statusChanged = false;
}
///
/// Set the tool to 'In Session' state
///
private void SetApplicationToInSession()
{
WriteLog(LogLevel.DETAILED, "OptInState was Changed to 'In-Session'", LogInteraction.FWOperation);
// Start (continue...) the polling
_targetSystem.StartPolling(true);
// Set the main button to enable
_UI.SetStartCancelButtonState(false);
// Update statistics
_UI.InitStatisticsTab(true);
// Changed the connection icon indication
_UI.ChangeConnectionIcon(true);
// Disable tab operation - BUT NOT THE CLOCK
_UI.ChangeSendCodeStatus(false);
// Enable start / cancel buttons
_UI.ChangeMainButtonsStatus(true);
// Enable advance tab
_UI.InitAdvancedTab(true);
// Change the GUI to indicate connection
_UI.ChangeGuiToDisconnect(ConnectionState.CONNECTED);
_statusChanged = false;
}
///
/// Update the power state label
///
///
public void UpdatePowerState(PowerState ps)
{
try
{
_UI.SetPowerState(ps);
// Update the power state combo-box
_UI.FillOperationOptions(ps);
}
catch (UCTException ex)
{
_UI.SetPowerState(PowerState.Unknown);
_UI.DisplayMessage(ex.Message, "Operation Failed", MessageType.ERROR);
WriteLog(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()), LogInteraction.FWOperation);
}
catch (Exception ex)
{
_UI.SetPowerState(PowerState.Unknown);
_UI.DisplayMessage(ex.Message, "Operation Failed", MessageType.ERROR);
WriteLog(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite.ToString()), LogInteraction.FWOperation);
}
}
public OptInState CheckOptInState()
{
return _targetSystem.GetOptInState();
}
#endregion
#region - Target system method -
#region - Wireless Methods -
///
/// Set the link preference
///
///
///
internal void SetLinkPreference(LinkControl link, uint timeout)
{
try
{
UpdateGUIMessages(LogLevel.BASIC, string.Format("Setting the link preference to: {0} {1}", link,
(link == LinkControl.ME) ? " for " + timeout + " seconds" : string.Empty),
LogInteraction.UserOperation, "Setting the link preference to " + link + "...");
uint res = _targetSystem.SetLinkPreference(link, timeout);
if (res != 0)
{
UpdateGUIMessages(LogLevel.BASIC, "SetLinkPreference failed with error code: " + res,
LogInteraction.Error, "Failed to set the link preference");
}
else
{
_UI.DisplayStatusBar("Link preference was set successfully");
_targetSystem.WirelessOperation.GetWirelessLinkState(this);
}
}
catch (UCTException ex)
{
_UI.DisplayMessage("Setting the link preference failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite),
LogInteraction.Error, "Failed to set the link preference");
}
catch (Exception ex)
{
_UI.DisplayMessage(String.Format(Properties.Resources.EXCEPTION_WAS_THROWN, ex.Message), "Operation Failed", MessageType.ERROR);
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite),
LogInteraction.Error, "Failed to set the link preference");
}
}
///
/// Update the wireless details (link control, lan id ect.)
///
///
///
internal void UpdateWirelessDetails(LinkControl linkControl, LinkControl linkPreference)
{
try
{
_UI.SetWirelessDetails(linkControl, linkPreference);
}
catch (UCTException ex)
{
_UI.SetPowerState(PowerState.Unknown);
_UI.DisplayMessage(ex.Message, "Operation Failed", MessageType.ERROR);
WriteLog(LogLevel.DETAILED, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite),
LogInteraction.Error);
}
catch (Exception ex)
{
_UI.SetPowerState(PowerState.Unknown);
WriteLog(LogLevel.DETAILED, String.Format(Properties.Resources.EXCEPTION_WAS_THROWN, ex.Message),
LogInteraction.Error);
}
}
#endregion
///
/// Set the default screens
///
///
public void ChangeDefaultScreen(DefaultScreen screen)
{
try
{
UpdateGUIMessages(LogLevel.BASIC, "Settings the default monitor to: " + Utilities.GetEnumDescription(screen),
LogInteraction.UserOperation, "Setting the default screen to: " + Utilities.GetEnumDescription(screen));
_targetSystem.SetDefaultMonitor(screen);
_UI.DisplayStatusBar("Default screen was set successfully");
}
catch (UCTException ex)
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite),
LogInteraction.Error, "Failed to set the default screen");
_UI.DisplayMessage("Set default monitor failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
catch (Exception ex)
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite),
LogInteraction.Error, "Failed to set the default screen");
_UI.DisplayMessage("Set default monitor failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
}
///
/// Switch screens
///
public void SetDefaultMonitor()
{
try
{
_targetSystem.SetDefaultMonitor();
_UI.DisplayStatusBar("Set default monitor completed successfully");
}
catch (UCTException ex)
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite),
LogInteraction.Error, "Failed to set the default monitor");
_UI.DisplayMessage("Set default monitor failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
catch (Exception ex)
{
UpdateGUIMessages(LogLevel.BASIC, String.Format(Properties.Resources.EXCEPTION_OCCURED_ERROR_CODE, ex.Message, ex.TargetSite),
LogInteraction.Error, "Failed to set the default monitor");
_UI.DisplayMessage("Set default monitor failed with exception: " + ex.Message, "Operation Failed", MessageType.ERROR);
}
}
#endregion
#endregion
#region IUserConsentFlow Members
public bool CheckIfConsentIsRequired()
{
if (_targetSystem.GetOptInPolicy() == OptInPolicy.NONE)
{
_UI.DisplayMessage(Properties.Resources.USER_CONSENT_NOT_REQUIRED, Properties.Resources.OPERATION_FAILED, MessageType.INFO);
UpdateGUIMessages(LogLevel.DETAILED, Properties.Resources.USER_CONSNET_LOG_NOT_REQUIRED,
LogInteraction.Information, "Consent is not required for any operation");
return false;
}
return true;
}
public bool CheckIfConsentAlreadyObtain()
{
// Get the User Consent state
OptInState state = _targetSystem.GetOptInState();
// If state is In-Session - indicate the user and exit the flow
if (state == OptInState.InSession)
{
_UI.DisplayMessage(Properties.Resources.USER_CONSENT_OPEN_SESSION, Properties.Resources.OPERATION_FAILED, MessageType.INFO);
UpdateGUIMessages(LogLevel.DETAILED, "Consent was already obtained - a KVM or Redirection session is open",
LogInteraction.Information, "Consent was already obtained");
return true;
}
// If state is Recieved - indicate the user that consent was already obtained and exit the flow
if (state == OptInState.Received)
{
_UI.DisplayMessage(Properties.Resources.USER_CONSENT_ALREADY_OBTAINED, Properties.Resources.OPERATION_FAILED, MessageType.INFO);
UpdateGUIMessages(LogLevel.DETAILED, Properties.Resources.USER_CONSENT_ALREADY_OBTAINED_LOG,
LogInteraction.Information, "Consent was already obtained");
return true;
}
// Any other state (except "Not Started") - reset the flow using cancel operation
if (state != OptInState.NotStarted)
{
UpdateGUIMessages(LogLevel.BASIC, "Reseting the User Consent state in order to start the consent process",
LogInteraction.Information, Properties.Resources.RESETING_USER_CONSENT);
// Cancel the consent flow
uint result = _targetSystem.CancelConsent();
if (result != 0)
{
UpdateGUIMessages(LogLevel.DETAILED, string.Format(Properties.Resources.CANCEL_USER_CONSENT_FAILURE_ERROR_CODE, result),
LogInteraction.Error, "Failed to reset the consent state");
}
}
return false;
}
public void PerformSxFlow()
{
if (!StartUserConsentProcess())
return;
// Ask the user if he want the tool to reboot the system
if (_UI.DisplayMessage("The target system is in Sx power state.\nA boot is needed in order to display the consent form.\nWould you like to boot the system?",
Properties.Resources.BOOTING_SYSTEM_MESSAGE, MessageType.QUESTION) == DialogResult.Yes)
{
_UI.RefreshScreen();
// Check if meanwhile the state changed to display
if (!EnsureRelevantState())
return;
_UI.RefreshScreen();
// Perform power operation (graceful and force)
PerformAMTShutDown(PowerState.On);
}
else
{
//Check if meanwhile the machine state changed to 'Display' (= the user woke up the machine)
if (_targetSystem.GetOptInState() != OptInState.Displayed)
{
_UI.DisplayMessage("In order to complete the consent process, please turn-on the target system.\nYou can ask the user to perform it localy, or use the advanced tab operations to perform it remotely. ", "Information Message", MessageType.INFO);
UpdateGUIMessages(LogLevel.DETAILED, "Power operation was aborted",
LogInteraction.UserOperation, "Power operation was aborted.");
}
}
}
public bool StartUserConsentProcess()
{
// Start the consent process
uint result = _targetSystem.StartConsent();
if (result != 0)
{
_UI.DisplayMessage("Start consent operation failed with error code: " + result + " - " + StatusCodes[result], Properties.Resources.STARTING_CONSNET_FAILED, MessageType.ERROR);
UpdateGUIMessages(LogLevel.BASIC, string.Format(Properties.Resources.STARTING_USER_CONSENT_FAILED_ERROR_CODE, result.ToString()),
LogInteraction.Error, "Start consent operation failed");
return false;
}
return true;
}
public void DetectingIfSpriteIsSupported()
{
UpdateGUIMessages(LogLevel.BASIC, Properties.Resources.DETECTING_SPRITE_LOG_MESSAGE,
LogInteraction.FWOperation, Properties.Resources.DETECTING_SPRITE_MESSAGE + "...");
_timer.Start();
_UI.stopProgress = false;
_UI.RefreshScreen();
// Detecting if sprite is supported, that may take up to 15 seconds.
// A timer is set to indicate this time had elapsed.
DialogResult dialogResult = _UI.RunProgressBar(Properties.Resources.DETECTING_SPRITE_MESSAGE + " (may take up to 15 sec.)",
Properties.Resources.DETECTING_SPRITE_MESSAGE, true, false);
if (dialogResult != DialogResult.Cancel)
{
_timer.Stop();
_UI.stopProgress = _timer.Enabled = false;
_UI.RefreshScreen();
// If user choose 'Skip' or 'cancel' at the Sprite detection progress bar - just stop the detection
// the button of 'Skip' removed , so the 'cancel' behave as the 'skip'
if (dialogResult == DialogResult.Abort || dialogResult == DialogResult.Ignore)
{
_userCancel = true;
UpdateGUIMessages(LogLevel.DETAILED, "Detection if sprite is supported was caceled", LogInteraction.UserOperation, "Detection if sprite is supported was caceled");
return;
}
}
if (!_timeHadElapsed)
_userCancel = true;
_UI.RefreshScreen();
while ((!_timeHadElapsed) && (!_spriteIsSupported) && (!_userCancel)) ;
}
public void ExecuteWirelessFlow()
{
// Check if AMT's wireless link is passive.
// If true returned - indicate that control link = ME, just perform reboot
if (!_targetSystem.CheckAMTWirelessLink())
{
// Get the wireless profiles state
WirelessProfilesState wirelessState = _targetSystem.GetWirelessProfilesState();
// Wireless profiles does not exist - indicate the user and stop the flow
if (wirelessState == WirelessProfilesState.None)
{
if (_UI.DisplayWarningMessage("The target system does not have wireless profiles, flow cannot be executed.", "Wireless Flow Aborted", MessageBoxButtons.OK) == DialogResult.OK)
{
_UI.RefreshScreen();
CancelUserConsentProcess();
}
UpdateGUIMessages(LogLevel.BASIC, "No wireless profile defined, Wireless flow aborted", LogInteraction.Error, "Wireless flow aborted");
return;
}
// Check if there is SSID match between AMT's profiles and host profile
if (!_targetSystem.CheckConnectionBetweenProfiles())
{
// The target system include only IT profiles, flow cannot be executed
if (wirelessState == WirelessProfilesState.ITProfiles)
{
_UI.DisplayWarningMessage("The target system does not have user profiles defined, flow cannot be executed.", "Wireless Flow Aborted", MessageBoxButtons.OK);
UpdateGUIMessages(LogLevel.BASIC, "No wireless profile defined, Wireless flow aborted", LogInteraction.Error, "Wireless flow aborted");
return;
}
// No match between profiles - indicate the user about the risk
if (_UI.DisplayMessage("LANID doesn't match SSID and only user profiles exist, hence the flow may fail.\nDo you wish to continue?", "Wireless Flow",
MessageType.QUESTION) == DialogResult.No)
{
// User don't want to continue the flow - abort
UpdateGUIMessages(LogLevel.BASIC, "Wireless profile does not match, Wireless flow aborted", LogInteraction.Error, "Wireless flow aborted");
// Cancel the flow
CancelUserConsentProcess();
return;
}
}
DialogResult dResult;
uint protectionLevel = _targetSystem.GetLinkProtectionLevel();
if (protectionLevel == 0) // Override
{
if ((dResult = _UI.DisplayWarningMessage("The Intel AMT system must be rebooted to display a user consent code.\n" +
"To remain connected via a wireless connection during reboot,\n" +
"link protection must be restored " +
"\nSelect one of the following options:\n" +
"Yes – Restore the link protection and reboot the system.\n" +
"No – Restore the link protection and do NOT reboot the system.\n" +
"Cancel – Cancel the user consent process (make no changes).", "Wireless Flow Notification",
MessageBoxButtons.YesNoCancel)) == DialogResult.Cancel)
{
_UI.RefreshScreen();
// User choose to cancel the flow - exits the flow at this point, not setting the link preference and not boot
UpdateGUIMessages(LogLevel.BASIC, "Consent flow was canceled by the user", LogInteraction.UserOperation, "Consent flow was canceled");
CancelUserConsentProcess();
return;
}
// Check if meanwhile the state changed to display
if (!EnsureRelevantState())
return;
_targetSystem.RestoreLinkProtection();
// No- indicates the user don't want to reboot the system,
// so we just restored the link protection (for the case the user will use the discrete operation to reboot)
if (dResult == DialogResult.No)
{
return;
}
else // Reboot the syetem
{
RebootSystem(LinkInterface.Wireless);
}
}
else // None
{
// Notify the user about the link preference
if ((dResult = _UI.DisplayWarningMessage("The Intel AMT system must be rebooted to display a user consent code.\n" +
"To remain connected via a wireless connection during reboot,\n" +
"control of network connections on the system must be passed to the Intel AMT Manageability Engine " +
"(by changing the 'Link Preference' of the Intel AMT system to 'ME').\n" +
"\nSelect one of the following options:\n" +
"Yes – Set the link preference to ME and reboot the system.\n" +
"No – Set the link preference to ME and do NOT reboot the system.\n" +
"Cancel – Cancel the user consent process (make no changes).", "Wireless Flow Notification",
MessageBoxButtons.YesNoCancel)) == DialogResult.Cancel)
{
_UI.RefreshScreen();
// User choose to cancel the flow - exits the flow at this point, not setting the link preference and not boot
UpdateGUIMessages(LogLevel.BASIC, "Consent flow was canceled by the user", LogInteraction.UserOperation, "Consent flow was canceled");
CancelUserConsentProcess();
return;
}
// Check if meanwhile the state changed to display
if (!EnsureRelevantState())
return;
// No indicates the user don't want to reboot the system,
// so we just set the link preference (for the case the user will use the discrete operation to reboot)
if (dResult == DialogResult.No)
{
_targetSystem.StartLinkPreferenceThread(true);
return;
}
RebootSystem(LinkInterface.Wireless);
}
}
else // Reboot the syetem
{
if (_UI.DisplayMessage(Properties.Resources.SPRITE_NOT_AVAILIBLE_MESSAGE_BOX_MESSAGE,
Properties.Resources.QUESTION_HEADER, MessageType.QUESTION) == DialogResult.Yes)
{
// Check if meanwhile the state changed to display
if (!EnsureRelevantState())
return;
RebootSystem(LinkInterface.Wireless);
}
}
}
public void ExecuteNonSpriteFlow()
{
// Check the system power state - because it needs to be s0 for this flow to continue.
if (_targetSystem.GetPowerState() != PowerState.On)
{
UpdateGUIMessages(LogLevel.BASIC, Properties.Resources.POWER_ON_MESSAGE,
LogInteraction.Information, Properties.Resources.POWER_ON_MESSAGE);
_UI.RefreshScreen();
if (_UI.DisplayMessage(Properties.Resources.POWER_ON_MESSAGE_BOX_MESSAGE +
"\n\nNote that if you choose 'No', in order to complete the consent process, you have to boot the target system." +
"\nYou can ask the user to perform it localy, or use the advanced tab operations to perform it remotely.",
Properties.Resources.BOOTING_SYSTEM_MESSAGE, MessageType.QUESTION) == DialogResult.Yes)
{
// Check if meanwhile the state changed to display
if (!EnsureRelevantState())
return;
// Power on the system
PerformAMTShutDown(PowerState.On);
}
}
// System is on and needs to be re-booted
else
{
// First try graceful shutdown - via OS, if failed try AMT reboot.
if (_UI.DisplayMessage(Properties.Resources.SPRITE_NOT_AVAILIBLE_MESSAGE_BOX_MESSAGE,
Properties.Resources.QUESTION_HEADER, MessageType.QUESTION) == DialogResult.Yes)
{
// Check if meanwhile the state changed to display
if (!EnsureRelevantState())
return;
RebootSystem(LinkInterface.Wired);
}
UpdateGUIMessages(LogLevel.BASIC, Properties.Resources.MEBx_USER_CONSENT_MESSAGE,
LogInteraction.Information, Properties.Resources.MEBx_USER_CONSENT_MESSAGE);
}
}
public void RunFullFlow()
{
bool wasSxFlow = false;
// Reseting all arguments to default
_timeHadElapsed = _spriteIsSupported = _userCancel = false;
_spriteCounter = 0;
// Update log and status bar
UpdateGUIMessages(LogLevel.BASIC, Properties.Resources.STARTING_USER_CONSENT_LOG_MESSAGE,
LogInteraction.UserOperation, Properties.Resources.STARTING_USER_CONSENT_PROGRESS_BAR_MESSAGE);
// 1) Check if consent is required
if (!CheckIfConsentIsRequired())
return;
// 2) Check if consent was already obtained
if (CheckIfConsentAlreadyObtain())
return;
// 3) Check the system power state
if (_targetSystem.GetPowerState() != PowerState.On)
{
PerformSxFlow();
wasSxFlow = true;
}
// 4) Start the consent process
if(!wasSxFlow)
if (!StartUserConsentProcess())
return;
// 5) Detecting if sprite is supported
DetectingIfSpriteIsSupported();
if (_userCancel == true)
{
if (_targetSystem.GetOptInState() == OptInState.Displayed)
{
UpdateGUIMessages(LogLevel.DETAILED, Properties.Resources.ASK_OPTIN_CODE_MESSAGE,
LogInteraction.Information, Properties.Resources.ASK_OPTIN_CODE_MESSAGE);
}
return;
}
// 6) Check if sprite is not supported - if so, executing the non-sprite flow:
// A reboot is needed to display form from MEbx.
// But before, there is a need to check the connection interface, if the connection is over wireless
// a SetLinkPreference command must be sent in order to for keep the connection.
// For the case that the user press "Skip" but the state already changed to display,
// we asking here again what the OptIn state is.
if (_targetSystem.GetOptInState() != OptInState.Displayed)
{
if (_spriteIsSupported == false)
{
// Check if the connection is over wireless and the FW version is earlier than 8.1 (in later versions, the ling preference is automaticly taken care of)
if (Configuration.InterfaceSettings.GetInstance().LinkInterface == LinkInterface.Wireless && !CheckLinkProtectionSupport())
{
ExecuteWirelessFlow();
}
else
{
ExecuteNonSpriteFlow();
}
}
}
else
{
UpdateGUIMessages(LogLevel.BASIC, Properties.Resources.ASK_OPTIN_CODE_MESSAGE,
LogInteraction.Information, Properties.Resources.ASK_OPTIN_CODE_MESSAGE);
}
}
public bool PerformGracefulShutdown()
{
return PerformGracefulShutdown(true, true, true);
}
public bool PerformAMTShutDown(PowerState state)
{
return PerformAMTShutDown(state, true, true);
}
public void SetGUIToConnect()
{
UpdateGUIMessages(LogLevel.BASIC, "Successfully Connected to: " + Configuration.GetInstance().Basic.AmtHost,
LogInteraction.Connection, "Connected to the remote system");
}
#endregion
#region IDisposable Members
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
private void Dispose(bool disposing)
{
if (disposing)
{
_timerBoot.Elapsed -= new ElapsedEventHandler(timerBoot_Elapsed);
_timerGraceful.Elapsed -= new ElapsedEventHandler(timerGraceful_Elapsed);
_timer.Elapsed -= new ElapsedEventHandler(OnShortTimedEvent);
_timer.Dispose();
_timerBoot.Dispose();
_timerGraceful.Dispose();
}
}
#endregion
internal PowerState GetPowerState()
{
return _targetSystem.GetPowerState();
}
}
}