fix multi-threads bugs

This commit is contained in:
Vector Von 2022-07-01 17:18:11 +08:00
parent 4afd6790de
commit 541d539f61
4 changed files with 97 additions and 54 deletions

View File

@ -32,6 +32,9 @@
<ComboBox x:Name="ComboBox_Disk1" Height="20" Width="60" VerticalAlignment="Center"/> <ComboBox x:Name="ComboBox_Disk1" Height="20" Width="60" VerticalAlignment="Center"/>
</StackPanel> </StackPanel>
<StackPanel Grid.Row="3" Orientation="Horizontal" HorizontalAlignment="Right" Margin="5"> <StackPanel Grid.Row="3" Orientation="Horizontal" HorizontalAlignment="Right" Margin="5">
<TextBlock Text="状态:" VerticalAlignment="Center"/>
<TextBlock x:Name="TextBlock_Status" Text="未连接" Foreground="Red" VerticalAlignment="Center" />
<Separator Width="10" Background="Transparent" />
<Button Content="应用并保存" Click="Button_Save_Click" Height="25" Width="80" /> <Button Content="应用并保存" Click="Button_Save_Click" Height="25" Width="80" />
<Separator Width="10" Background="Transparent" /> <Separator Width="10" Background="Transparent" />
<Button Content="隐藏" Click="Button_Hide_Click" Height="25" Width="40" /> <Button Content="隐藏" Click="Button_Hide_Click" Height="25" Width="40" />

View File

