Free cookie consent management tool by TermsFeed Policy Generator

source: branches/HeuristicLab.Hive-3.4/sources/HeuristicLab.Clients.Hive.Slave.Views/3.4/SlaveView.cs @ 6422

Last change on this file since 6422 was 6371, checked in by ascheibe, 13 years ago

#1233

  • code cleanups for slave review
  • added switch between privileged and unprivileged sandbox
  • removed childjob management because it's not used
File size: 12.1 KB
RevLine 
[5314]1#region License Information
2/* HeuristicLab
3 * Copyright (C) 2002-2011 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
4 *
5 * This file is part of HeuristicLab.
6 *
7 * HeuristicLab is free software: you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation, either version 3 of the License, or
10 * (at your option) any later version.
11 *
12 * HeuristicLab is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
19 */
20#endregion
21
[5795]22using System;
[6257]23using System.Diagnostics;
24using System.Runtime.InteropServices;
[5826]25using System.Security.Principal;
26using System.ServiceProcess;
[5795]27using System.Threading;
28using System.Threading.Tasks;
[5314]29using System.Windows.Forms;
[5789]30using System.Windows.Forms.DataVisualization.Charting;
[5314]31using HeuristicLab.Common;
32using HeuristicLab.Core.Views;
33using HeuristicLab.MainForm;
34
35
[5599]36namespace HeuristicLab.Clients.Hive.SlaveCore.Views {
[5314]37
38  [View("HeuristicLab Slave View")]
39  [Content(typeof(SlaveItem), IsDefaultView = true)]
40  public partial class SlaveView : ItemView {
[6371]41    private SlaveDisplayStat lastSlaveDisplayStat;
42    private const string serviceName = "HeuristicLab.Clients.Hive.SlaveCore.SlaveWindowsService";
[5314]43
[6263]44    private const UInt32 BCM_SETSHIELD = 0x160C;
45    [DllImport("user32", CharSet = CharSet.Auto, SetLastError = true)]
46    static extern int SendMessage(IntPtr hWnd, UInt32 Msg, int wParam, IntPtr lParam);
47
[5314]48    public new SlaveItem Content {
49      get { return (SlaveItem)base.Content; }
[5320]50      set {
51        if (base.Content != value) {
52          base.Content = value;
53        }
54      }
[5314]55    }
56
57    public SlaveView() {
58      InitializeComponent();
[5826]59
[6263]60      if (CheckRunAsAdmin()) {
61        btnKill.ImageAlign = System.Drawing.ContentAlignment.MiddleLeft;
62        btnKill.Image = HeuristicLab.Common.Resources.VSImageLibrary.BreakpointActive;
63      } else {
64        this.btnKill.FlatStyle = FlatStyle.System;
65        SendMessage(btnKill.Handle, BCM_SETSHIELD, 0, (IntPtr)1);
66      }
[5826]67
[6257]68      lblSlaveState.Text = SlaveDisplayStat.NoService.ToString();
[6263]69      lastSlaveDisplayStat = SlaveDisplayStat.NoService;
70      Content_SlaveDisplayStateChanged(this, new EventArgs<SlaveDisplayStat>(lastSlaveDisplayStat));
[5314]71    }
72
73    #region Register Content Events
74    protected override void DeregisterContentEvents() {
75      Content.SlaveShutdown -= new System.EventHandler(Content_SlaveShutdown);
76      Content.SlaveStatusChanged -= new System.EventHandler<EventArgs<StatusCommons>>(Content_SlaveStatusChanged);
[6257]77      Content.SlaveDisplayStateChanged -= new EventHandler<EventArgs<SlaveDisplayStat>>(Content_SlaveDisplayStateChanged);
78      Content.CoreConnectionChanged -= new EventHandler<EventArgs<CoreConnection>>(Content_CoreConnectionChanged);
[5320]79
80      base.DeregisterContentEvents();
[5314]81    }
82
83    protected override void RegisterContentEvents() {
84      base.RegisterContentEvents();
85
86      Content.SlaveShutdown += new System.EventHandler(Content_SlaveShutdown);
87      Content.SlaveStatusChanged += new System.EventHandler<EventArgs<StatusCommons>>(Content_SlaveStatusChanged);
[6257]88      Content.SlaveDisplayStateChanged += new EventHandler<EventArgs<SlaveDisplayStat>>(Content_SlaveDisplayStateChanged);
89      Content.CoreConnectionChanged += new EventHandler<EventArgs<CoreConnection>>(Content_CoreConnectionChanged);
[5314]90    }
91    #endregion
92
93    protected override void OnContentChanged() {
94      base.OnContentChanged();
[6257]95      btnKill.Enabled = false;
96      btnStart.Enabled = false;
97      btnStop.Enabled = false;
98
[5314]99      if (Content == null) {
[6257]100        //nothing to do...         
[5314]101      } else {
102        //try to establish a connection to the slave service
[5795]103        if (base.Content != null) {
[5314]104          ((SlaveItem)base.Content).Open();
[5795]105          Task.Factory.StartNew(Connector);
[5314]106        }
107      }
108    }
109
[5795]110    private void Connector() {
[6263]111      Content_SlaveDisplayStateChanged(this, new EventArgs<SlaveDisplayStat>(SlaveDisplayStat.NoService));
[5795]112      bool connected = false;
113      while (!connected) {
114        this.Invoke(new Func<bool>(() => connected = ((SlaveItem)base.Content).ReconnectToSlaveCore()));
115
116        if (!connected) {
117          Thread.Sleep(1000);
118        }
119      }
120      this.Invoke(new Action(SetEnabledStateOfControls));
121    }
122
[5314]123    protected override void SetEnabledStateOfControls() {
124      base.SetEnabledStateOfControls();
125      //do nothing at the moment, we have nothing editable
126    }
127
128    #region Event Handlers
129    void Content_SlaveStatusChanged(object sender, EventArgs<StatusCommons> e) {
[6257]130      RenderJobChart(e.Value);
131      RenderCoreChart(e.Value);
[5314]132    }
133
134    void Content_SlaveShutdown(object sender, System.EventArgs e) {
[5795]135      Task.Factory.StartNew(Connector);
[5314]136    }
[6257]137
138    void Content_SlaveDisplayStateChanged(object sender, EventArgs<SlaveDisplayStat> e) {
139      lblSlaveState.Text = e.Value.ToString();
140      lastSlaveDisplayStat = e.Value;
141
142      if (e.Value == SlaveDisplayStat.Asleep || e.Value == SlaveDisplayStat.NoService) {
143        btnKill.Enabled = false;
144        btnStart.Enabled = true;
145        btnStop.Enabled = false;
146      }
147
148      if (e.Value == SlaveDisplayStat.Busy || e.Value == SlaveDisplayStat.Idle || e.Value == SlaveDisplayStat.Offline) {
149        btnKill.Enabled = true;
150        btnStart.Enabled = false;
151        btnStop.Enabled = true;
152      }
153    }
154
155    void Content_CoreConnectionChanged(object sender, EventArgs<CoreConnection> e) {
156      if (e.Value == CoreConnection.Offline) {
157        btnKill.Enabled = false;
158        btnStart.Enabled = false;
159        btnStop.Enabled = false;
160      }
161    }
[5314]162    #endregion
[5315]163
[6257]164    private void RenderJobChart(StatusCommons status) {
[5826]165      jobChart.Series[0].Points.Clear();
[6257]166      jobChart.Series[1].Points.Clear();
167      jobChart.Series[2].Points.Clear();
168      jobChart.Series[3].Points.Clear();
[6263]169      jobChart.Series[4].Points.Clear();
[5789]170
[6263]171
[6257]172      DataPoint pJobs = new DataPoint(1, status.Jobs.Count);
173      DataPoint pJobsAborted = new DataPoint(2, status.JobsAborted);
174      DataPoint pJobsDone = new DataPoint(3, status.JobsFinished);
175      DataPoint pJobsFetched = new DataPoint(4, status.JobsFetched);
[6263]176      DataPoint pJobsFailed = new DataPoint(5, status.JobsFailed);
[5789]177
[5826]178      pJobs.LegendText = "Current jobs: " + status.Jobs.Count;
[6263]179      pJobs.Color = System.Drawing.Color.Yellow;
[6257]180      pJobs.ToolTip = pJobs.LegendText;
[6263]181      jobChart.Series[0].Color = System.Drawing.Color.Yellow;
[6257]182      jobChart.Series[0].LegendText = pJobs.LegendText;
183      jobChart.Series[0].Points.Add(pJobs);
184
[5826]185      pJobsAborted.LegendText = "Aborted jobs: " + status.JobsAborted;
[6263]186      pJobsAborted.Color = System.Drawing.Color.Orange;
[6257]187      pJobsAborted.ToolTip = pJobsAborted.LegendText;
[6263]188      jobChart.Series[1].Color = System.Drawing.Color.Orange;
[6257]189      jobChart.Series[1].LegendText = pJobsAborted.LegendText;
190      jobChart.Series[1].Points.Add(pJobsAborted);
191
[6203]192      pJobsDone.LegendText = "Finished jobs: " + status.JobsFinished;
[5826]193      pJobsDone.Color = System.Drawing.Color.Green;
[6257]194      pJobsDone.ToolTip = pJobsDone.LegendText;
[6263]195      jobChart.Series[2].Color = System.Drawing.Color.Green;
[6257]196      jobChart.Series[2].LegendText = pJobsDone.LegendText;
197      jobChart.Series[2].Points.Add(pJobsDone);
198
[5826]199      pJobsFetched.LegendText = "Fetched jobs: " + status.JobsFetched;
[6257]200      pJobsFetched.ToolTip = pJobsFetched.LegendText;
[5826]201      pJobsFetched.Color = System.Drawing.Color.Blue;
[6263]202      jobChart.Series[3].Color = System.Drawing.Color.Blue;
[6257]203      jobChart.Series[3].LegendText = pJobsFetched.LegendText;
204      jobChart.Series[3].Points.Add(pJobsFetched);
[6263]205
206      pJobsFailed.LegendText = "Failed jobs: " + status.JobsFailed;
207      pJobsFailed.ToolTip = pJobsFailed.LegendText;
208      pJobsFailed.Color = System.Drawing.Color.Red;
209      jobChart.Series[4].Color = System.Drawing.Color.Red;
210      jobChart.Series[4].LegendText = pJobsFailed.LegendText;
211      jobChart.Series[4].Points.Add(pJobsFailed);
[5789]212    }
213
[6257]214    private void RenderCoreChart(StatusCommons statusCommons) {
215      int usedCores = statusCommons.TotalCores - statusCommons.FreeCores;
216      DataPoint pFreeCores = new DataPoint(statusCommons.FreeCores, statusCommons.FreeCores);
217      DataPoint pUsedCores = new DataPoint(usedCores, usedCores);
[5315]218
[6257]219      coresChart.Series[0].Points.Clear();
[5315]220
[6257]221      pFreeCores.LegendText = "Free cores: " + statusCommons.FreeCores;
222      pFreeCores.Color = System.Drawing.Color.Green;
223      pUsedCores.LegendText = "Used cores: " + usedCores;
224      pUsedCores.Color = System.Drawing.Color.Red;
[5451]225
[6257]226      coresChart.Series[0].Points.Add(pFreeCores);
227      coresChart.Series[0].Points.Add(pUsedCores);
[5451]228    }
[5602]229
[5826]230    private bool CheckRunAsAdmin() {
231      bool isRunAsAdmin = false;
232      WindowsIdentity user = WindowsIdentity.GetCurrent();
233      WindowsPrincipal principal = new WindowsPrincipal(user);
234
235      try {
236        isRunAsAdmin = principal.IsInRole(WindowsBuiltInRole.Administrator);
237      }
238      catch { }
239      return isRunAsAdmin;
240    }
241
[6263]242    /// <summary>
[6371]243    /// Shows the windows UAC dialog and restarts tray icon app
[6263]244    /// </summary>
[6257]245    private void ElevateApplication() {
[6371]246      // launch itself as administrator
[6257]247      ProcessStartInfo proc = new ProcessStartInfo(Application.ExecutablePath, "showui");
248      proc.UseShellExecute = true;
249      proc.WorkingDirectory = Environment.CurrentDirectory;
250      proc.FileName = Application.ExecutablePath;
251      proc.Verb = "runas";
252
253      try {
254        Process.Start(proc);
255      }
256      catch {
[6263]257        // user refused to allow privileges elevation       
[6257]258        return;
259      }
[6263]260      Application.Exit();
[6257]261    }
262
263    private void StartService() {
[5826]264      TimeSpan timeout = TimeSpan.FromMilliseconds(5000);
265
266      ServiceController service = new ServiceController(serviceName);
267      try {
268        if (service.Status == ServiceControllerStatus.Running) {
269          service.Stop();
270          service.WaitForStatus(ServiceControllerStatus.Stopped, timeout);
271        }
272
273        service.Start();
274        service.WaitForStatus(ServiceControllerStatus.Running, timeout);
275      }
276      catch (InvalidOperationException ex) {
[6004]277        MessageBox.Show("Error starting service: Hive Slave Service not found!" + Environment.NewLine + ex.ToString());
[5826]278      }
279      catch (Exception ex) {
[6004]280        MessageBox.Show("Error starting service, exception is: " + Environment.NewLine + ex.ToString());
[5826]281      }
282    }
[6257]283
284    private void StopService() {
[6263]285      TimeSpan timeout = TimeSpan.FromMilliseconds(7000);
[6257]286
287      ServiceController service = new ServiceController(serviceName);
288      try {
289        if (service.Status == ServiceControllerStatus.Running) {
290          service.Stop();
291          service.WaitForStatus(ServiceControllerStatus.Stopped, timeout);
292        }
293      }
294      catch (InvalidOperationException ex) {
295        MessageBox.Show("Error starting service: Hive Slave Service not found!" + Environment.NewLine + ex.ToString());
296      }
297      catch (Exception ex) {
298        MessageBox.Show("Error starting service, exception is: " + Environment.NewLine + ex.ToString());
299      }
300    }
301
302    private void btnKill_Click(object sender, EventArgs e) {
303      if (CheckRunAsAdmin()) {
304        StopService();
305      } else {
306        ElevateApplication();
307      }
308    }
309
310    private void btnStop_Click(object sender, EventArgs e) {
311      if (Content != null) {
312        Content.Sleep();
313      }
314    }
315
316    private void btnStart_Click(object sender, EventArgs e) {
317      if (Content != null) {
318        if (lastSlaveDisplayStat == SlaveDisplayStat.Asleep) {
319          Content.RestartCore();
320        } else if (lastSlaveDisplayStat == SlaveDisplayStat.NoService) {
321          if (CheckRunAsAdmin()) {
322            StartService();
323          } else {
324            ElevateApplication();
325          }
326        }
327      }
328    }
[5314]329  }
330}
Note: See TracBrowser for help on using the repository browser.