1 #include "configuration.h"
6 #include "networkInterfaces.h"
9 #include "olsr_types.h"
18 #include <netinet/in.h>
19 #include <arpa/inet.h>
20 #include <sys/socket.h>
22 #include <nmea/util.h>
29 Determine the address of the port in an OLSR socket address
32 The IP version (AF_INET or AF_INET6)
34 A pointer to OLSR socket address
38 static in_port_t * getOlsrSockaddrPort(int ipVersion, union olsr_sockaddr * addr) {
39 if (ipVersion == AF_INET) {
40 return &addr->in4.sin_port;
42 return &addr->in6.sin6_port;
47 Get pointer to the IP address and port in an OLSR socket address
49 The IP version (AF_INET or AF_INET6)
51 A pointer to OLSR socket address
53 A pointer to the location where the pointer to the IP address will be stored
55 A pointer to the location where the pointer to the port will be stored
57 static void getOlsrSockAddrAndPort(int ipVersion, union olsr_sockaddr * addr,
58 void ** ipAddress, in_port_t ** port) {
59 if (ipVersion == AF_INET) {
60 *ipAddress = (void *) &addr->in4.sin_addr;
61 *port = (void *) &addr->in4.sin_port;
63 *ipAddress = (void *) &addr->in6.sin6_addr;
64 *port = (void *) &addr->in6.sin6_port;
69 Read an unsigned long long number from a value string
74 the string to convert to a number
76 a pointer to the location where to store the number upon successful conversion
82 static bool readULL(const char * valueName, const char * value,
83 unsigned long long * valueNumber) {
85 unsigned long long valueNew;
88 valueNew = strtoull(value, &endPtr, 10);
90 if (!((endPtr != value) && (*value != '\0') && (*endPtr == '\0'))) {
91 /* invalid conversion */
92 pudError(true, "Configured %s (%s) could not be converted to a number",
97 *valueNumber = valueNew;
103 Read a double number from a value string
106 the name of the value
108 the string to convert to a number
110 a pointer to the location where to store the number upon successful conversion
116 static bool readDouble(const char * valueName, const char * value,
117 double * valueNumber) {
118 char * endPtr = NULL;
122 valueNew = strtod(value, &endPtr);
124 if (!((endPtr != value) && (*value != '\0') && (*endPtr == '\0'))) {
125 /* invalid conversion */
126 pudError(true, "Configured %s (%s) could not be converted to a number",
131 *valueNumber = valueNew;
140 /** The nodeIdType */
141 static NodeIdType nodeIdType = PUD_NODE_ID_TYPE_DEFAULT;
147 NodeIdType getNodeIdTypeNumber(void) {
152 Set the node ID type.
155 The value of the node ID type to set (a number in string representation)
162 - true when an error is detected
165 int setNodeIdType(const char *value, void *data __attribute__ ((unused)),
166 set_plugin_parameter_addon addon __attribute__ ((unused))) {
167 static const char * valueName = PUD_NODE_ID_TYPE_NAME;
168 unsigned long long nodeIdTypeNew;
170 assert (value != NULL);
172 if (!readULL(valueName, value, &nodeIdTypeNew)) {
176 if (nodeIdTypeNew > PUD_NODE_ID_TYPE_MAX) {
177 pudError(false, "Configured %s (%llu) is out of range 0-%u", valueName,
178 nodeIdTypeNew, PUD_NODE_ID_TYPE_MAX);
182 switch (nodeIdTypeNew) {
183 case PUD_NODEIDTYPE_MAC:
184 case PUD_NODEIDTYPE_MSISDN:
185 case PUD_NODEIDTYPE_TETRA:
186 case PUD_NODEIDTYPE_DNS:
187 case PUD_NODEIDTYPE_IPV4:
188 case PUD_NODEIDTYPE_IPV6:
189 case PUD_NODEIDTYPE_192:
190 case PUD_NODEIDTYPE_193:
191 case PUD_NODEIDTYPE_194:
195 pudError(false, "Configured %s (%llu) is reserved", valueName,
200 nodeIdType = nodeIdTypeNew;
209 /** The maximum length of a nodeId */
210 #define PUD_NODEIDMAXLENGTH 255
212 /** The nodeId buffer */
213 static unsigned char nodeId[PUD_NODEIDMAXLENGTH + 1];
215 /** The length of the string in the nodeId buffer */
216 static size_t nodeIdLength = 0;
218 /** True when the nodeId is set */
219 static bool nodeIdSet = false;
221 /** The nodeId as a nuber */
222 static unsigned long long nodeIdNumber = 0;
224 /** True when the nodeIdNumber is set */
225 static bool nodeIdNumberSet = false;
231 unsigned char * getNodeId(void) {
232 return getNodeIdWithLength(NULL);
237 A pointer to the node ID number
242 bool getNodeIdAsNumber(unsigned long long * value) {
243 if (!nodeIdNumberSet) {
244 if (!readULL(PUD_NODE_ID_NAME, (char *) &nodeId[0], &nodeIdNumber)) {
247 nodeIdNumberSet = true;
249 *value = nodeIdNumber;
254 Get the nodeId and its length
257 a pointer to the variable in which to store the nodeId length (allowed to be
258 NULL, in which case the length is not stored)
263 unsigned char * getNodeIdWithLength(size_t *length) {
265 setNodeId("", NULL, (set_plugin_parameter_addon) {.pc = NULL});
268 if (length != NULL) {
269 *length = nodeIdLength;
279 The value of the node ID to set (in string representation)
286 - true when an error is detected
289 int setNodeId(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
290 static const char * valueName = PUD_NODE_ID_NAME;
293 assert (value != NULL);
295 valueLength = strlen(value);
296 if (valueLength > PUD_NODEIDMAXLENGTH) {
297 pudError(false, "Configured %s is too long, maximum length is"
298 " %u, current length is %lu", valueName, PUD_NODEIDMAXLENGTH,
299 (unsigned long) valueLength);
303 strcpy((char *) &nodeId[0], value);
304 nodeIdLength = valueLength;
314 /** The size of the cached nodeId buffer */
315 #define PUD_CACHED_NODEID_BUFFER_SIZE 16
317 /** The cached nodeId buffer: contains a pre-processed version of the nodeId
318 in order to improve performance. It is currently used for nodeIdTypes
319 PUD_NODEIDTYPE_MSISDN, PUD_NODEIDTYPE_TETRA, PUD_NODEIDTYPE_192,
320 PUD_NODEIDTYPE_193 (so basically for numbers that will not change) */
321 static unsigned char cachedNodeIdBuffer[PUD_CACHED_NODEID_BUFFER_SIZE];
323 /** The number of bytes stored in cachedNodeIdBuffer */
324 static unsigned int cachedNodeIdBufferLength = 0;
328 A pointer to the location in which to store a pointer to the nodeId cache
331 A pointer to the location in which to store the number of bytes in the buffer
333 void getNodeIdNumberForOlsrCache(unsigned char ** buffer, unsigned int * length) {
334 *buffer = &cachedNodeIdBuffer[0];
335 *length = cachedNodeIdBufferLength;
339 Check a nodeId number for validity and if valid set it up in the
340 cachedNodeIdBuffer. The valid range for the number is [min, max].
343 The lower bound for a valid number
345 The upper bound for a valid number
347 The number of bytes used by the number in the wire format
350 - true when the number is valid
353 static bool setupNodeIdNumberForOlsrCache(unsigned long long min,
354 unsigned long long max, unsigned int bytes) {
355 unsigned long long val;
357 assert (bytes <= PUD_CACHED_NODEID_BUFFER_SIZE);
359 if (!getNodeIdAsNumber(&val)) {
363 if ((val >= min) && (val <= max)) {
366 cachedNodeIdBuffer[i] = val & 0xff;
373 cachedNodeIdBufferLength = bytes;
377 pudError(false, "%s value %llu is out of range [%llu,%llu]",
378 PUD_NODE_ID_NAME, val, min, max);
387 Validate whether the configured nodeId is valid w.r.t. the configured
394 static bool setupNodeIdNumberForOlsrCacheAndValidate(NodeIdType nodeIdTypeNumber) {
395 switch (nodeIdTypeNumber) {
396 case PUD_NODEIDTYPE_IPV4: /* IPv4 address */
397 case PUD_NODEIDTYPE_IPV6: /* IPv6 address */
398 case PUD_NODEIDTYPE_MAC: /* hardware address */
399 /* explicit return: configured nodeId is not relevant */
402 case PUD_NODEIDTYPE_MSISDN: /* an MSISDN number */
403 return setupNodeIdNumberForOlsrCache(0LL, 999999999999999LL,
404 PUD_NODEIDTYPE_MSISDN_BYTES);
406 case PUD_NODEIDTYPE_TETRA: /* a Tetra number */
407 return setupNodeIdNumberForOlsrCache(0LL, 99999999999999999LL,
408 PUD_NODEIDTYPE_TETRA_BYTES);
410 case PUD_NODEIDTYPE_DNS: /* DNS name */
415 invalidChars = nmea_string_has_invalid_chars((char *) getNodeId(),
416 PUD_NODE_ID_NAME, &report[0], sizeof(report));
418 pudError(false, &report[0]);
420 return !invalidChars;
423 case PUD_NODEIDTYPE_192:
424 return setupNodeIdNumberForOlsrCache(0LL, 9999999LL,
425 PUD_NODEIDTYPE_192_BYTES);
427 case PUD_NODEIDTYPE_193:
428 return setupNodeIdNumberForOlsrCache(0LL, 999999LL,
429 PUD_NODEIDTYPE_193_BYTES);
431 case PUD_NODEIDTYPE_194:
432 return setupNodeIdNumberForOlsrCache(1LL, 8191LL,
433 PUD_NODEIDTYPE_194_BYTES);
435 default: /* unsupported */
436 /* explicit return: configured nodeId is not relevant, will
437 * fallback to IP addresses */
448 /** The maximum number of RX non-OLSR interfaces */
449 #define PUD_RX_NON_OLSR_IF_MAX 32
451 /** Array with RX non-OLSR interface names */
452 static unsigned char rxNonOlsrInterfaceNames[PUD_RX_NON_OLSR_IF_MAX][IFNAMSIZ + 1];
454 /** The number of RX non-OLSR interface names in the array */
455 static unsigned int rxNonOlsrInterfaceCount = 0;
458 Determine whether a give interface name is configured as a receive non-OLSR
462 The interface name to check
465 - true when the given interface name is configured as a receive non-OLSR
469 bool isRxNonOlsrInterface(const char *ifName) {
472 assert (ifName != NULL);
474 for (i = 0; i < rxNonOlsrInterfaceCount; i++) {
475 if (strncmp((char *) &rxNonOlsrInterfaceNames[i][0], ifName, IFNAMSIZ
485 Add a receive non-OLSR interface
488 The name of the non-OLSR interface to add
495 - true when an error is detected
498 int addRxNonOlsrInterface(const char *value, void *data __attribute__ ((unused)),
499 set_plugin_parameter_addon addon __attribute__ ((unused))) {
500 unsigned long valueLength;
502 assert (value != NULL);
504 valueLength = strlen(value);
505 if (valueLength > IFNAMSIZ) {
506 pudError(false, "Configured %s (%s) is too long,"
507 " maximum length is %u, current length is %lu",
508 PUD_RX_NON_OLSR_IF_NAME, value, IFNAMSIZ, valueLength);
512 if (!isRxNonOlsrInterface(value)) {
513 if (rxNonOlsrInterfaceCount >= PUD_RX_NON_OLSR_IF_MAX) {
514 pudError(false, "Can't configure more than %u receive interfaces",
515 PUD_RX_NON_OLSR_IF_MAX);
519 strcpy((char *) &rxNonOlsrInterfaceNames[rxNonOlsrInterfaceCount][0],
521 rxNonOlsrInterfaceCount++;
528 * rxAllowedSourceIpAddress
531 /** The maximum number of RX allowed source IP addresses */
532 #define PUD_RX_ALLOWED_SOURCE_IP_MAX 32
534 /** Array with RX allowed source IP addresses */
535 static struct sockaddr rxAllowedSourceIpAddresses[PUD_RX_ALLOWED_SOURCE_IP_MAX];
537 /** The number of RX allowed source IP addresses in the array */
538 static unsigned int rxAllowedSourceIpAddressesCount = 0;
541 Determine whether a give IP address is configured as an allowed source IP
545 The IP address to check
548 - true when the given IP address is configured as an allowed source IP
552 bool isRxAllowedSourceIpAddress(struct sockaddr * sender) {
554 unsigned int addrSize;
557 if (rxAllowedSourceIpAddressesCount == 0) {
561 if (sender == NULL) {
565 if (sender->sa_family == AF_INET) {
566 addr = (void *) (&((struct sockaddr_in *) sender)->sin_addr);
567 addrSize = sizeof(struct in_addr);
569 addr = (void *) (&((struct sockaddr_in6 *) sender)->sin6_addr);
570 addrSize = sizeof(struct in6_addr);
573 for (i = 0; i < rxAllowedSourceIpAddressesCount; i++) {
574 if ((rxAllowedSourceIpAddresses[i].sa_family == sender->sa_family)
575 && (memcmp(&rxAllowedSourceIpAddresses[i].sa_data, addr,
585 Set the RX allowed source IP addresses.
588 The RX allowed source IP address (in string representation)
595 - true when an error is detected
598 int addRxAllowedSourceIpAddress(const char *value, void *data __attribute__ ((unused)),
599 set_plugin_parameter_addon addon __attribute__ ((unused))) {
600 static const char * valueName = PUD_RX_ALLOWED_SOURCE_IP_NAME;
601 const char * valueInternal = value;
603 struct sockaddr addr;
605 assert (value != NULL);
607 memset(&addr, 0, sizeof(addr));
609 addr.sa_family = olsr_cnf->ip_version;
610 conversion = inet_pton(olsr_cnf->ip_version, valueInternal, &addr.sa_data);
611 if (conversion != 1) {
612 pudError((conversion == -1) ? true : false,
613 "Configured %s (%s) is not an IP address", valueName,
618 if ((rxAllowedSourceIpAddressesCount == 0) || !isRxAllowedSourceIpAddress(&addr)) {
619 if (rxAllowedSourceIpAddressesCount >= PUD_RX_ALLOWED_SOURCE_IP_MAX) {
620 pudError(false, "Can't configure more than %u allowed source IP"
621 " addresses", PUD_RX_ALLOWED_SOURCE_IP_MAX);
625 memcpy(&rxAllowedSourceIpAddresses[rxAllowedSourceIpAddressesCount],
626 &addr, sizeof(addr));
627 rxAllowedSourceIpAddressesCount++;
637 /** The rx multicast address */
638 static union olsr_sockaddr rxMcAddr;
640 /** True when the rx multicast address is set */
641 static bool rxMcAddrSet = false;
645 The receive multicast address (in network byte order). Sets both the address
646 and the port to their default values when the address was not yet set.
648 union olsr_sockaddr * getRxMcAddr(void) {
650 setRxMcAddr(NULL, NULL, ((set_plugin_parameter_addon) {.pc = NULL}));
656 Set the receive multicast address. Sets the address to its default value when
657 the value is NULL. Also sets the port to its default value when the address
661 The receive multicast address (in string representation)
668 - true when an error is detected
671 int setRxMcAddr(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
672 static const char * valueName = PUD_RX_MC_ADDR_NAME;
675 const char * valueInternal = value;
678 getOlsrSockAddrAndPort(olsr_cnf->ip_version, &rxMcAddr, &ipAddress, &port);
679 if (olsr_cnf->ip_version == AF_INET) {
680 rxMcAddr.in4.sin_family = olsr_cnf->ip_version;
681 if (valueInternal == NULL) {
682 valueInternal = PUD_RX_MC_ADDR_4_DEFAULT;
685 rxMcAddr.in6.sin6_family = olsr_cnf->ip_version;
686 if (valueInternal == NULL) {
687 valueInternal = PUD_RX_MC_ADDR_6_DEFAULT;
692 *port = htons(PUD_RX_MC_PORT_DEFAULT);
695 conversion = inet_pton(olsr_cnf->ip_version, valueInternal, ipAddress);
696 if (conversion != 1) {
697 pudError((conversion == -1) ? true : false,
698 "Configured %s (%s) is not an IP address", valueName,
703 if (!isMulticast(olsr_cnf->ip_version, &rxMcAddr)) {
704 pudError(false, "Configured %s (%s) is not a multicast address",
705 valueName, valueInternal);
719 The receive multicast port (in network byte order)
721 unsigned short getRxMcPort(void) {
722 union olsr_sockaddr * addr = getRxMcAddr();
723 return *getOlsrSockaddrPort(olsr_cnf->ip_version, addr);
727 Set the receive multicast port
730 The receive multicast port (a number in string representation)
737 - true when an error is detected
740 int setRxMcPort(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
741 static const char * valueName = PUD_RX_MC_PORT_NAME;
742 unsigned long long rxMcPortNew;
744 union olsr_sockaddr * addr = getRxMcAddr();
746 assert (value != NULL);
748 if (!readULL(valueName, value, &rxMcPortNew)) {
752 if ((rxMcPortNew < 1) || (rxMcPortNew > 65535)) {
753 pudError(false, "Configured %s (%llu) is outside of"
754 " valid range 1-65535", valueName, rxMcPortNew);
758 port = getOlsrSockaddrPort(olsr_cnf->ip_version, addr);
759 *port = htons((uint16_t) rxMcPortNew);
768 /** The maximum number of rx non-olsr interfaces */
769 #define PUD_TX_NON_OLSR_IF_MAX 32
771 /** Array with tx non-olsr interface names */
772 static unsigned char txNonOlsrInterfaceNames[PUD_TX_NON_OLSR_IF_MAX][IFNAMSIZ + 1];
774 /** The number of tx interface names in the array */
775 static unsigned int txNonOlsrInterfaceCount = 0;
778 Determine whether a give interface name is configured as a transmit non-OLSR
782 The interface to check
785 - true when the given interface name is configured as a transmit non-OLSR
789 bool isTxNonOlsrInterface(const char *ifName) {
792 assert (ifName != NULL);
794 for (i = 0; i < txNonOlsrInterfaceCount; i++) {
795 if (strncmp((char *) &txNonOlsrInterfaceNames[i][0], ifName, IFNAMSIZ
805 Add a transmit non-OLSR interface
808 The name of the non-OLSR interface to add
815 - true when an error is detected
818 int addTxNonOlsrInterface(const char *value, void *data __attribute__ ((unused)),
819 set_plugin_parameter_addon addon __attribute__ ((unused))) {
820 unsigned long valueLength;
822 assert (value != NULL);
824 valueLength = strlen(value);
825 if (valueLength > IFNAMSIZ) {
826 pudError(false, "Configured %s (%s) is too long,"
827 " maximum length is %u, current length is %lu",
828 PUD_TX_NON_OLSR_IF_NAME, value, IFNAMSIZ, valueLength);
832 if (!isTxNonOlsrInterface(value)) {
833 if (txNonOlsrInterfaceCount >= PUD_TX_NON_OLSR_IF_MAX) {
834 pudError(false, "Can not configure more than %u transmit"
835 " interfaces", PUD_TX_NON_OLSR_IF_MAX);
839 strcpy((char *) &txNonOlsrInterfaceNames[txNonOlsrInterfaceCount][0],
841 txNonOlsrInterfaceCount++;
851 /** The tx multicast address */
852 static union olsr_sockaddr txMcAddr;
854 /** True when the tx multicast address is set */
855 static bool txMcAddrSet = false;
859 The transmit multicast address (in network byte order). Sets both the address
860 and the port to their default values when the address was not yet set.
862 union olsr_sockaddr * getTxMcAddr(void) {
864 setTxMcAddr(NULL, NULL, ((set_plugin_parameter_addon) {.pc = NULL}));
870 Set the transmit multicast address. Sets the address to its default value when
871 the value is NULL. Also sets the port to its default value when the address
875 The transmit multicast address (in string representation)
882 - true when an error is detected
885 int setTxMcAddr(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
886 static const char * valueName = PUD_TX_MC_ADDR_NAME;
889 const char * valueInternal = value;
892 getOlsrSockAddrAndPort(olsr_cnf->ip_version, &txMcAddr, &ipAddress, &port);
893 if (olsr_cnf->ip_version == AF_INET) {
894 txMcAddr.in4.sin_family = olsr_cnf->ip_version;
895 if (valueInternal == NULL) {
896 valueInternal = PUD_TX_MC_ADDR_4_DEFAULT;
899 txMcAddr.in6.sin6_family = olsr_cnf->ip_version;
900 if (valueInternal == NULL) {
901 valueInternal = PUD_TX_MC_ADDR_6_DEFAULT;
906 *port = htons(PUD_TX_MC_PORT_DEFAULT);
909 conversion = inet_pton(olsr_cnf->ip_version, valueInternal, ipAddress);
910 if (conversion != 1) {
911 pudError((conversion == -1) ? true : false,
912 "Configured %s (%s) is not an IP address", valueName,
917 if (!isMulticast(olsr_cnf->ip_version, &txMcAddr)) {
918 pudError(false, "Configured %s (%s) is not a multicast address",
919 valueName, valueInternal);
933 The transmit multicast port (in network byte order)
935 unsigned short getTxMcPort(void) {
936 union olsr_sockaddr * addr = getTxMcAddr();
937 return *getOlsrSockaddrPort(olsr_cnf->ip_version, addr);
941 Set the transmit multicast port
944 The transmit multicast port (a number in string representation)
951 - true when an error is detected
954 int setTxMcPort(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
955 static const char * valueName = PUD_TX_MC_PORT_NAME;
956 unsigned long long txMcPortNew;
958 union olsr_sockaddr * addr = getTxMcAddr();
960 assert (value != NULL);
962 if (!readULL(valueName, value, &txMcPortNew)) {
966 if ((txMcPortNew < 1) || (txMcPortNew > 65535)) {
967 pudError(false, "Configured %s (%llu) is outside of"
968 " valid range 1-65535", valueName, txMcPortNew);
972 port = getOlsrSockaddrPort(olsr_cnf->ip_version, addr);
973 *port = htons((uint16_t) txMcPortNew);
983 static unsigned char txTtl = PUD_TX_TTL_DEFAULT;
987 The transmit multicast IP packet time-to-live
989 unsigned char getTxTtl(void) {
994 Set the transmit multicast IP packet time-to-live
997 The transmit multicast IP packet time-to-live (a number in string representation)
1004 - true when an error is detected
1007 int setTxTtl(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
1008 static const char * valueName = PUD_TX_TTL_NAME;
1009 unsigned long long txTtlNew;
1011 assert (value != NULL);
1013 if (!readULL(valueName, value, &txTtlNew)) {
1017 if ((txTtlNew < 1) || (txTtlNew > MAX_TTL)) {
1018 pudError(false, "Configured %s (%llu) is outside of"
1019 " valid range 1-%u", valueName, txTtlNew, MAX_TTL);
1029 * txNmeaMessagePrefix
1032 /** The exact length of the tx NMEA message prefix */
1033 #define PUD_TXNMEAMESSAGEPREFIXLENGTH 4
1035 /** The tx NMEA message prefix buffer */
1036 static unsigned char txNmeaMessagePrefix[PUD_TXNMEAMESSAGEPREFIXLENGTH + 1];
1038 /** True when the tx NMEA message prefix is set */
1039 static bool txNmeaMessagePrefixSet = false;
1043 The transmit multicast NMEA message prefix
1045 unsigned char * getTxNmeaMessagePrefix(void) {
1046 if (!txNmeaMessagePrefixSet) {
1047 setTxNmeaMessagePrefix(PUD_TX_NMEAMESSAGEPREFIX_DEFAULT, NULL,
1048 (set_plugin_parameter_addon) {.pc = NULL});
1050 return &txNmeaMessagePrefix[0];
1054 Set the transmit multicast NMEA message prefix
1057 The transmit multicast NMEA message prefix (in string representation)
1064 - true when an error is detected
1067 int setTxNmeaMessagePrefix(const char *value, void *data __attribute__ ((unused)),
1068 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1069 static const char * valueName = PUD_TX_NMEAMESSAGEPREFIX_NAME;
1074 assert (value != NULL);
1076 valueLength = strlen(value);
1077 if (valueLength != PUD_TXNMEAMESSAGEPREFIXLENGTH) {
1078 pudError(false, "Configured %s (%s) must be %u exactly characters",
1079 valueName, value, PUD_TXNMEAMESSAGEPREFIXLENGTH);
1083 invalidChars = nmea_string_has_invalid_chars(value, valueName, &report[0],
1086 pudError(false, &report[0]);
1090 if ((strchr(value, ' ') != NULL) || (strchr(value, '\t') != NULL)) {
1091 pudError(false, "Configured %s (%s) can not contain whitespace",
1096 strcpy((char *) &txNmeaMessagePrefix[0], value);
1097 txNmeaMessagePrefixSet = true;
1106 static unsigned char olsrTtl = PUD_OLSR_TTL_DEFAULT;
1110 The OLSR multicast IP packet time-to-live
1112 unsigned char getOlsrTtl(void) {
1117 Set the OLSR multicast IP packet time-to-live
1120 The OLSR multicast IP packet time-to-live (a number in string representation)
1127 - true when an error is detected
1130 int setOlsrTtl(const char *value, void *data __attribute__ ((unused)), set_plugin_parameter_addon addon __attribute__ ((unused))) {
1131 static const char * valueName = PUD_OLSR_TTL_NAME;
1132 unsigned long long olsrTtlNew;
1134 assert (value != NULL);
1136 if (!readULL(valueName, value, &olsrTtlNew)) {
1140 if ((olsrTtlNew < 1) || (olsrTtlNew > MAX_TTL)) {
1141 pudError(false, "Configured %s (%llu) is outside of valid range 1-%u",
1142 valueName, olsrTtlNew, MAX_TTL);
1146 olsrTtl = olsrTtlNew;
1152 * updateIntervalStationary
1155 /** The stationary interval update plugin parameter (in seconds) */
1156 static unsigned long long updateIntervalStationary = PUD_UPDATE_INTERVAL_STATIONARY_DEFAULT;
1160 The stationary interval update plugin parameter (in seconds)
1162 unsigned long long getUpdateIntervalStationary(void) {
1163 return updateIntervalStationary;
1167 Set stationary interval update plugin parameter
1170 The stationary interval update plugin parameter (in seconds)
1177 - true when an error is detected
1180 int setUpdateIntervalStationary(const char *value, void *data __attribute__ ((unused)),
1181 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1182 static const char * valueName = PUD_UPDATE_INTERVAL_STATIONARY_NAME;
1183 unsigned long long updateIntervalStationaryNew;
1185 assert (value != NULL);
1187 if (!readULL(valueName, value, &updateIntervalStationaryNew)) {
1191 if (updateIntervalStationaryNew < 1) {
1192 pudError(false, "Configured %s must be at least 1", valueName);
1196 updateIntervalStationary = updateIntervalStationaryNew;
1202 * updateIntervalMoving
1205 /** The moving interval update plugin parameter (in seconds) */
1206 static unsigned long long updateIntervalMoving = PUD_UPDATE_INTERVAL_MOVING_DEFAULT;
1210 The moving interval update plugin parameter (in seconds)
1212 unsigned long long getUpdateIntervalMoving(void) {
1213 return updateIntervalMoving;
1217 Set moving interval update plugin parameter
1220 The moving interval update plugin parameter (in seconds)
1227 - true when an error is detected
1230 int setUpdateIntervalMoving(const char *value, void *data __attribute__ ((unused)),
1231 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1232 static const char * valueName = PUD_UPDATE_INTERVAL_MOVING_NAME;
1233 unsigned long long updateIntervalMovingNew;
1235 assert (value != NULL);
1237 if (!readULL(valueName, value, &updateIntervalMovingNew)) {
1241 if (updateIntervalMovingNew < 1) {
1242 pudError(false, "Configured %s must be at least 1", valueName);
1246 updateIntervalMoving = updateIntervalMovingNew;
1252 * movingSpeedThreshold
1255 /** The moving speed threshold plugin parameter (in kph) */
1256 static unsigned long long movingSpeedThreshold = PUD_MOVING_SPEED_THRESHOLD_DEFAULT;
1260 The moving speed threshold plugin parameter (in kph)
1262 unsigned long long getMovingSpeedThreshold(void) {
1263 return movingSpeedThreshold;
1267 Set moving speed threshold plugin parameter
1270 The moving speed threshold plugin parameter (in kph)
1277 - true when an error is detected
1280 int setMovingSpeedThreshold(const char *value, void *data __attribute__ ((unused)),
1281 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1282 static const char * valueName = PUD_MOVING_SPEED_THRESHOLD_NAME;
1283 unsigned long long movingSpeedThresholdNew;
1285 assert (value != NULL);
1287 if (!readULL(valueName, value, &movingSpeedThresholdNew)) {
1291 movingSpeedThreshold = movingSpeedThresholdNew;
1297 * movingDistanceThreshold
1300 /** The moving distance threshold plugin parameter (in meters) */
1301 static unsigned long long movingDistanceThreshold = PUD_MOVING_DISTANCE_THRESHOLD_DEFAULT;
1305 The moving distance threshold plugin parameter (in meters)
1307 unsigned long long getMovingDistanceThreshold(void) {
1308 return movingDistanceThreshold;
1312 Set moving distance threshold plugin parameter
1315 The moving distance threshold plugin parameter (in meter)
1322 - true when an error is detected
1325 int setMovingDistanceThreshold(const char *value, void *data __attribute__ ((unused)),
1326 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1327 static const char * valueName = PUD_MOVING_DISTANCE_THRESHOLD_NAME;
1328 unsigned long long movingDistanceThresholdNew;
1330 assert (value != NULL);
1332 if (!readULL(valueName, value, &movingDistanceThresholdNew)) {
1336 movingDistanceThreshold = movingDistanceThresholdNew;
1345 /* The DOP multiplier plugin parameter */
1346 static double dopMultiplier = PUD_DOP_MULTIPLIER_DEFAULT;
1350 The DOP multiplier plugin parameter
1352 double getDopMultiplier(void) {
1353 return dopMultiplier;
1357 Set DOP multiplier plugin parameter
1360 The DOP multiplier plugin parameter
1367 - true when an error is detected
1370 int setDopMultiplier(const char *value, void *data __attribute__ ((unused)),
1371 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1372 static const char * valueName = PUD_DOP_MULTIPLIER_NAME;
1373 double dopMultiplierNew;
1375 assert (value != NULL);
1377 if (!readDouble(valueName, value, &dopMultiplierNew)) {
1381 dopMultiplier = dopMultiplierNew;
1390 /** The default HDOP plugin parameter (in meters) */
1391 static unsigned long long defaultHdop = PUD_DEFAULT_HDOP_DEFAULT;
1395 The default HDOP plugin parameter (in meters)
1397 unsigned long long getDefaultHdop(void) {
1402 Set default HDOP plugin parameter
1405 The default HDOP plugin parameter (in meters)
1412 - true when an error is detected
1415 int setDefaultHdop(const char *value, void *data __attribute__ ((unused)),
1416 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1417 static const char * valueName = PUD_MOVING_DISTANCE_THRESHOLD_NAME;
1418 unsigned long long defaultHdopNew;
1420 assert (value != NULL);
1422 if (!readULL(valueName, value, &defaultHdopNew)) {
1426 defaultHdop = defaultHdopNew;
1435 /** The default VDOP plugin parameter (in meters) */
1436 static unsigned long long defaultVdop = PUD_DEFAULT_VDOP_DEFAULT;
1440 The default VDOP plugin parameter (in meters)
1442 unsigned long long getDefaultVdop(void) {
1447 Set default VDOP plugin parameter
1450 The default VDOP plugin parameter (in meters)
1457 - true when an error is detected
1460 int setDefaultVdop(const char *value, void *data __attribute__ ((unused)),
1461 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1462 static const char * valueName = PUD_MOVING_DISTANCE_THRESHOLD_NAME;
1463 unsigned long long defaultVdopNew;
1465 assert (value != NULL);
1467 if (!readULL(valueName, value, &defaultVdopNew)) {
1471 defaultVdop = defaultVdopNew;
1480 /** The depth of the average list */
1481 static unsigned long long averageDepth = PUD_AVERAGE_DEPTH_DEFAULT;
1485 The depth of the average list
1487 unsigned long long getAverageDepth(void) {
1488 return averageDepth;
1492 Set average depth plugin parameter
1495 The average depth plugin parameter
1502 - true when an error is detected
1505 int setAverageDepth(const char *value, void *data __attribute__ ((unused)),
1506 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1507 static const char * valueName = PUD_AVERAGE_DEPTH_NAME;
1508 unsigned long long averageDepthNew;
1510 assert (value != NULL);
1512 if (!readULL(valueName, value, &averageDepthNew)) {
1516 if (averageDepthNew < 1) {
1517 pudError(false, "Configured %s must be at least 1", valueName);
1521 averageDepth = averageDepthNew;
1527 * hysteresisCountToStationary
1530 /** The hysteresis count for changing state from moving to stationary */
1531 static unsigned long long hysteresisCountToStationary = PUD_HYSTERESIS_COUNT_2STAT_DEFAULT;
1535 The hysteresis count for changing state from moving to stationary
1537 unsigned long long getHysteresisCountToStationary(void) {
1538 return hysteresisCountToStationary;
1542 Set hysteresis count plugin parameter
1545 The hysteresis count plugin parameter
1552 - true when an error is detected
1555 int setHysteresisCountToStationary(const char *value, void *data __attribute__ ((unused)),
1556 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1557 static const char * valueName = PUD_HYSTERESIS_COUNT_2STAT_NAME;
1558 unsigned long long hysteresisCountNew;
1560 assert (value != NULL);
1562 if (!readULL(valueName, value, &hysteresisCountNew)) {
1566 hysteresisCountToStationary = hysteresisCountNew;
1572 * hysteresisCountToMoving
1575 /** The hysteresis count for changing state from stationary to moving */
1576 static unsigned long long hysteresisCountToMoving = PUD_HYSTERESIS_COUNT_2MOV_DEFAULT;
1580 The hysteresis count for changing state from stationary to moving
1582 unsigned long long getHysteresisCountToMoving(void) {
1583 return hysteresisCountToMoving;
1587 Set hysteresis count plugin parameter
1590 The hysteresis count plugin parameter
1597 - true when an error is detected
1600 int setHysteresisCountToMoving(const char *value, void *data __attribute__ ((unused)),
1601 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1602 static const char * valueName = PUD_HYSTERESIS_COUNT_2MOV_NAME;
1603 unsigned long long hysteresisCountNew;
1605 assert (value != NULL);
1607 if (!readULL(valueName, value, &hysteresisCountNew)) {
1611 hysteresisCountToMoving = hysteresisCountNew;
1620 /* when true then duplicate message detection is performed */
1621 static bool useDeDup = PUD_USE_DEDUP_DEFAULT;
1625 The duplicate message detection setting
1627 bool getUseDeDup(void) {
1632 Set duplicate message detection setting plugin parameter
1635 The duplicate message detection setting plugin parameter
1642 - true when an error is detected
1645 int setUseDeDup(const char *value, void *data __attribute__ ((unused)),
1646 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1647 static const char * valueName = PUD_USE_DEDUP_NAME;
1648 unsigned long long useDeDupNew;
1650 assert (value != NULL);
1652 if (!readULL(valueName, value, &useDeDupNew)) {
1656 if ((useDeDupNew != 0) && (useDeDupNew != 1)) {
1657 pudError(false, "Configured %s must be 0 (false) or 1 (true)",
1662 useDeDup = (useDeDupNew == 1);
1671 /** The hysteresis count for changing state from stationary to moving */
1672 static unsigned long long deDupDepth = PUD_DEDUP_DEPTH_DEFAULT;
1676 The hysteresis count for changing state from stationary to moving
1678 unsigned long long getDeDupDepth(void) {
1683 Set de-duplication depth plugin parameter
1686 The de-duplication depth plugin parameter
1693 - true when an error is detected
1696 int setDeDupDepth(const char *value, void *data __attribute__ ((unused)),
1697 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1698 static const char * valueName = PUD_DEDUP_DEPTH_NAME;
1699 unsigned long long deDupDepthNew;
1701 assert (value != NULL);
1703 if (!readULL(valueName, value, &deDupDepthNew)) {
1707 deDupDepth = deDupDepthNew;
1716 /* when true then loopback is performed */
1717 static bool useLoopback = PUD_USE_LOOPBACK_DEFAULT;
1721 The loopback usage setting
1723 bool getUseLoopback(void) {
1728 Set loopback usage plugin parameter
1731 The loopback usage plugin parameter
1738 - true when an error is detected
1741 int setUseLoopback(const char *value, void *data __attribute__ ((unused)),
1742 set_plugin_parameter_addon addon __attribute__ ((unused))) {
1743 static const char * valueName = PUD_USE_LOOPBACK_NAME;
1744 unsigned long long useLoopbackNew;
1746 assert (value != NULL);
1748 if (!readULL(valueName, value, &useLoopbackNew)) {
1752 if ((useLoopbackNew != 0) && (useLoopbackNew != 1)) {
1753 pudError(false, "Configured %s must be 0 (false) or 1 (true)",
1758 useLoopback = (useLoopbackNew == 1);
1768 Check the configuration for consistency and validity.
1771 - true when the configuration is consistent and valid
1774 unsigned int checkConfig(void) {
1777 if (rxNonOlsrInterfaceCount == 0) {
1778 pudError(false, "No receive non-OLSR interfaces configured");
1782 if (txNonOlsrInterfaceCount == 0) {
1783 pudError(false, "No transmit non-OLSR interfaces configured");
1788 if (nodeIdType == PUD_NODEIDTYPE_DNS) {
1789 char name[PUD_NODEIDMAXLENGTH + 1];
1792 if (gethostname(&name[0], sizeof(name)) < 0) {
1793 pudError(true, "Could not get the host name");
1796 setNodeId(&name[0], NULL,
1797 (set_plugin_parameter_addon) {.pc = NULL});
1799 } else if ((nodeIdType != PUD_NODEIDTYPE_MAC) && (nodeIdType
1800 != PUD_NODEIDTYPE_IPV4) && (nodeIdType != PUD_NODEIDTYPE_IPV6)) {
1801 pudError(false, "No node ID set while one is required for"
1802 " node type %u", nodeIdType);
1807 if (!setupNodeIdNumberForOlsrCacheAndValidate(nodeIdType)) {
1811 if (updateIntervalMoving > updateIntervalStationary) {
1812 pudError(false,"The update interval for moving situations must not be"
1813 " larger than that for stationary situations");
1821 Check the configuration for consistency and validity after everything has been
1825 - true when the configuration is consistent and valid
1828 unsigned int checkRunSetup(void) {
1832 /* any receive interface name that is configured but is not the name of an
1833 * actual receive interface is not a valid interface name */
1834 for (i = 0; i < rxNonOlsrInterfaceCount; i++) {
1835 unsigned char * nonOlsrInterfaceName = &rxNonOlsrInterfaceNames[i][0];
1837 TRxTxNetworkInterface * interfaceObject = getRxNetworkInterfaces();
1839 while (interfaceObject != NULL) {
1840 if (strncmp((char *) nonOlsrInterfaceName,
1841 (char *) &interfaceObject->name[0], IFNAMSIZ + 1) == 0) {
1845 interfaceObject = interfaceObject->next;
1848 pudError(false, "Configured receive non-OLSR interface %s is not"
1849 " a known interface name", nonOlsrInterfaceName);
1854 /* any transmit interface name that is configured but is not the name of an
1855 * actual transmit interface is not a valid interface name */
1856 for (i = 0; i < txNonOlsrInterfaceCount; i++) {
1857 unsigned char * nonOlsrInterfaceName = &txNonOlsrInterfaceNames[i][0];
1859 TRxTxNetworkInterface * interfaceObject = getTxNetworkInterfaces();
1861 while (interfaceObject != NULL) {
1862 if (strncmp((char *) nonOlsrInterfaceName,
1863 (char *) &interfaceObject->name[0], IFNAMSIZ + 1) == 0) {
1867 interfaceObject = interfaceObject->next;
1870 pudError(false, "Configured transmit non-OLSR interface %s is not"
1871 " a known interface name", nonOlsrInterfaceName);