@ -22,6 +22,11 @@ namespace Topuino_Client_Windows
{ {
InitializeComponent(); InitializeComponent();
trayIon.Icon = new Icon(@"Topuino.ico");
trayIon.Visible = true;
trayIon.Text = "Topuino";
trayIon.DoubleClick += TrayIcon_DoubleClick;
allDrives = new List<DriveInfo>(); allDrives = new List<DriveInfo>();
DriveInfo[] drives = DriveInfo.GetDrives(); DriveInfo[] drives = DriveInfo.GetDrives();
foreach (DriveInfo drive in drives) foreach (DriveInfo drive in drives)
@ -42,6 +47,8 @@ namespace Topuino_Client_Windows
ShowInTaskbar = true; ShowInTaskbar = true;
Visibility = Visibility.Hidden; Visibility = Visibility.Hidden;
LoadConfig(); LoadConfig();
ApplyConfig();
StartRun();
} }
else else
{ {
@ -49,11 +56,6 @@ namespace Topuino_Client_Windows
ComboBox_Disk0.SelectedIndex = 0; ComboBox_Disk0.SelectedIndex = 0;
ComboBox_Disk1.SelectedIndex = 0; ComboBox_Disk1.SelectedIndex = 0;
} }
trayIon.Icon = new Icon(@"Topuino.ico");
trayIon.Visible = true;
trayIon.Text = "Topuino";
trayIon.DoubleClick += TrayIcon_DoubleClick;
} }
private NotifyIcon trayIon = new NotifyIcon(); private NotifyIcon trayIon = new NotifyIcon();
@ -64,12 +66,10 @@ namespace Topuino_Client_Windows
private DriveInfo drive0; private DriveInfo drive0;
private DriveInfo drive1; private DriveInfo drive1;
private bool ready = false;
private Thread? refreshThread = null; private Thread? refreshThread = null;
private ManualResetEvent requestStop = new ManualResetEvent(false); private ManualResetEvent requestStopEvent = new ManualResetEvent(false);
private ManualResetEvent stopDone = new ManualResetEvent(false); private ManualResetEvent stopDoneEvent = new ManualResetEvent(false);
private OnlineConnector? onlineClient = null; private OnlineConnector? onlineClient = null;
private UsbConnector? usbClient = null; private UsbConnector? usbClient = null;
@ -144,9 +144,6 @@ namespace Topuino_Client_Windows
ShowErrorBox("初始参数加载错误,请检查配置文件"); ShowErrorBox("初始参数加载错误,请检查配置文件");
Close(); Close();
} }
ApplyConfig();
StartRun();
} }
private void Run() private void Run()
@ -164,7 +161,7 @@ namespace Topuino_Client_Windows
long netBytesReceiveBefore; long netBytesReceiveBefore;
long netBytesReceiveAfter; long netBytesReceiveAfter;
while (!requestStop.WaitOne(0)) while (!requestStopEvent.WaitOne(0))
{ {
netBytesSentBefore = 0; netBytesSentBefore = 0;
netBytesSentAfter = 0; netBytesSentAfter = 0;
@ -205,18 +202,33 @@ namespace Topuino_Client_Windows
OnlineRun(data); OnlineRun(data);
break; break;
case 2: case 2:
OfflineRun(data); LocalRun(data);
break; break;
default: default:
break; break;
} }
} }
stopDone.Set(); stopDoneEvent.Set();
} }
private void UsbRun(MonitorData data) private void UsbRun(MonitorData data)
{ {
if (usbClient == null)
{
try
{
usbClient = new UsbConnector();
ShowConnected();
}
catch
{
usbClient = null;
ShowDisconnected();
return;
}
}
int size = Marshal.SizeOf(data); int size = Marshal.SizeOf(data);
byte[] bin = new byte[size]; byte[] bin = new byte[size];
IntPtr ptr = IntPtr.Zero; IntPtr ptr = IntPtr.Zero;
@ -231,11 +243,25 @@ namespace Topuino_Client_Windows
Marshal.FreeHGlobal(ptr); Marshal.FreeHGlobal(ptr);
} }
try
{
usbClient.Send(bin); usbClient.Send(bin);
} }
catch
{
usbClient.Dispose();
usbClient = null;
ShowDisconnected();
}
}
private void OnlineRun(MonitorData data) private void OnlineRun(MonitorData data)
{ {
if (onlineClient == null)
{
onlineClient = new OnlineConnector();
}
Dictionary<string, string> statusInfo = new Dictionary<string, string>(); Dictionary<string, string> statusInfo = new Dictionary<string, string>();
statusInfo.Add("SN", sn); statusInfo.Add("SN", sn);
statusInfo.Add("CPU_PERCENT", data.cpuPercent.ToString()); statusInfo.Add("CPU_PERCENT", data.cpuPercent.ToString());
@ -247,10 +273,20 @@ namespace Topuino_Client_Windows
statusInfo.Add("NET_SENT_RATE", data.netSentRate.ToString()); statusInfo.Add("NET_SENT_RATE", data.netSentRate.ToString());
statusInfo.Add("NET_RECV_RATE", data.netRecvRate.ToString()); statusInfo.Add("NET_RECV_RATE", data.netRecvRate.ToString());
onlineClient.Post(statusInfo); try
{
onlineClient.Post(statusInfo).Wait();
ShowConnected();
}
catch
{
onlineClient.Dispose();
onlineClient = null;
ShowDisconnected();
}
} }
private void OfflineRun(MonitorData data) private void LocalRun(MonitorData data)
{ {
} }
@ -274,39 +310,28 @@ namespace Topuino_Client_Windows
if (RadioButton_UsbMode.IsChecked == true) if (RadioButton_UsbMode.IsChecked == true)
{ {
mode = 0; mode = 0;
usbClient = new UsbConnector();
} }
else if (RadioButton_OnlineMode.IsChecked == true) else if (RadioButton_OnlineMode.IsChecked == true)
{ {
mode = 1; mode = 1;
onlineClient = new OnlineConnector();
} }
else if (RadioButton_LocalMode.IsChecked == true) else if (RadioButton_LocalMode.IsChecked == true)
{ {
mode = 2; mode = 2;
// TODO
} }
sn = TextBox_DeviceSn.Text; sn = TextBox_DeviceSn.Text;
drive0 = ComboBox_Disk0.SelectedItem as DriveInfo; drive0 = ComboBox_Disk0.SelectedItem as DriveInfo;
drive1 = ComboBox_Disk1.SelectedItem as DriveInfo; drive1 = ComboBox_Disk1.SelectedItem as DriveInfo;
ready = true;
} }
catch (Exception e) catch (Exception e)
{ {
ready = false;
ShowErrorBox(e.Message); ShowErrorBox(e.Message);
} }
} }
private void StartRun() private void StartRun()
{ {
if (!ready)
{
return;
}
if (!drive0.IsReady || !drive1.IsReady) if (!drive0.IsReady || !drive1.IsReady)
{ {
ShowErrorBox("磁盘未就绪"); ShowErrorBox("磁盘未就绪");
@ -321,14 +346,14 @@ namespace Topuino_Client_Windows
{ {
if (refreshThread != null) if (refreshThread != null)
{ {
requestStop.Set(); requestStopEvent.Set();
stopDone.WaitOne(); stopDoneEvent.WaitOne();
} }
refreshThread = null; refreshThread = null;
requestStop.Reset(); requestStopEvent.Reset();
stopDone.Reset(); stopDoneEvent.Reset();
} }
private async void SaveConfig() private async void SaveConfig()
@ -368,6 +393,32 @@ namespace Topuino_Client_Windows
Visibility = Visibility.Hidden; Visibility = Visibility.Hidden;
} }
private void ShowConnected()
{
if (requestStopEvent.WaitOne(0))
{
return;
}
Dispatcher.Invoke(() => {
TextBlock_Status.Text = "已连接";
TextBlock_Status.Foreground = System.Windows.Media.Brushes.Green;
});
}
private void ShowDisconnected()
{
if (requestStopEvent.WaitOne(0))
{
return;
}
Dispatcher.Invoke(() => {
TextBlock_Status.Text = "未连接";
TextBlock_Status.Foreground = System.Windows.Media.Brushes.Red;
});
}
private void Window_Closing(object sender, System.ComponentModel.CancelEventArgs e) private void Window_Closing(object sender, System.ComponentModel.CancelEventArgs e)
{ {
StopRun(); StopRun();

View File

@ -2,6 +2,7 @@
using System.Net.Http; using System.Net.Http;
using System.Text; using System.Text;
using Newtonsoft.Json; using Newtonsoft.Json;
using System.Threading.Tasks;
using System.Collections.Generic; using System.Collections.Generic;
namespace Topuino_Client_Windows namespace Topuino_Client_Windows
@ -9,11 +10,8 @@ namespace Topuino_Client_Windows
internal class OnlineConnector internal class OnlineConnector
{ {
private HttpClient client = new HttpClient(); private HttpClient client = new HttpClient();
private int errorCount = 0;
internal async void Post(Dictionary<string, string> data) internal async Task Post(Dictionary<string, string> data)
{
try
{ {
HttpContent content = new FormUrlEncodedContent(data); HttpContent content = new FormUrlEncodedContent(data);
HttpResponseMessage response = await client.PostAsync("https://iot.vvzero.com/topuino/putdata", content); HttpResponseMessage response = await client.PostAsync("https://iot.vvzero.com/topuino/putdata", content);
@ -22,17 +20,7 @@ namespace Topuino_Client_Windows
OnlineConnectorResponse? respData = JsonConvert.DeserializeObject<OnlineConnectorResponse>(responseBody); OnlineConnectorResponse? respData = JsonConvert.DeserializeObject<OnlineConnectorResponse>(responseBody);
if (respData == null || respData.CODE != 0) if (respData == null || respData.CODE != 0)
{ {
throw new Exception(); throw new Exception("网络连接异常");
}
errorCount = 0;
}
catch
{
errorCount++;
if (errorCount > 5)
{
// TODO
}
} }
} }

View File

@ -75,6 +75,7 @@ namespace Topuino_Client_Windows
if (pongBuff[0] == 0x68 && pongBuff[1] == 0x61) if (pongBuff[0] == 0x68 && pongBuff[1] == 0x61)
{ {
portValid = true; portValid = true;
portInitReceived.Set();
} }
} }
} }