PUD: cfg: remove pointless comments of setters
[olsrd.git] / lib / pud / src / configuration.c
1 #include "configuration.h"
2
3 /* Plugin includes */
4 #include "pud.h"
5 #include "networkInterfaces.h"
6 #include "netTools.h"
7 #include "posFile.h"
8 #include "configTools.h"
9
10 /* OLSR includes */
11 #include <olsr_protocol.h>
12
13 /* System includes */
14 #include <unistd.h>
15 #include <nmea/util.h>
16 #include <OlsrdPudWireFormat/nodeIdConversion.h>
17 #include <limits.h>
18
19 /*
20  * Note:
21  * Setters must return true when an error is detected, false otherwise
22  */
23
24 /*
25  * nodeIdType
26  */
27
28 /** The nodeIdType */
29 static NodeIdType nodeIdType = PUD_NODE_ID_TYPE_DEFAULT;
30
31 /**
32  @return
33  The node ID type
34  */
35 NodeIdType getNodeIdTypeNumber(void) {
36         return nodeIdType;
37 }
38
39 int setNodeIdType(const char *value, void *data __attribute__ ((unused)),
40                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
41         static const char * valueName = PUD_NODE_ID_TYPE_NAME;
42         unsigned long long nodeIdTypeNew;
43
44         assert (value != NULL);
45
46         if (!readULL(valueName, value, &nodeIdTypeNew)) {
47                 return true;
48         }
49
50         if (!isValidNodeIdType(nodeIdTypeNew)) {
51                 pudError(false, "Configured %s (%llu) is reserved", valueName,
52                                 nodeIdTypeNew);
53                 return true;
54         }
55
56         nodeIdType = nodeIdTypeNew;
57
58         return false;
59 }
60
61 /*
62  * nodeId
63  */
64
65 /** The nodeId buffer */
66 static unsigned char nodeId[PUD_TX_NODEID_BUFFERSIZE + 1];
67
68 /** The length of the string in the nodeId buffer */
69 static size_t nodeIdLength = 0;
70
71 /** True when the nodeId is set */
72 static bool nodeIdSet = false;
73
74 /** The nodeId as a binary representation, with status */
75 static nodeIdBinaryType nodeIdBinary;
76
77 /**
78  @return
79  The node ID
80  */
81 unsigned char * getNodeId(void) {
82         return getNodeIdWithLength(NULL);
83 }
84
85 /**
86  Get the nodeId and its length
87
88  @param length
89  a pointer to the variable in which to store the nodeId length (allowed to be
90  NULL, in which case the length is not stored)
91
92  @return
93  The node ID
94  */
95 unsigned char * getNodeIdWithLength(size_t *length) {
96         if (!nodeIdSet) {
97                 setNodeId("", NULL, (set_plugin_parameter_addon) {.pc = NULL});
98         }
99
100         if (length != NULL) {
101                 *length = nodeIdLength;
102         }
103
104         return &nodeId[0];
105 }
106
107 /**
108  Get the nodeIdBinary
109
110  @return
111  The node ID in binary representation
112  */
113 nodeIdBinaryType * getNodeIdBinary(void) {
114         if (!nodeIdBinary.set) {
115                 setNodeId("", NULL, (set_plugin_parameter_addon) {.pc = NULL});
116         }
117
118         return &nodeIdBinary;
119 }
120
121 int setNodeId(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
122         static const char * valueName = PUD_NODE_ID_NAME;
123         size_t valueLength;
124
125         assert (value != NULL);
126
127         valueLength = strlen(value);
128         if (valueLength > PUD_TX_NODEID_BUFFERSIZE) {
129                 pudError(false, "Configured %s is too long, maximum length is"
130                         " %u, current length is %lu", valueName, PUD_TX_NODEID_BUFFERSIZE,
131                                 (unsigned long) valueLength);
132                 return true;
133         }
134
135         strcpy((char *) &nodeId[0], value);
136         nodeIdLength = valueLength;
137         nodeIdSet = true;
138
139         return false;
140 }
141
142 /*
143  * nodeId Validation
144  */
145
146 /**
147  Validate whether the configured nodeId is valid w.r.t. the configured
148  nodeIdType, for types that are MAC addresses
149
150  @return
151  - true when ok
152  - false on failure
153  */
154 static bool intSetupNodeIdBinaryMAC(void) {
155         unsigned char * mac = getMainIpMacAddress();
156         if (!mac) {
157                 return false;
158         }
159
160         return setupNodeIdBinaryMAC(&nodeIdBinary, mac);
161 }
162
163 /**
164  Validate whether the configured nodeId is valid w.r.t. the configured
165  nodeIdType, for types that fit in an unsigned long long (64 bits)
166
167  @param min
168  the minimum value
169  @param max
170  the maximum value
171  @param bytes
172  the number of bytes in the buffer
173
174  @return
175  - true when ok
176  - false on failure
177  */
178 static bool intSetupNodeIdBinaryLongLong(unsigned long long min,
179                 unsigned long long max, unsigned int bytes) {
180         unsigned long long longValue = 0;
181         if (!readULL(PUD_NODE_ID_NAME, (char *) getNodeId(), &longValue)) {
182                 return false;
183         }
184
185         if ((longValue < min) || (longValue > max)) {
186                 pudError(false, "%s value %llu is out of range [%llu,%llu]",
187                                 PUD_NODE_ID_NAME, longValue, min, max);
188                 return false;
189         }
190
191         return setupNodeIdBinaryLongLong(&nodeIdBinary, longValue, bytes);
192 }
193
194 /**
195  Validate whether the configured nodeId is valid w.r.t. the configured
196  nodeIdType, for types that are strings
197
198  @return
199  - true when ok
200  - false on failure
201  */
202 static bool intSetupNodeIdBinaryString(void) {
203         bool invalidChars;
204         char report[256];
205         size_t nodeidlength;
206         char * nodeid = (char *)getNodeIdWithLength(&nodeidlength);
207
208         invalidChars = nmea_string_has_invalid_chars(nodeid,
209                         PUD_NODE_ID_NAME, &report[0], sizeof(report));
210         if (invalidChars) {
211                 pudError(false, "%s", &report[0]);
212                 return false;
213         }
214
215         if (nodeidlength > PUD_TX_NODEID_BUFFERSIZE) {
216                 pudError(false, "%s value \"%s\" is too long", PUD_NODE_ID_NAME, &nodeid[0]);
217                 return false;
218         }
219
220         return setupNodeIdBinaryString(&nodeIdBinary, nodeid, nodeidlength);
221 }
222
223 /**
224  Validate whether the configured nodeId is valid w.r.t. the configured
225  nodeIdType, for types that are IP addresses
226
227  @return
228  - true when ok
229  - false on failure
230  */
231 static bool intSetupNodeIdBinaryIp(void) {
232         void * src;
233         size_t length;
234         if (olsr_cnf->ip_version == AF_INET) {
235                 src = &olsr_cnf->main_addr.v4;
236                 length = sizeof(struct in_addr);
237         } else {
238                 src = &olsr_cnf->main_addr.v6;
239                 length = sizeof(struct in6_addr);
240         }
241
242         return setupNodeIdBinaryIp(&nodeIdBinary, src, length);
243 }
244
245 /**
246  Validate whether the configured nodeId is valid w.r.t. the configured
247  nodeIdType
248
249  @return
250  - true when ok
251  - false on failure
252  */
253 static bool setupNodeIdBinaryAndValidate(NodeIdType nodeIdTypeNumber) {
254         switch (nodeIdTypeNumber) {
255                 case PUD_NODEIDTYPE_MAC: /* hardware address */
256                         return intSetupNodeIdBinaryMAC();
257
258                 case PUD_NODEIDTYPE_MSISDN: /* an MSISDN number */
259                         return intSetupNodeIdBinaryLongLong(PUD_NODEIDTYPE_MSISDN_MIN,
260                                 PUD_NODEIDTYPE_MSISDN_MAX, PUD_NODEIDTYPE_MSISDN_BYTES);
261
262                 case PUD_NODEIDTYPE_TETRA: /* a Tetra number */
263                         return intSetupNodeIdBinaryLongLong(PUD_NODEIDTYPE_TETRA_MIN,
264                                 PUD_NODEIDTYPE_TETRA_MAX, PUD_NODEIDTYPE_TETRA_BYTES);
265
266                 case PUD_NODEIDTYPE_DNS: /* DNS name */
267                         return intSetupNodeIdBinaryString();
268
269                 case PUD_NODEIDTYPE_MMSI: /* an AIS MMSI number */
270                         return intSetupNodeIdBinaryLongLong(PUD_NODEIDTYPE_MMSI_MIN,
271                                 PUD_NODEIDTYPE_MMSI_MAX, PUD_NODEIDTYPE_MMSI_BYTES);
272
273                 case PUD_NODEIDTYPE_URN: /* a URN number */
274                         return intSetupNodeIdBinaryLongLong(PUD_NODEIDTYPE_URN_MIN,
275                                 PUD_NODEIDTYPE_URN_MAX, PUD_NODEIDTYPE_URN_BYTES);
276
277                 case PUD_NODEIDTYPE_192:
278                         return intSetupNodeIdBinaryLongLong(PUD_NODEIDTYPE_192_MIN,
279                                 PUD_NODEIDTYPE_192_MAX, PUD_NODEIDTYPE_192_BYTES);
280
281                 case PUD_NODEIDTYPE_193:
282                         return intSetupNodeIdBinaryLongLong(PUD_NODEIDTYPE_193_MIN,
283                                 PUD_NODEIDTYPE_193_MAX, PUD_NODEIDTYPE_193_BYTES);
284
285                 case PUD_NODEIDTYPE_194:
286                         return intSetupNodeIdBinaryLongLong(PUD_NODEIDTYPE_194_MIN,
287                                 PUD_NODEIDTYPE_194_MAX, PUD_NODEIDTYPE_194_BYTES);
288
289                 case PUD_NODEIDTYPE_IPV4: /* IPv4 address */
290                 case PUD_NODEIDTYPE_IPV6: /* IPv6 address */
291                 default: /* unsupported */
292                         return intSetupNodeIdBinaryIp();
293         }
294
295         return false;
296 }
297
298 /*
299  * rxNonOlsrIf
300  */
301
302 /** The maximum number of RX non-OLSR interfaces */
303 #define PUD_RX_NON_OLSR_IF_MAX 32
304
305 /** Array with RX non-OLSR interface names */
306 static unsigned char rxNonOlsrInterfaceNames[PUD_RX_NON_OLSR_IF_MAX][IFNAMSIZ + 1];
307
308 /** The number of RX non-OLSR interface names in the array */
309 static unsigned int rxNonOlsrInterfaceCount = 0;
310
311 /**
312  Determine whether a give interface name is configured as a receive non-OLSR
313  interface.
314
315  @param ifName
316  The interface name to check
317
318  @return
319  - true when the given interface name is configured as a receive non-OLSR
320  interface
321  - false otherwise
322  */
323 bool isRxNonOlsrInterface(const char *ifName) {
324         unsigned int i;
325
326         assert (ifName != NULL);
327
328         for (i = 0; i < rxNonOlsrInterfaceCount; i++) {
329                 if (strncmp((char *) &rxNonOlsrInterfaceNames[i][0], ifName, IFNAMSIZ
330                                 + 1) == 0) {
331                         return true;
332                 }
333         }
334
335         return false;
336 }
337
338 int addRxNonOlsrInterface(const char *value, void *data __attribute__ ((unused)),
339                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
340         unsigned long valueLength;
341
342         assert (value != NULL);
343
344         valueLength = strlen(value);
345         if (valueLength > IFNAMSIZ) {
346                 pudError(false, "Configured %s (%s) is too long,"
347                         " maximum length is %u, current length is %lu",
348                                 PUD_RX_NON_OLSR_IF_NAME, value, IFNAMSIZ, valueLength);
349                 return true;
350         }
351
352         if (!isRxNonOlsrInterface(value)) {
353                 if (rxNonOlsrInterfaceCount >= PUD_RX_NON_OLSR_IF_MAX) {
354                         pudError(false, "Can't configure more than %u receive interfaces",
355                                         PUD_RX_NON_OLSR_IF_MAX);
356                         return true;
357                 }
358
359                 strcpy((char *) &rxNonOlsrInterfaceNames[rxNonOlsrInterfaceCount][0],
360                                 value);
361                 rxNonOlsrInterfaceCount++;
362         }
363
364         return false;
365 }
366
367 /*
368  * rxAllowedSourceIpAddress
369  */
370
371 /** The maximum number of RX allowed source IP addresses */
372 #define PUD_RX_ALLOWED_SOURCE_IP_MAX 32
373
374 /** Array with RX allowed source IP addresses */
375 static union olsr_sockaddr rxAllowedSourceIpAddresses[PUD_RX_ALLOWED_SOURCE_IP_MAX];
376
377 /** The number of RX allowed source IP addresses in the array */
378 static unsigned int rxAllowedSourceIpAddressesCount = 0;
379
380 /**
381  Determine whether a give IP address is configured as an allowed source IP
382  address.
383
384  @param sender
385  The IP address to check
386
387  @return
388  - true when the given IP address is configured as an allowed source IP
389  address
390  - false otherwise
391  */
392 bool isRxAllowedSourceIpAddress(union olsr_sockaddr * sender) {
393         unsigned int i;
394
395         if (rxAllowedSourceIpAddressesCount == 0) {
396                 return true;
397         }
398
399         if (sender == NULL) {
400                 return false;
401         }
402
403         for (i = 0; i < rxAllowedSourceIpAddressesCount; i++) {
404                 if (sender->in.sa_family != rxAllowedSourceIpAddresses[i].in.sa_family) {
405                         continue;
406                 }
407
408                 if (sender->in.sa_family == AF_INET) {
409                         if (memcmp(&rxAllowedSourceIpAddresses[i].in4.sin_addr, &sender->in4.sin_addr, sizeof(struct in_addr))
410                                         == 0) {
411                                 return true;
412                         }
413                 } else {
414                         if (memcmp(&rxAllowedSourceIpAddresses[i].in6.sin6_addr, &sender->in6.sin6_addr, sizeof(struct in6_addr))
415                                         == 0) {
416                                 return true;
417                         }
418                 }
419         }
420
421         return false;
422 }
423
424 int addRxAllowedSourceIpAddress(const char *value, void *data __attribute__ ((unused)),
425                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
426         static const char * valueName = PUD_RX_ALLOWED_SOURCE_IP_NAME;
427         union olsr_sockaddr addr;
428         bool addrSet = false;
429
430         assert (value != NULL);
431
432         if (rxAllowedSourceIpAddressesCount >= PUD_RX_ALLOWED_SOURCE_IP_MAX) {
433                 pudError(false, "Can't configure more than %u allowed source IP"
434                         " addresses", PUD_RX_ALLOWED_SOURCE_IP_MAX);
435                 return true;
436         }
437
438         if (!readIPAddress(valueName, value, 0, &addr, &addrSet)) {
439                 return true;
440         }
441
442         if (!isRxAllowedSourceIpAddress(&addr)) {
443                 rxAllowedSourceIpAddresses[rxAllowedSourceIpAddressesCount] = addr;
444                 rxAllowedSourceIpAddressesCount++;
445         }
446
447         return false;
448 }
449
450 /*
451  * rxMcAddr
452  */
453
454 /** The rx multicast address */
455 static union olsr_sockaddr rxMcAddr;
456
457 /** True when the rx multicast address is set */
458 static bool rxMcAddrSet = false;
459
460 /**
461  @return
462  The receive multicast address (in network byte order). Sets both the address
463  and the port to their default values when the address was not yet set.
464  */
465 union olsr_sockaddr * getRxMcAddr(void) {
466         if (!rxMcAddrSet) {
467                 setRxMcAddr((olsr_cnf->ip_version == AF_INET) ? PUD_RX_MC_ADDR_4_DEFAULT : PUD_RX_MC_ADDR_6_DEFAULT,
468                                 NULL, ((set_plugin_parameter_addon) {.pc = NULL}));
469         }
470         return &rxMcAddr;
471 }
472
473 int setRxMcAddr(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
474         static const char * valueName = PUD_RX_MC_ADDR_NAME;
475
476         assert(value != NULL);
477
478         if (!readIPAddress(valueName, value, PUD_RX_MC_PORT_DEFAULT, &rxMcAddr, &rxMcAddrSet)) {
479                         return true;
480         }
481
482         if (!isMulticast(&rxMcAddr)) {
483                 pudError(false, "Value of parameter %s (%s) is not a multicast address",
484                                 valueName, value);
485                 return true;
486         }
487
488         return false;
489 }
490
491 /*
492  * rxMcPort
493  */
494
495 /**
496  @return
497  The receive multicast port (in network byte order)
498  */
499 unsigned short getRxMcPort(void) {
500         in_port_t * port;
501         union olsr_sockaddr * sock = getRxMcAddr();
502         getOlsrSockaddrPortAddress(sock, &port);
503         return *port;
504 }
505
506 int setRxMcPort(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
507         static const char * valueName = PUD_RX_MC_PORT_NAME;
508         unsigned short rxMcPortNew;
509         in_port_t * port;
510         union olsr_sockaddr * addr = getRxMcAddr();
511
512         assert (value != NULL);
513
514         if (!readUS(valueName, value, &rxMcPortNew)) {
515                 return true;
516         }
517
518         if (rxMcPortNew < 1) {
519                 pudError(false, "Value of parameter %s (%u) is outside of valid range 1-65535", valueName, rxMcPortNew);
520                 return true;
521         }
522
523         getOlsrSockaddrPortAddress(addr, &port);
524         *port = htons((uint16_t) rxMcPortNew);
525
526         return false;
527 }
528
529 /*
530  * positionFile
531  */
532
533 /** The positionFile buffer */
534 static char positionFile[PATH_MAX + 1];
535
536 /** True when the positionFile is set */
537 static bool positionFileSet = false;
538
539 /**
540  @return
541  The positionFile (NULL when not set)
542  */
543 char * getPositionFile(void) {
544         if (!positionFileSet) {
545                 return NULL;
546         }
547
548         return &positionFile[0];
549 }
550
551 int setPositionFile(const char *value, void *data __attribute__ ((unused)),
552                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
553         static const char * valueName = PUD_POSFILE_NAME;
554         size_t valueLength;
555
556         assert(value != NULL);
557
558         if (!startPositionFile()) {
559                 stopPositionFile();
560                 return true;
561         }
562
563         valueLength = strlen(value);
564         if (valueLength > PATH_MAX) {
565                 pudError(false, "Configured %s is too long, maximum length is"
566                                 " %u, current length is %lu", valueName, PATH_MAX, (unsigned long) valueLength);
567                 return true;
568         }
569
570         strcpy((char *) &positionFile[0], value);
571         positionFileSet = true;
572
573         return false;
574 }
575
576 /*
577  * txNonOlsrIf
578  */
579
580 /** The maximum number of rx non-olsr interfaces */
581 #define PUD_TX_NON_OLSR_IF_MAX 32
582
583 /** Array with tx non-olsr interface names */
584 static unsigned char txNonOlsrInterfaceNames[PUD_TX_NON_OLSR_IF_MAX][IFNAMSIZ + 1];
585
586 /** The number of tx interface names in the array */
587 static unsigned int txNonOlsrInterfaceCount = 0;
588
589 /**
590  Determine whether a give interface name is configured as a transmit non-OLSR
591  interface.
592
593  @param ifName
594  The interface to check
595
596  @return
597  - true when the given interface name is configured as a transmit non-OLSR
598  interface
599  - false otherwise
600  */
601 bool isTxNonOlsrInterface(const char *ifName) {
602         unsigned int i;
603
604         assert (ifName != NULL);
605
606         for (i = 0; i < txNonOlsrInterfaceCount; i++) {
607                 if (strncmp((char *) &txNonOlsrInterfaceNames[i][0], ifName, IFNAMSIZ
608                                 + 1) == 0) {
609                         return true;
610                 }
611         }
612
613         return false;
614 }
615
616 int addTxNonOlsrInterface(const char *value, void *data __attribute__ ((unused)),
617                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
618         unsigned long valueLength;
619
620         assert (value != NULL);
621
622         valueLength = strlen(value);
623         if (valueLength > IFNAMSIZ) {
624                 pudError(false, "Configured %s (%s) is too long,"
625                         " maximum length is %u, current length is %lu",
626                                 PUD_TX_NON_OLSR_IF_NAME, value, IFNAMSIZ, valueLength);
627                 return true;
628         }
629
630         if (!isTxNonOlsrInterface(value)) {
631                 if (txNonOlsrInterfaceCount >= PUD_TX_NON_OLSR_IF_MAX) {
632                         pudError(false, "Can not configure more than %u transmit"
633                                 " interfaces", PUD_TX_NON_OLSR_IF_MAX);
634                         return true;
635                 }
636
637                 strcpy((char *) &txNonOlsrInterfaceNames[txNonOlsrInterfaceCount][0],
638                                 value);
639                 txNonOlsrInterfaceCount++;
640         }
641
642         return false;
643 }
644
645 /*
646  * txMcAddr
647  */
648
649 /** The tx multicast address */
650 static union olsr_sockaddr txMcAddr;
651
652 /** True when the tx multicast address is set */
653 static bool txMcAddrSet = false;
654
655 /**
656  @return
657  The transmit multicast address (in network byte order). Sets both the address
658  and the port to their default values when the address was not yet set.
659  */
660 union olsr_sockaddr * getTxMcAddr(void) {
661         if (!txMcAddrSet) {
662                 setTxMcAddr((olsr_cnf->ip_version == AF_INET) ? PUD_TX_MC_ADDR_4_DEFAULT : PUD_TX_MC_ADDR_6_DEFAULT,
663                                 NULL, ((set_plugin_parameter_addon) {.pc = NULL}));
664         }
665         return &txMcAddr;
666 }
667
668 int setTxMcAddr(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
669         static const char * valueName = PUD_TX_MC_ADDR_NAME;
670
671         assert (value != NULL);
672
673         if (!readIPAddress(valueName, value, PUD_TX_MC_PORT_DEFAULT, &txMcAddr, &txMcAddrSet)) {
674                         return true;
675         }
676
677         if (!isMulticast(&txMcAddr)) {
678                 pudError(false, "Value of parameter %s (%s) is not a multicast address",
679                                 valueName, value);
680                 return true;
681         }
682
683         return false;
684 }
685
686 /*
687  * txMcPort
688  */
689
690 /**
691  @return
692  The transmit multicast port (in network byte order)
693  */
694 unsigned short getTxMcPort(void) {
695         in_port_t * port;
696         union olsr_sockaddr * sock = getTxMcAddr();
697         getOlsrSockaddrPortAddress(sock, &port);
698         return *port;
699 }
700
701 int setTxMcPort(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
702         static const char * valueName = PUD_TX_MC_PORT_NAME;
703         unsigned short txMcPortNew;
704         in_port_t * port;
705         union olsr_sockaddr * addr = getTxMcAddr();
706
707         assert (value != NULL);
708
709         if (!readUS(valueName, value, &txMcPortNew)) {
710                 return true;
711         }
712
713         if (txMcPortNew < 1) {
714                 pudError(false, "Value of parameter %s (%u) is outside of valid range 1-65535", valueName, txMcPortNew);
715                 return true;
716         }
717
718         getOlsrSockaddrPortAddress(addr, &port);
719         *port = htons((uint16_t) txMcPortNew);
720
721         return false;
722 }
723
724 /*
725  * uplinkAddr
726  */
727
728 /** The uplink address */
729 static union olsr_sockaddr uplinkAddr;
730
731 /** True when the uplink address is set */
732 static bool uplinkAddrSet = false;
733
734 /**
735  @return
736  - true when the uplink address is set
737  - false otherwise
738  */
739 bool isUplinkAddrSet(void) {
740         return uplinkAddrSet;
741 }
742
743 /**
744  @return
745  The uplink address (in network byte order). Sets both the address
746  and the port to their default values when the address was not yet set.
747  */
748 union olsr_sockaddr * getUplinkAddr(void) {
749         if (!uplinkAddrSet) {
750                 setUplinkAddr((olsr_cnf->ip_version == AF_INET) ? PUD_UPLINK_ADDR_4_DEFAULT : PUD_UPLINK_ADDR_6_DEFAULT,
751                                 NULL, ((set_plugin_parameter_addon) {.pc = NULL}));
752         }
753         return &uplinkAddr;
754 }
755
756 int setUplinkAddr(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
757         static const char * valueName = PUD_UPLINK_ADDR_NAME;
758
759         assert (value != NULL);
760
761         if (!readIPAddress(valueName, value, PUD_UPLINK_PORT_DEFAULT, &uplinkAddr, &uplinkAddrSet)) {
762                         return true;
763         }
764
765         return false;
766 }
767
768 /*
769  * uplinkPort
770  */
771
772 /**
773  @return
774  The uplink port (in network byte order)
775  */
776 unsigned short getUplinkPort(void) {
777         in_port_t * port;
778         union olsr_sockaddr * addr = getUplinkAddr();
779         getOlsrSockaddrPortAddress(addr, &port);
780         return *port;
781 }
782
783 int setUplinkPort(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
784         static const char * valueName = PUD_UPLINK_PORT_NAME;
785         unsigned short uplinkPortNew;
786         in_port_t * port;
787         union olsr_sockaddr * addr = getUplinkAddr();
788
789         assert (value != NULL);
790
791         if (!readUS(valueName, value, &uplinkPortNew)) {
792                 return true;
793         }
794
795         if (uplinkPortNew < 1) {
796                 pudError(false, "Value of parameter %s (%u) is outside of valid range 1-65535", valueName, uplinkPortNew);
797                 return true;
798         }
799
800         getOlsrSockaddrPortAddress(addr, &port);
801         *port = htons((uint16_t) uplinkPortNew);
802
803         return false;
804 }
805
806
807 /*
808  * downlinkPort
809  */
810
811 /** the downlink port */
812 unsigned short downlinkPort = 0;
813
814 /** true when the downlinkPort is set */
815 bool downlinkPortSet = false;
816
817 /**
818  @return
819  The downlink port (in network byte order)
820  */
821 unsigned short getDownlinkPort(void) {
822         if (!downlinkPortSet) {
823                 downlinkPort = htons(PUD_DOWNLINK_PORT_DEFAULT);
824                 downlinkPortSet = true;
825         }
826
827         return downlinkPort;
828 }
829
830 int setDownlinkPort(const char *value, void *data __attribute__ ((unused)),
831                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
832         static const char * valueName = PUD_DOWNLINK_PORT_NAME;
833         unsigned short downlinkPortNew;
834
835         assert(value != NULL);
836
837         if (!readUS(valueName, value, &downlinkPortNew)) {
838                 return true;
839         }
840
841         if (downlinkPortNew < 1) {
842                 pudError(false, "Value of parameter %s (%u) is outside of valid range 1-65535", valueName, downlinkPortNew);
843                 return true;
844         }
845
846         downlinkPort = htons(downlinkPortNew);
847         downlinkPortSet = true;
848
849         return false;
850 }
851
852 /*
853  * txTtl
854  */
855
856 /** The tx TTL */
857 static unsigned char txTtl = PUD_TX_TTL_DEFAULT;
858
859 /**
860  @return
861  The transmit multicast IP packet time-to-live
862  */
863 unsigned char getTxTtl(void) {
864         return txTtl;
865 }
866
867 int setTxTtl(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
868         static const char * valueName = PUD_TX_TTL_NAME;
869         unsigned long long txTtlNew;
870
871         assert (value != NULL);
872
873         if (!readULL(valueName, value, &txTtlNew)) {
874                 return true;
875         }
876
877         if ((txTtlNew < 1) || (txTtlNew > MAX_TTL)) {
878                 pudError(false, "Configured %s (%llu) is outside of"
879                         " valid range 1-%u", valueName, txTtlNew, MAX_TTL);
880                 return true;
881         }
882
883         txTtl = txTtlNew;
884
885         return false;
886 }
887
888 /*
889  * txNmeaMessagePrefix
890  */
891
892 /** The exact length of the tx NMEA message prefix */
893 #define PUD_TXNMEAMESSAGEPREFIXLENGTH 4
894
895 /** The tx NMEA message prefix buffer */
896 static unsigned char txNmeaMessagePrefix[PUD_TXNMEAMESSAGEPREFIXLENGTH + 1];
897
898 /** True when the tx NMEA message prefix is set */
899 static bool txNmeaMessagePrefixSet = false;
900
901 /**
902  @return
903  The transmit multicast NMEA message prefix
904  */
905 unsigned char * getTxNmeaMessagePrefix(void) {
906         if (!txNmeaMessagePrefixSet) {
907                 setTxNmeaMessagePrefix(PUD_TX_NMEAMESSAGEPREFIX_DEFAULT, NULL,
908                                 (set_plugin_parameter_addon) {.pc = NULL});
909         }
910         return &txNmeaMessagePrefix[0];
911 }
912
913 int setTxNmeaMessagePrefix(const char *value, void *data __attribute__ ((unused)),
914                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
915         static const char * valueName = PUD_TX_NMEAMESSAGEPREFIX_NAME;
916         size_t valueLength;
917         bool invalidChars;
918         char report[256];
919
920         assert (value != NULL);
921
922         valueLength = strlen(value);
923         if (valueLength != PUD_TXNMEAMESSAGEPREFIXLENGTH) {
924                 pudError(false, "Configured %s (%s) must be %u exactly characters",
925                                 valueName, value, PUD_TXNMEAMESSAGEPREFIXLENGTH);
926                 return true;
927         }
928
929         invalidChars = nmea_string_has_invalid_chars(value, valueName, &report[0],
930                         sizeof(report));
931         if (invalidChars) {
932                 pudError(false, "%s", &report[0]);
933                 return true;
934         }
935
936         if ((strchr(value, ' ') != NULL) || (strchr(value, '\t') != NULL)) {
937                 pudError(false, "Configured %s (%s) can not contain whitespace",
938                                 valueName, value);
939                 return true;
940         }
941
942         strcpy((char *) &txNmeaMessagePrefix[0], value);
943         txNmeaMessagePrefixSet = true;
944         return false;
945 }
946
947 /*
948  * olsrTtl
949  */
950
951 /** The OLSR TTL */
952 static unsigned char olsrTtl = PUD_OLSR_TTL_DEFAULT;
953
954 /**
955  @return
956  The OLSR multicast IP packet time-to-live
957  */
958 unsigned char getOlsrTtl(void) {
959         return olsrTtl;
960 }
961
962 int setOlsrTtl(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
963         static const char * valueName = PUD_OLSR_TTL_NAME;
964         unsigned long long olsrTtlNew;
965
966         assert (value != NULL);
967
968         if (!readULL(valueName, value, &olsrTtlNew)) {
969                 return true;
970         }
971
972         if ((olsrTtlNew < 1) || (olsrTtlNew > MAX_TTL)) {
973                 pudError(false, "Configured %s (%llu) is outside of valid range 1-%u",
974                                 valueName, olsrTtlNew, MAX_TTL);
975                 return true;
976         }
977
978         olsrTtl = olsrTtlNew;
979
980         return false;
981 }
982
983 /*
984  * updateIntervalStationary
985  */
986
987 /** The stationary interval update plugin parameter (in seconds) */
988 static unsigned long long updateIntervalStationary = PUD_UPDATE_INTERVAL_STATIONARY_DEFAULT;
989
990 /**
991  @return
992  The stationary interval update plugin parameter (in seconds)
993  */
994 unsigned long long getUpdateIntervalStationary(void) {
995         return updateIntervalStationary;
996 }
997
998 int setUpdateIntervalStationary(const char *value, void *data __attribute__ ((unused)),
999                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1000         static const char * valueName = PUD_UPDATE_INTERVAL_STATIONARY_NAME;
1001         unsigned long long updateIntervalStationaryNew;
1002
1003         assert (value != NULL);
1004
1005         if (!readULL(valueName, value, &updateIntervalStationaryNew)) {
1006                 return true;
1007         }
1008
1009         if (updateIntervalStationaryNew < 1) {
1010                 pudError(false, "Configured %s must be at least 1", valueName);
1011                 return true;
1012         }
1013
1014         updateIntervalStationary = updateIntervalStationaryNew;
1015
1016         return false;
1017 }
1018
1019 /*
1020  * updateIntervalMoving
1021  */
1022
1023 /** The moving interval update plugin parameter (in seconds) */
1024 static unsigned long long updateIntervalMoving = PUD_UPDATE_INTERVAL_MOVING_DEFAULT;
1025
1026 /**
1027  @return
1028  The moving interval update plugin parameter (in seconds)
1029  */
1030 unsigned long long getUpdateIntervalMoving(void) {
1031         return updateIntervalMoving;
1032 }
1033
1034 int setUpdateIntervalMoving(const char *value, void *data __attribute__ ((unused)),
1035                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1036         static const char * valueName = PUD_UPDATE_INTERVAL_MOVING_NAME;
1037         unsigned long long updateIntervalMovingNew;
1038
1039         assert (value != NULL);
1040
1041         if (!readULL(valueName, value, &updateIntervalMovingNew)) {
1042                 return true;
1043         }
1044
1045         if (updateIntervalMovingNew < 1) {
1046                 pudError(false, "Configured %s must be at least 1", valueName);
1047                 return true;
1048         }
1049
1050         updateIntervalMoving = updateIntervalMovingNew;
1051
1052         return false;
1053 }
1054
1055 /*
1056  * uplinkUpdateIntervalStationary
1057  */
1058
1059 /** The uplink stationary interval update plugin parameter (in seconds) */
1060 static unsigned long long uplinkUpdateIntervalStationary = PUD_UPLINK_UPDATE_INTERVAL_STATIONARY_DEFAULT;
1061
1062 /**
1063  @return
1064  The uplink stationary interval update plugin parameter (in seconds)
1065  */
1066 unsigned long long getUplinkUpdateIntervalStationary(void) {
1067         return uplinkUpdateIntervalStationary;
1068 }
1069
1070 int setUplinkUpdateIntervalStationary(const char *value, void *data __attribute__ ((unused)),
1071                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1072         static const char * valueName = PUD_UPLINK_UPDATE_INTERVAL_STATIONARY_NAME;
1073         unsigned long long uplinkUpdateIntervalStationaryNew;
1074
1075         assert (value != NULL);
1076
1077         if (!readULL(valueName, value, &uplinkUpdateIntervalStationaryNew)) {
1078                 return true;
1079         }
1080
1081         if (uplinkUpdateIntervalStationaryNew < 1) {
1082                 pudError(false, "Configured %s must be at least 1", valueName);
1083                 return true;
1084         }
1085
1086         uplinkUpdateIntervalStationary = uplinkUpdateIntervalStationaryNew;
1087
1088         return false;
1089 }
1090
1091 /*
1092  * uplinkUpdateIntervalMoving
1093  */
1094
1095 /** The uplink moving interval update plugin parameter (in seconds) */
1096 static unsigned long long uplinkUpdateIntervalMoving = PUD_UPLINK_UPDATE_INTERVAL_MOVING_DEFAULT;
1097
1098 /**
1099  @return
1100  The uplink moving interval update plugin parameter (in seconds)
1101  */
1102 unsigned long long getUplinkUpdateIntervalMoving(void) {
1103         return uplinkUpdateIntervalMoving;
1104 }
1105
1106 int setUplinkUpdateIntervalMoving(const char *value, void *data __attribute__ ((unused)),
1107                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1108         static const char * valueName = PUD_UPLINK_UPDATE_INTERVAL_MOVING_NAME;
1109         unsigned long long uplinkUpdateIntervalMovingNew;
1110
1111         assert (value != NULL);
1112
1113         if (!readULL(valueName, value, &uplinkUpdateIntervalMovingNew)) {
1114                 return true;
1115         }
1116
1117         if (uplinkUpdateIntervalMovingNew < 1) {
1118                 pudError(false, "Configured %s must be at least 1", valueName);
1119                 return true;
1120         }
1121
1122         uplinkUpdateIntervalMoving = uplinkUpdateIntervalMovingNew;
1123
1124         return false;
1125 }
1126
1127 /*
1128  * gatewayDeterminationInterval
1129  */
1130
1131 /** The gateway determination interval plugin parameter (in seconds) */
1132 static unsigned long long gatewayDeterminationInterval = PUD_GATEWAY_DETERMINATION_INTERVAL_DEFAULT;
1133
1134 /**
1135  @return
1136  The gateway determination interval plugin parameter (in seconds)
1137  */
1138 unsigned long long getGatewayDeterminationInterval(void) {
1139         return gatewayDeterminationInterval;
1140 }
1141
1142 int setGatewayDeterminationInterval(const char *value, void *data __attribute__ ((unused)),
1143                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1144         static const char * valueName = PUD_GATEWAY_DETERMINATION_INTERVAL_NAME;
1145         unsigned long long gatewayDeterminationIntervalNew;
1146
1147         assert (value != NULL);
1148
1149         if (!readULL(valueName, value, &gatewayDeterminationIntervalNew)) {
1150                 return true;
1151         }
1152
1153         if (gatewayDeterminationIntervalNew < 1) {
1154                 pudError(false, "Configured %s must be at least 1", valueName);
1155                 return true;
1156         }
1157
1158         gatewayDeterminationInterval = gatewayDeterminationIntervalNew;
1159
1160         return false;
1161 }
1162
1163 /*
1164  * movingSpeedThreshold
1165  */
1166
1167 /** The moving speed threshold plugin parameter (in kph) */
1168 static unsigned long long movingSpeedThreshold = PUD_MOVING_SPEED_THRESHOLD_DEFAULT;
1169
1170 /**
1171  @return
1172  The moving speed threshold plugin parameter (in kph)
1173  */
1174 unsigned long long getMovingSpeedThreshold(void) {
1175         return movingSpeedThreshold;
1176 }
1177
1178 int setMovingSpeedThreshold(const char *value, void *data __attribute__ ((unused)),
1179                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1180         static const char * valueName = PUD_MOVING_SPEED_THRESHOLD_NAME;
1181         unsigned long long movingSpeedThresholdNew;
1182
1183         assert (value != NULL);
1184
1185         if (!readULL(valueName, value, &movingSpeedThresholdNew)) {
1186                 return true;
1187         }
1188
1189         movingSpeedThreshold = movingSpeedThresholdNew;
1190
1191         return false;
1192 }
1193
1194 /*
1195  * movingDistanceThreshold
1196  */
1197
1198 /** The moving distance threshold plugin parameter (in meters) */
1199 static unsigned long long movingDistanceThreshold = PUD_MOVING_DISTANCE_THRESHOLD_DEFAULT;
1200
1201 /**
1202  @return
1203  The moving distance threshold plugin parameter (in meters)
1204  */
1205 unsigned long long getMovingDistanceThreshold(void) {
1206         return movingDistanceThreshold;
1207 }
1208
1209 int setMovingDistanceThreshold(const char *value, void *data __attribute__ ((unused)),
1210                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1211         static const char * valueName = PUD_MOVING_DISTANCE_THRESHOLD_NAME;
1212         unsigned long long movingDistanceThresholdNew;
1213
1214         assert (value != NULL);
1215
1216         if (!readULL(valueName, value, &movingDistanceThresholdNew)) {
1217                 return true;
1218         }
1219
1220         movingDistanceThreshold = movingDistanceThresholdNew;
1221
1222         return false;
1223 }
1224
1225 /*
1226  * dopMultiplier
1227  */
1228
1229 /* The DOP multiplier plugin parameter */
1230 static double dopMultiplier = PUD_DOP_MULTIPLIER_DEFAULT;
1231
1232 /**
1233  @return
1234  The DOP multiplier plugin parameter
1235  */
1236 double getDopMultiplier(void) {
1237         return dopMultiplier;
1238 }
1239
1240 int setDopMultiplier(const char *value, void *data __attribute__ ((unused)),
1241                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1242         static const char * valueName = PUD_DOP_MULTIPLIER_NAME;
1243         double dopMultiplierNew;
1244
1245         assert (value != NULL);
1246
1247         if (!readDouble(valueName, value, &dopMultiplierNew)) {
1248                 return true;
1249         }
1250
1251         dopMultiplier = dopMultiplierNew;
1252
1253         return false;
1254 }
1255
1256 /*
1257  * defaultHdop
1258  */
1259
1260 /** The default HDOP plugin parameter (in meters) */
1261 static unsigned long long defaultHdop = PUD_DEFAULT_HDOP_DEFAULT;
1262
1263 /**
1264  @return
1265  The default HDOP plugin parameter (in meters)
1266  */
1267 unsigned long long getDefaultHdop(void) {
1268         return defaultHdop;
1269 }
1270
1271 int setDefaultHdop(const char *value, void *data __attribute__ ((unused)),
1272                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1273         static const char * valueName = PUD_MOVING_DISTANCE_THRESHOLD_NAME;
1274         unsigned long long defaultHdopNew;
1275
1276         assert (value != NULL);
1277
1278         if (!readULL(valueName, value, &defaultHdopNew)) {
1279                 return true;
1280         }
1281
1282         defaultHdop = defaultHdopNew;
1283
1284         return false;
1285 }
1286
1287 /*
1288  * defaultVdop
1289  */
1290
1291 /** The default VDOP plugin parameter (in meters) */
1292 static unsigned long long defaultVdop = PUD_DEFAULT_VDOP_DEFAULT;
1293
1294 /**
1295  @return
1296  The default VDOP plugin parameter (in meters)
1297  */
1298 unsigned long long getDefaultVdop(void) {
1299         return defaultVdop;
1300 }
1301
1302 int setDefaultVdop(const char *value, void *data __attribute__ ((unused)),
1303                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1304         static const char * valueName = PUD_MOVING_DISTANCE_THRESHOLD_NAME;
1305         unsigned long long defaultVdopNew;
1306
1307         assert (value != NULL);
1308
1309         if (!readULL(valueName, value, &defaultVdopNew)) {
1310                 return true;
1311         }
1312
1313         defaultVdop = defaultVdopNew;
1314
1315         return false;
1316 }
1317
1318 /*
1319  * averageDepth
1320  */
1321
1322 /** The depth of the average list */
1323 static unsigned long long averageDepth = PUD_AVERAGE_DEPTH_DEFAULT;
1324
1325 /**
1326  @return
1327  The depth of the average list
1328  */
1329 unsigned long long getAverageDepth(void) {
1330         return averageDepth;
1331 }
1332
1333 int setAverageDepth(const char *value, void *data __attribute__ ((unused)),
1334                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1335         static const char * valueName = PUD_AVERAGE_DEPTH_NAME;
1336         unsigned long long averageDepthNew;
1337
1338         assert (value != NULL);
1339
1340         if (!readULL(valueName, value, &averageDepthNew)) {
1341                 return true;
1342         }
1343
1344         if (averageDepthNew < 1) {
1345                 pudError(false, "Configured %s must be at least 1", valueName);
1346                 return true;
1347         }
1348
1349         averageDepth = averageDepthNew;
1350
1351         return false;
1352 }
1353
1354 /*
1355  * hysteresisCountToStationary
1356  */
1357
1358 /** The hysteresis count for changing state from moving to stationary */
1359 static unsigned long long hysteresisCountToStationary = PUD_HYSTERESIS_COUNT_2STAT_DEFAULT;
1360
1361 /**
1362  @return
1363  The hysteresis count for changing state from moving to stationary
1364  */
1365 unsigned long long getHysteresisCountToStationary(void) {
1366         return hysteresisCountToStationary;
1367 }
1368
1369 int setHysteresisCountToStationary(const char *value, void *data __attribute__ ((unused)),
1370                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1371         static const char * valueName = PUD_HYSTERESIS_COUNT_2STAT_NAME;
1372         unsigned long long hysteresisCountNew;
1373
1374         assert (value != NULL);
1375
1376         if (!readULL(valueName, value, &hysteresisCountNew)) {
1377                 return true;
1378         }
1379
1380         hysteresisCountToStationary = hysteresisCountNew;
1381
1382         return false;
1383 }
1384
1385 /*
1386  * hysteresisCountToMoving
1387  */
1388
1389 /** The hysteresis count for changing state from stationary to moving */
1390 static unsigned long long hysteresisCountToMoving = PUD_HYSTERESIS_COUNT_2MOV_DEFAULT;
1391
1392 /**
1393  @return
1394  The hysteresis count for changing state from stationary to moving
1395  */
1396 unsigned long long getHysteresisCountToMoving(void) {
1397         return hysteresisCountToMoving;
1398 }
1399
1400 int setHysteresisCountToMoving(const char *value, void *data __attribute__ ((unused)),
1401                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1402         static const char * valueName = PUD_HYSTERESIS_COUNT_2MOV_NAME;
1403         unsigned long long hysteresisCountNew;
1404
1405         assert (value != NULL);
1406
1407         if (!readULL(valueName, value, &hysteresisCountNew)) {
1408                 return true;
1409         }
1410
1411         hysteresisCountToMoving = hysteresisCountNew;
1412
1413         return false;
1414 }
1415
1416 /*
1417  * gatewayHysteresisCountToStationary
1418  */
1419
1420 /** The hysteresis count for changing state from moving to stationary */
1421 static unsigned long long gatewayHysteresisCountToStationary = PUD_GAT_HYSTERESIS_COUNT_2STAT_DEFAULT;
1422
1423 /**
1424  @return
1425  The hysteresis count for changing state from moving to stationary
1426  */
1427 unsigned long long getGatewayHysteresisCountToStationary(void) {
1428         return gatewayHysteresisCountToStationary;
1429 }
1430
1431 int setGatewayHysteresisCountToStationary(const char *value, void *data __attribute__ ((unused)),
1432                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1433         static const char * valueName = PUD_GAT_HYSTERESIS_COUNT_2STAT_NAME;
1434         unsigned long long hysteresisCountNew;
1435
1436         assert (value != NULL);
1437
1438         if (!readULL(valueName, value, &hysteresisCountNew)) {
1439                 return true;
1440         }
1441
1442         gatewayHysteresisCountToStationary = hysteresisCountNew;
1443
1444         return false;
1445 }
1446
1447 /*
1448  * gatewayHysteresisCountToMoving
1449  */
1450
1451 /** The hysteresis count for changing state from stationary to moving */
1452 static unsigned long long gatewayHysteresisCountToMoving = PUD_GAT_HYSTERESIS_COUNT_2MOV_DEFAULT;
1453
1454 /**
1455  @return
1456  The hysteresis count for changing state from stationary to moving
1457  */
1458 unsigned long long getGatewayHysteresisCountToMoving(void) {
1459         return gatewayHysteresisCountToMoving;
1460 }
1461
1462 int setGatewayHysteresisCountToMoving(const char *value, void *data __attribute__ ((unused)),
1463                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1464         static const char * valueName = PUD_GAT_HYSTERESIS_COUNT_2MOV_NAME;
1465         unsigned long long hysteresisCountNew;
1466
1467         assert (value != NULL);
1468
1469         if (!readULL(valueName, value, &hysteresisCountNew)) {
1470                 return true;
1471         }
1472
1473         gatewayHysteresisCountToMoving = hysteresisCountNew;
1474
1475         return false;
1476 }
1477
1478 /*
1479  * useDeDup
1480  */
1481
1482 /* when true then duplicate message detection is performed */
1483 static bool useDeDup = PUD_USE_DEDUP_DEFAULT;
1484
1485 /**
1486  @return
1487  The duplicate message detection setting
1488  */
1489 bool getUseDeDup(void) {
1490         return useDeDup;
1491 }
1492
1493 int setUseDeDup(const char *value, void *data __attribute__ ((unused)),
1494                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1495         return !readBool(PUD_USE_DEDUP_NAME, value, &useDeDup);
1496 }
1497
1498 /*
1499  * deDupDepth
1500  */
1501
1502 /** The hysteresis count for changing state from stationary to moving */
1503 static unsigned long long deDupDepth = PUD_DEDUP_DEPTH_DEFAULT;
1504
1505 /**
1506  @return
1507  The hysteresis count for changing state from stationary to moving
1508  */
1509 unsigned long long getDeDupDepth(void) {
1510         return deDupDepth;
1511 }
1512
1513 int setDeDupDepth(const char *value, void *data __attribute__ ((unused)),
1514                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1515         static const char * valueName = PUD_DEDUP_DEPTH_NAME;
1516         unsigned long long deDupDepthNew;
1517
1518         assert (value != NULL);
1519
1520         if (!readULL(valueName, value, &deDupDepthNew)) {
1521                 return true;
1522         }
1523
1524         deDupDepth = deDupDepthNew;
1525
1526         return false;
1527 }
1528
1529 /*
1530  * useLoopback
1531  */
1532
1533 /* when true then loopback is performed */
1534 static bool useLoopback = PUD_USE_LOOPBACK_DEFAULT;
1535
1536 /**
1537  @return
1538  The loopback usage setting
1539  */
1540 bool getUseLoopback(void) {
1541         return useLoopback;
1542 }
1543
1544 int setUseLoopback(const char *value, void *data __attribute__ ((unused)),
1545                 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1546         return !readBool(PUD_USE_LOOPBACK_NAME, value, &useLoopback);
1547 }
1548
1549 /*
1550  * Check Functions
1551  */
1552
1553 /**
1554  Check the configuration for consistency and validity.
1555
1556  @return
1557  - true when the configuration is consistent and valid
1558  - false otherwise
1559  */
1560 unsigned int checkConfig(void) {
1561         int retval = true;
1562
1563         if (!olsr_cnf->smart_gw_active) {
1564                 pudError(false, "Smart Gateway must be active");
1565                 retval = false;
1566         }
1567
1568         if (rxNonOlsrInterfaceCount == 0) {
1569                 pudError(false, "No receive non-OLSR interfaces configured");
1570                 retval = false;
1571         }
1572
1573         if (txNonOlsrInterfaceCount == 0) {
1574                 pudError(false, "No transmit non-OLSR interfaces configured");
1575                 retval = false;
1576         }
1577
1578         if (!nodeIdSet) {
1579                 if (nodeIdType == PUD_NODEIDTYPE_DNS) {
1580                         char name[PUD_TX_NODEID_BUFFERSIZE + 1];
1581
1582                         errno = 0;
1583                         if (gethostname(&name[0], sizeof(name)) < 0) {
1584                                 pudError(true, "Could not get the host name");
1585                                 retval = false;
1586                         } else {
1587                                 setNodeId(&name[0], NULL,
1588                                                 (set_plugin_parameter_addon) {.pc = NULL});
1589                         }
1590                 } else if ((nodeIdType != PUD_NODEIDTYPE_MAC) && (nodeIdType
1591                                 != PUD_NODEIDTYPE_IPV4) && (nodeIdType != PUD_NODEIDTYPE_IPV6)) {
1592                         pudError(false, "No node ID set while one is required for"
1593                                 " node type %u", nodeIdType);
1594                         retval = false;
1595                 }
1596         }
1597
1598         if (!setupNodeIdBinaryAndValidate(nodeIdType)) {
1599                 retval = false;
1600         }
1601
1602         if (updateIntervalMoving > updateIntervalStationary) {
1603                 pudError(false,"The update interval for moving situations must not be"
1604                 " larger than that for stationary situations");
1605                 retval = false;
1606         }
1607
1608         if (uplinkUpdateIntervalMoving > uplinkUpdateIntervalStationary) {
1609                 pudError(false,"The uplink update interval for moving situations must not be"
1610                 " larger than that for stationary situations");
1611                 retval = false;
1612         }
1613
1614         if (getUplinkPort() == getDownlinkPort()) {
1615                 pudError(false, "The uplink port and the downlink port must not be the same");
1616                 retval = false;
1617         }
1618
1619         return retval;
1620 }
1621
1622 /**
1623  Check the configuration for consistency and validity after everything has been
1624  setup.
1625
1626  @return
1627  - true when the configuration is consistent and valid
1628  - false otherwise
1629  */
1630 unsigned int checkRunSetup(void) {
1631         int retval = true;
1632         unsigned int i;
1633
1634         /* any receive interface name that is configured but is not the name of an
1635          * actual receive interface is not a valid interface name */
1636         for (i = 0; i < rxNonOlsrInterfaceCount; i++) {
1637                 unsigned char * nonOlsrInterfaceName = &rxNonOlsrInterfaceNames[i][0];
1638
1639                 TRxTxNetworkInterface * interfaceObject = getRxNetworkInterfaces();
1640                 bool found = false;
1641                 while (interfaceObject != NULL) {
1642                         if (strncmp((char *) nonOlsrInterfaceName,
1643                                         (char *) &interfaceObject->name[0], IFNAMSIZ + 1) == 0) {
1644                                 found = true;
1645                                 break;
1646                         }
1647                         interfaceObject = interfaceObject->next;
1648                 }
1649                 if (!found) {
1650                         pudError(false, "Configured receive non-OLSR interface %s is not"
1651                                 " a known interface name", nonOlsrInterfaceName);
1652                         retval = false;
1653                 }
1654         }
1655
1656         /* any transmit interface name that is configured but is not the name of an
1657          * actual transmit interface is not a valid interface name */
1658         for (i = 0; i < txNonOlsrInterfaceCount; i++) {
1659                 unsigned char * nonOlsrInterfaceName = &txNonOlsrInterfaceNames[i][0];
1660
1661                 TRxTxNetworkInterface * interfaceObject = getTxNetworkInterfaces();
1662                 bool found = false;
1663                 while (interfaceObject != NULL) {
1664                         if (strncmp((char *) nonOlsrInterfaceName,
1665                                         (char *) &interfaceObject->name[0], IFNAMSIZ + 1) == 0) {
1666                                 found = true;
1667                                 break;
1668                         }
1669                         interfaceObject = interfaceObject->next;
1670                 }
1671                 if (!found) {
1672                         pudError(false, "Configured transmit non-OLSR interface %s is not"
1673                                 " a known interface name", nonOlsrInterfaceName);
1674                         retval = false;
1675                 }
1676         }
1677
1678         return retval;
1679 }