-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathNTP.cpp
323 lines (229 loc) · 7.25 KB
/
NTP.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
#include <ESP8266WiFi.h>
#include <WiFiUdp.h>
#include <Time.h>//EVITAR LLAMAR A TIME AQUI
#include "NTP.h"
IPAddress timeServer(129, 6, 15, 28); // time.nist.gov NTP server
//instanciamos un objeto de la libreria udp
WiFiUDP udp;
unsigned int localPort = 2390;
NTP::NTP() {}
/**
* Inicializacion de la libreria. Se pone a la escucha por defecto en el puerto 2390.
*/
void NTP::begin() {udp.begin(localPort);}
/**
*Inicializa la libreria escuchando en el puerto indicado
*/
void NTP::begin(int port) {udp.begin(port);}
/**
*Gestiona el envio de paquetes
*/
unsigned long NTP::sendNTPpacket(IPAddress& address) {
//Inicializamos el buffer a 0
memset(packetBuffer, 0, NTP_PACKET_SIZE);
// Inicializamos los valores del NTP request
packetBuffer[0] = 0b11100011; // LI, Version, Mode
packetBuffer[1] = 0; // Stratum, or type of clock
packetBuffer[2] = 6; // Polling Interval
packetBuffer[3] = 0xEC; // Peer Clock Precision
// 8 bytes of zero for Root Delay & Root Dispersion
packetBuffer[12] = 49;
packetBuffer[13] = 0x4E;
packetBuffer[14] = 49;
packetBuffer[15] = 52;
udp.beginPacket(address, 123); //NTP requests are to port 123
udp.write(packetBuffer, NTP_PACKET_SIZE);
udp.endPacket();
}
/**
* Devuelve el tiempo en hora unix
*/
unsigned long NTP::get_unix_time() {
WiFi.hostByName(ntpServerName, timeServerIP);//Obtenemos la dirección del host.
sendNTPpacket(timeServerIP); //Enviamos la solicitud al servidor NTP
//Esperamos a la respuesta
delay(1000);
//Nos aseguramos de haber obtenido respuesta
int cb = udp.parsePacket();
if (!cb) {
return -1;
}
else {
//Si hemos recibido los paquetes empezamos a trabajar con ellos.
udp.read(packetBuffer, NTP_PACKET_SIZE); //leemos el paquete dentro del buffer
//El servido contesta con dos palabras de 4bytes, las extraemos.
unsigned long highWord = word(packetBuffer[40], packetBuffer[41]);
unsigned long lowWord = word(packetBuffer[42], packetBuffer[43]);
//Combinamos ambas palabras en una sola para obtener el tiempo NTP (segundos transcurridos desde 1/1/1900)
unsigned long secsSince1900 = highWord << 16 | lowWord;
return secsSince1900;
}
}
/**
*Devuelve la hora actual
*/
unsigned long NTP::get_hour() {
//Obtenemos y devolvemos la hora
return ((onTime() % 86400L) / 3600);
}
/**
* Devuelve el minuto actual
*/
unsigned long NTP::get_minutes() {
//obtenemos y devolvemos los minutos
return ((onTime() % 3600) / 60);
}
/**
*Devuelve el segundo actual
*/
unsigned long NTP::get_secons() {
//Obtenemos y devolvemos los segundos
return (onTime() % 60); // print the second
}
/**
*Devuelve la hora como un String en formato HH:MM:SS
*/
String NTP::get_timeNow() {
WiFi.hostByName(ntpServerName, timeServerIP);
String timeNow;
sendNTPpacket(timeServerIP);
delay(1000);
int cb = udp.parsePacket();
if (!cb) {
return "-1";
}
else {
udp.read(packetBuffer, NTP_PACKET_SIZE);
unsigned long highWord = word(packetBuffer[40], packetBuffer[41]);
unsigned long lowWord = word(packetBuffer[42], packetBuffer[43]);
unsigned long secsSince1900 = highWord << 16 | lowWord;
const unsigned long seventyYears = 2208988800UL;
unsigned long epoch = secsSince1900 - seventyYears;
timeNow = ((epoch % 86400L) / 3600);
timeNow = timeNow + ':';
if ( ((epoch % 3600) / 60) < 10 ) {
//si han pasado menos de 10 añadimos un 0
timeNow = timeNow + '0';
}
timeNow = timeNow + ((epoch % 3600) / 60);
timeNow = timeNow + ":";
if ( (epoch % 60) < 10 ) {
timeNow = timeNow + '0';
}
timeNow = timeNow + epoch % 60;
}
return timeNow;
}
/**
* Devuelve la hora como un String con formato HH:MM:SS en el uso horario indicado
*/
String NTP::get_timeNow(int UTC) {
WiFi.hostByName(ntpServerName, timeServerIP);
String timeNow;
sendNTPpacket(timeServerIP);
delay(1000);
int cb = udp.parsePacket();
if (!cb) {
return "-1";
}
else {
udp.read(packetBuffer, NTP_PACKET_SIZE);
unsigned long highWord = word(packetBuffer[40], packetBuffer[41]);
unsigned long lowWord = word(packetBuffer[42], packetBuffer[43]);
unsigned long secsSince1900 = highWord << 16 | lowWord;
const unsigned long seventyYears = 2208988800UL;
unsigned long epoch = secsSince1900 - seventyYears;
timeNow = ((epoch % 86400L) / 3600) + UTC;
timeNow = timeNow + ':';
if ( ((epoch % 3600) / 60) < 10 ) {
timeNow = timeNow + '0';
}
timeNow = timeNow + ((epoch % 3600) / 60);
timeNow = timeNow + ":";
if ( (epoch % 60) < 10 ) {
timeNow = timeNow + '0';
}
timeNow = timeNow + epoch % 60;
}
return timeNow;
}
time_t NTP::toTime( int dia, int mes, int anyo, int hora, int minuto, int segundo){
tmElements_t Fecha ; // Estructura para time
Fecha.Second = segundo;
Fecha.Minute = minuto ;
Fecha.Hour = hora ;
Fecha.Day = dia ;
Fecha.Month = mes ;
Fecha.Year = anyo -1970 ;
return makeTime(Fecha) ;
}
int NTP::get_year() {
// TIENE QUE CALCULAR EL ANYO POR SI MISMA!!
WiFi.hostByName(ntpServerName, timeServerIP);
String timeNow;
sendNTPpacket(timeServerIP);
delay(1000);
int cb = udp.parsePacket();
if (!cb) {
return -1;
}
else {
udp.read(packetBuffer, NTP_PACKET_SIZE);
unsigned long highWord = word(packetBuffer[40], packetBuffer[41]);
unsigned long lowWord = word(packetBuffer[42], packetBuffer[43]);
unsigned long secsSince1900 = highWord << 16 | lowWord;
const unsigned long seventyYears = 2208988800UL;
unsigned long epoch = secsSince1900 - seventyYears;
return epoch;
//return year();
}
}
int NTP::get_month() {
//MEJORAR
return month();
}
int NTP::get_day() {
// MEJORAR
return day();
}
int NTP::onTime(){
//OPTIMIZAR.
WiFi.hostByName(ntpServerName, timeServerIP);
String timeNow;
sendNTPpacket(timeServerIP);
delay(1000);
int cb = udp.parsePacket();
if (!cb) {
return -1;
}else {
udp.read(packetBuffer, NTP_PACKET_SIZE);
unsigned long highWord = word(packetBuffer[40], packetBuffer[41]);
unsigned long lowWord = word(packetBuffer[42], packetBuffer[43]);
unsigned long secsSince1900 = highWord << 16 | lowWord;
const unsigned long seventyYears = 2208988800UL;
unsigned long epoch = secsSince1900 - seventyYears;
setTime(epoch);//Devolver el tiempo y calcularlo con funciones dia/mes/anyo
return epoch;
}
}
int NTP::ajusteHorario( int dia, int mes, int anyo, int hora, int minuto, int segundo){
int ajuste;
time_t cambio_1, cambio_2, fecha_hoy;
for (int i = 31 ; i >0 ; i--){
cambio_1 = toTime(i, 3, 2015, 2, 0, 0) ; // A las 2 am seran las 3
if ( weekday( cambio_1) == 1 ) // Domingo = 1
break ;
}
for (int i = 31 ; i >0 ; i--){
cambio_2 = toTime(i, 10, 2015, 3, 0, 0) ; // A las 3 am seran las 2
if ( weekday( cambio_2) == 1 ) // Domingo = 1
break;
}
fecha_hoy = toTime(dia, mes, anyo, hora, minuto, segundo);
if ( fecha_hoy > cambio_1 && fecha_hoy < cambio_2){
ajuste = 2;
}else{
ajuste = 1;
}
return ajuste;
}