C# 同步更新系统时间

匿名 (未验证) 提交于 2019-12-02 22:06:11

前言

在定位用户问题时,发现有些电脑,会出现系统时间不是最新的问题。

可能原因:

  1. 取消了勾选服务器时间同步
  2. 当前安装的系统,是一个未知来源系统,导致系统时间更新失败

而系统时间不正确,会导致IE选项-证书,校验不通过~

更新系统时间

1. 连接时间服务器

时间服务器列表(推荐): string[] timeHosts = { "time.windows.com", "time.nist.gov" };

 1     /// <summary>  2     /// 连接时间服务器  3     /// </summary>  4     /// <param name="socket">服务器接口</param>  5     /// <param name="startTime">开始时间</param>  6     /// <param name="errorMsg">错误信息</param>  7     /// <returns></returns>  8     private static bool TryConnectToTimeServer(out Socket socket, out DateTime startTime, out string errorMsg)  9     { 10         socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);//创建Socket    11         socket.ReceiveTimeout = 10 * 1000;//设置超时时间    12         errorMsg = string.Empty; 13         startTime = DateTime.Now; 14  15         // 遍历时间服务器列表    16         foreach (string strHost in timeHosts) 17         { 18             try 19             { 20                 // 记录开始的时间    21                 startTime = DateTime.Now; 22  23                 var iphostinfo = Dns.GetHostEntry(strHost); 24                 var ip = iphostinfo.AddressList[0]; 25                 //建立IPAddress对象与端口,创建IPEndPoint节点:    26                 int port = 13; 27                 var ipe = new IPEndPoint(ip, port); 28                 //连接到服务器    29                 socket.Connect(ipe); 30                 // 如果连接到服务器就跳出   31                 if (socket.Connected) break; 32             } 33             catch (Exception ex) 34             { 35                 errorMsg = $"时间服务器连接失败!/r错误信息:{ex.Message}系统提示"; 36             } 37         } 38         return socket.Connected; 39     }

2. 从服务器接收数据

 1     /// <summary>  2     /// 从服务器接收数据  3     /// </summary>  4     /// <param name="socket"></param>  5     /// <returns></returns>  6     private static StringBuilder ReceiveMessageFromServer(Socket socket)  7     {  8         //SOCKET同步接受数据     9         byte[] receiveBytes = new byte[1024]; 10         int nBytes, nTotalBytes = 0; 11         StringBuilder sb = new StringBuilder(); 12         System.Text.Encoding encoding = Encoding.UTF8; 13  14         while ((nBytes = socket.Receive(receiveBytes, 0, 1024, SocketFlags.None)) > 0) 15         { 16             nTotalBytes += nBytes; 17             sb.Append(encoding.GetString(receiveBytes, 0, nBytes)); 18         } 19  20         return sb; 21     }

3. 更新本地时间

 1     /// <summary>  2     /// 更新系统时间  3     /// </summary>  4     /// <returns>更新结果</returns>  5     public static string UpdateSystemTime()  6     {  7         try  8         {  9             var connected = TryConnectToTimeServer(out Socket socket, out var startTime, out string errorMsg); 10             if (connected) 11             { 12                 var receivedMsg = ReceiveMessageFromServer(socket); 13                 socket.Close(); 14                 //切割字符串  15                 string[] receiveMsgList = receivedMsg.ToString().Split(' '); 16                 if (receiveMsgList.Length >= 3) 17                 { 18                     var dateTimeValue = receiveMsgList[1] + " " + receiveMsgList[2]; 19                     SetLocalTime(startTime, dateTimeValue); 20                 } 21             } 22             else 23             { 24                 return errorMsg; 25             } 26         } 27         catch (Exception e) 28         { 29             return $"函数{nameof(UpdateSystemTime)}执行异常,{e.Message}"; 30         } 31         return "时间已同步"; 32     } 33     /// <summary> 34     /// 设置系统时间 35     /// </summary> 36     /// <param name="startTime">请求服务器时的开始时间</param> 37     /// <param name="dateTimeValue">服务器返回的时间</param> 38     private static void SetLocalTime(DateTime startTime, string dateTimeValue) 39     { 40         // 得到开始到现在所消耗的时间  41         TimeSpan k = DateTime.Now - startTime; 42         // 减去中途消耗的时间 43         DateTime updatedUtcTime = Convert.ToDateTime(dateTimeValue).Subtract(-k); 44  45         //处置北京时间 +8时    46         var updatedTime = updatedUtcTime.AddHours(8); 47  48         //转换System.DateTime到SystemTime    49         SystemTime systemTime = new SystemTime(); 50         systemTime.FromDateTime(updatedTime); 51  52         //调用Win32 API设置系统时间    53         Win32API.SetLocalTime(ref systemTime); 54     }

系统时间辅助类 & Win32API :

 1     /// <summary>  2     /// 系统时间帮助类  3     /// </summary>  4     public struct SystemTime  5     {  6         public ushort wYear;  7         public ushort wMonth;  8         public ushort wDayOfWeek;  9         public ushort wDay; 10         public ushort wHour; 11         public ushort wMinute; 12         public ushort wSecond; 13         public ushort wMilliseconds; 14  15         /// <summary> 16         /// 从System.DateTime转换。 17         /// </summary> 18         /// <param name="time">System.DateTime类型的时间。</param> 19         public void FromDateTime(DateTime time) 20         { 21             wYear = (ushort)time.Year; 22             wMonth = (ushort)time.Month; 23             wDayOfWeek = (ushort)time.DayOfWeek; 24             wDay = (ushort)time.Day; 25             wHour = (ushort)time.Hour; 26             wMinute = (ushort)time.Minute; 27             wSecond = (ushort)time.Second; 28             wMilliseconds = (ushort)time.Millisecond; 29         } 30         /// <summary> 31         /// 转换为System.DateTime类型。 32         /// </summary> 33         /// <returns></returns> 34         public DateTime ToDateTime() 35         { 36             return new DateTime(wYear, wMonth, wDay, wHour, wMinute, wSecond, wMilliseconds); 37         } 38         /// <summary> 39         /// 静态方法。转换为System.DateTime类型。 40         /// </summary> 41         /// <param name="time">SYSTEMTIME类型的时间。</param> 42         /// <returns></returns> 43         public static DateTime ToDateTime(SystemTime time) 44         { 45             return time.ToDateTime(); 46         } 47     } 48  49     /// <summary> 50     /// 系统更新时间DLL 51     /// </summary> 52     public class Win32API 53     { 54         [DllImport("Kernel32.dll")] 55         public static extern bool SetLocalTime(ref SystemTime Time); 56         [DllImport("Kernel32.dll")] 57         public static extern void GetLocalTime(ref SystemTime Time); 58     }
View Code

Github地址:IE环境修复工具

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!