1620 lines
73 KiB
C#
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

//----------------------------------------------------------------------------
//
// 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
{
/// <summary>
/// The main class - hold the logic behind the operations
/// </summary>
public class LogicLayer : IUserConsentFlow, IDisposable
{
#region - Dictionaries -
// OptInService Functions Statuses
Dictionary<uint, string> StatusCodes = new Dictionary<uint, string>()
{
{0, "Success"},
{1, "Internal error"},
{2, "Invalid state"},
{3, "Operation is blocked"},
{2066, "Invalid credentials"}
};
// Power state change return values
Dictionary<uint, string> PowerStatusCode = new Dictionary<uint, string>()
{
{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 -
/// <summary>
/// Timer that running when executing graceful shutdown
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
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();
}
}
/// <summary>
/// Timer that running when detecting if sprite is supported
/// </summary>
/// <param name="source"></param>
/// <param name="e"></param>
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();
}
}
/// <summary>
/// Timer that running when performing AMT reboot
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
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 -
/// <summary>
/// Constructor
/// </summary>
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;
}
/// <summary>
/// Register the GUI layer
/// </summary>
/// <param name="ui"></param>
public void RegisterUI(UserInterface ui)
{
_UI = ui;
}
/// <summary>
/// Register the target system layer
/// </summary>
/// <param name="trs"></param>
public void RegisterTargetSystem(TargetSystem trs)
{
_targetSystem = trs;
}
#endregion
#region - Methods -
#region - Main Methods Flow -
/// <summary>
/// Canceling user consent
/// </summary>
/// <returns></returns>
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);
}
}
/// <summary>
/// Canceling the user consent (include just the FW call, without the state checking)
/// </summary>
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");
}
}
/// <summary>
/// Start user consent flow
/// </summary>
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);
}
}
/// <summary>
/// Sent the OptIn code
/// </summary>
/// <param name="code"></param>
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 -
/// <summary>
/// This method try to reboot the system, first gracefully (via OS), if failed - try AMT shutdown
/// </summary>
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;
}
}
/// <summary>
/// Execute graceful shutdown on the target system
/// </summary>
/// <param name="hasCancel">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)</param>
/// <returns>true - continue the flow, false - abort the flow</returns>
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;
}
/// <summary>
/// Execute AMT shutdown on the target system
/// </summary>
/// <param name="hasCancel">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)</param>
/// <returns>true - continue the flow, false - abort the flow</returns>
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
/// <summary>
/// Change the connection address (used when changing the host name via the combo box)
/// </summary>
/// <returns></returns>
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;
}
/// <summary>
/// Set the application to its default values
/// </summary>
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);
}
}
/// <summary>
/// Get the statistics tab information
/// </summary>
/// <returns></returns>
public Dictionary<string, string> GetStatisticsParams()
{
WriteLog(LogLevel.BASIC, "Getting connection parameters", LogInteraction.FWOperation);
return _targetSystem.GetConnectionParameters();
}
/// <summary>
/// Open the log file (in notepad)
/// </summary>
public void ViewLog()
{
try
{
LogManager.GetInstance().ViewLogFile();
}
catch (UCTException e)
{
_UI.DisplayMessage(e.Message, "Failed to open the Log", MessageType.ERROR);
}
}
/// <summary>
/// Write a line to the log
/// </summary>
/// <param name="level"></param>
/// <param name="message"></param>
/// <param name="interaction"></param>
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) { }
}
/// <summary>
/// Update the GUI - write the current operation to the log and status bar
/// </summary>
/// <param name="logLevel"></param>
/// <param name="logMessage"></param>
/// <param name="logInteraction"></param>
/// <param name="statusbarMessage"></param>
private void UpdateGUIMessages(LogLevel logLevel, string logMessage, LogInteraction logInteraction, string statusbarMessage)
{
WriteLog(logLevel, logMessage, logInteraction);
_UI.DisplayStatusBar(statusbarMessage);
}
/// <summary>
/// Check if meanwhile, the consent state changed to disconnect
/// </summary>
/// <returns></returns>
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 -
/// <summary>
/// This is the main function - once the opt in state property is changed, this method is called
/// </summary>
/// <param name="state"></param>
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);
}
}
/// <summary>
/// Set the tool to 'Unknown' state
/// </summary>
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;
}
}
/// <summary>
/// Set the tool to 'Not Started' state
/// </summary>
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;
}
/// <summary>
/// Set the tool to 'Displayed' state
/// </summary>
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;
}
/// <summary>
/// Set the tool to 'Requested' state
/// </summary>
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;
}
/// <summary>
/// Set the tool to 'Recieved' state
/// </summary>
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;
}
/// <summary>
/// Set the tool to 'In Session' state
/// </summary>
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;
}
/// <summary>
/// Update the power state label
/// </summary>
/// <param name="ps"></param>
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 -
/// <summary>
/// Set the link preference
/// </summary>
/// <param name="link"></param>
/// <param name="timeout"></param>
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");
}
}
/// <summary>
/// Update the wireless details (link control, lan id ect.)
/// </summary>
/// <param name="linkControl"></param>
/// <param name="linkPreference"></param>
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
/// <summary>
/// Set the default screens
/// </summary>
/// <param name="screen"></param>
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);
}
}
/// <summary>
/// Switch screens
/// </summary>
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();
}
}
}