1 #include <iostream>
2 #include <stddef.h>
3 #include <time.h>
4 #include <WinSock.h>
5 #pragma comment (lib,"Ws2_32")
6
7 using namespace std;
8
9 struct NTP_Packet
10 {
11 int Control_Word;
12 int root_delay;
13 int root_dispersion;
14 int reference_identifier;
15 __int64 reference_timestamp;
16 __int64 originate_timestamp;
17 __int64 receive_timestamp;
18 int transmit_timestamp_seconds;
19 int transmit_timestamp_fractions;
20 };
21
22 /************************************************************************/
23 /* 函数说明:自动与时间服务器同步更新
24 /* 参数说明:无
25 /* 返 回 值:成功返回TRUE,失败返回FALSE
26 /************************************************************************/
27 BOOL UpdateSysTime()
28 {
29 WORD wVersionRequested;
30 WSADATA wsaData;
31
32 // 初始化版本
33 wVersionRequested = MAKEWORD( 1, 1 );
34 if (0!=WSAStartup(wVersionRequested, &wsaData))
35 {
36 WSACleanup();
37 return FALSE;
38 }
39 if (LOBYTE(wsaData.wVersion)!=1 || HIBYTE(wsaData.wVersion)!=1)
40 {
41 WSACleanup( );
42 return FALSE;
43 }
44
45 // 这个IP是中国大陆时间同步服务器地址,可自行修改
46 SOCKET soc=socket(AF_INET,SOCK_DGRAM,IPPROTO_UDP);
47 struct sockaddr_in addrSrv;
48 addrSrv.sin_addr.S_un.S_addr=inet_addr("132.163.4.101");//美国国家标准化研究所
49 addrSrv.sin_family=AF_INET;
50 addrSrv.sin_port=htons(37);//端口是37
51
52 NTP_Packet NTP_Send,NTP_Recv;
53 NTP_Send.Control_Word = htonl(0x0B000000);
54 NTP_Send.root_delay = 0;
55 NTP_Send.root_dispersion = 0;
56 NTP_Send.reference_identifier = 0;
57 NTP_Send.reference_timestamp = 0;
58 NTP_Send.originate_timestamp = 0;
59 NTP_Send.receive_timestamp = 0;
60 NTP_Send.transmit_timestamp_seconds = 0;
61 NTP_Send.transmit_timestamp_fractions = 0;
62
63 if(SOCKET_ERROR==sendto(soc,(const char*)&NTP_Send,sizeof(NTP_Send),
64 0,(struct sockaddr*)&addrSrv,sizeof(addrSrv)))
65 {
66 closesocket(soc);
67 return FALSE;
68 }
69
70 int sockaddr_Size =sizeof(addrSrv);
71 if(SOCKET_ERROR==recvfrom(soc,(char*)&NTP_Recv,sizeof(NTP_Recv),
72 0,(struct sockaddr*)&addrSrv,&sockaddr_Size))
73 {
74 closesocket(soc);
75 return FALSE;
76 }
77
78 closesocket(soc);
79 WSACleanup();
80
81 SYSTEMTIME newtime;
82 float Splitseconds;
83 struct tm *lpLocalTime;
84 time_t ntp_time;
85
86 // 获取时间服务器的时间
87 ntp_time = ntohl(NTP_Recv.transmit_timestamp_seconds)-2208988800;
88 lpLocalTime = localtime(&ntp_time);
89 if(lpLocalTime == NULL)
90 {
91 return FALSE;
92 }
93
94 // 获取新的时间
95 newtime.wYear =lpLocalTime->tm_year+1900;
96 newtime.wMonth =lpLocalTime->tm_mon+1;
97 newtime.wDayOfWeek =lpLocalTime->tm_wday;
98 newtime.wDay =lpLocalTime->tm_mday;
99 newtime.wHour =lpLocalTime->tm_hour;
100 newtime.wMinute =lpLocalTime->tm_min;
101 newtime.wSecond =lpLocalTime->tm_sec;
102
103 // 设置时间精度
104 Splitseconds=(float)ntohl(NTP_Recv.transmit_timestamp_fractions);
105 Splitseconds=(float)0.000000000200 * Splitseconds;
106 Splitseconds=(float)1000.0 * Splitseconds;
107 newtime.wMilliseconds = (unsigned short)Splitseconds;
108
109
110 // 修改本机系统时间
111 SetLocalTime(&newtime);
112 return TRUE;
113 }
114
115 int main(int argc, char *argv[])
116 {
117 UpdateSysTime();
118 return 0;
119 }