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