diff options
| -rw-r--r-- | lib/tests/test_utils.c | 81 | ||||
| -rw-r--r-- | lib/utils_base.c | 57 | ||||
| -rw-r--r-- | lib/utils_base.h | 8 | ||||
| -rw-r--r-- | plugins/check_ntp_peer.c | 60 |
4 files changed, 148 insertions, 58 deletions
diff --git a/lib/tests/test_utils.c b/lib/tests/test_utils.c index 86a17dc3..97343afa 100644 --- a/lib/tests/test_utils.c +++ b/lib/tests/test_utils.c | |||
| @@ -29,7 +29,7 @@ main (int argc, char **argv) | |||
| 29 | thresholds *thresholds = NULL; | 29 | thresholds *thresholds = NULL; |
| 30 | int rc; | 30 | int rc; |
| 31 | 31 | ||
| 32 | plan_tests(81); | 32 | plan_tests(81+23); |
| 33 | 33 | ||
| 34 | range = parse_range_string("6"); | 34 | range = parse_range_string("6"); |
| 35 | ok( range != NULL, "'6' is valid range"); | 35 | ok( range != NULL, "'6' is valid range"); |
| @@ -172,5 +172,84 @@ main (int argc, char **argv) | |||
| 172 | test = np_escaped_string("everything"); | 172 | test = np_escaped_string("everything"); |
| 173 | ok( strcmp(test, "everything") == 0, "everything okay"); | 173 | ok( strcmp(test, "everything") == 0, "everything okay"); |
| 174 | 174 | ||
| 175 | /* np_extract_value tests (23) */ | ||
| 176 | test=np_extract_value("foo=bar, bar=foo, foobar=barfoo\n", "foo"); | ||
| 177 | ok(test && !strcmp(test, "bar"), "1st test as expected"); | ||
| 178 | free(test); | ||
| 179 | |||
| 180 | test=np_extract_value("foo=bar,bar=foo,foobar=barfoo\n", "bar"); | ||
| 181 | ok(test && !strcmp(test, "foo"), "2nd test as expected"); | ||
| 182 | free(test); | ||
| 183 | |||
| 184 | test=np_extract_value("foo=bar, bar=foo, foobar=barfoo\n", "foobar"); | ||
| 185 | ok(test && !strcmp(test, "barfoo"), "3rd test as expected"); | ||
| 186 | free(test); | ||
| 187 | |||
| 188 | test=np_extract_value("foo=bar\n", "foo"); | ||
| 189 | ok(test && !strcmp(test, "bar"), "Single test as expected"); | ||
| 190 | free(test); | ||
| 191 | |||
| 192 | test=np_extract_value("foo=bar, bar=foo, foobar=barfooi\n", "abcd"); | ||
| 193 | ok(!test, "Key not found 1"); | ||
| 194 | |||
| 195 | test=np_extract_value("foo=bar\n", "abcd"); | ||
| 196 | ok(!test, "Key not found 2"); | ||
| 197 | |||
| 198 | test=np_extract_value("foo=bar=foobar", "foo"); | ||
| 199 | ok(test && !strcmp(test, "bar=foobar"), "Strange string 1"); | ||
| 200 | free(test); | ||
| 201 | |||
| 202 | test=np_extract_value("foo", "foo"); | ||
| 203 | ok(!test, "Malformed string 1"); | ||
| 204 | |||
| 205 | test=np_extract_value("foo,", "foo"); | ||
| 206 | ok(!test, "Malformed string 2"); | ||
| 207 | |||
| 208 | test=np_extract_value("foo=", "foo"); | ||
| 209 | ok(!test, "Malformed string 3"); | ||
| 210 | |||
| 211 | test=np_extract_value("foo=,bar=foo", "foo"); | ||
| 212 | ok(!test, "Malformed string 4"); | ||
| 213 | |||
| 214 | test=np_extract_value(",foo", "foo"); | ||
| 215 | ok(!test, "Malformed string 5"); | ||
| 216 | |||
| 217 | test=np_extract_value("=foo", "foo"); | ||
| 218 | ok(!test, "Malformed string 6"); | ||
| 219 | |||
| 220 | test=np_extract_value("=foo,", "foo"); | ||
| 221 | ok(!test, "Malformed string 7"); | ||
| 222 | |||
| 223 | test=np_extract_value(",,,", "foo"); | ||
| 224 | ok(!test, "Malformed string 8"); | ||
| 225 | |||
| 226 | test=np_extract_value("===", "foo"); | ||
| 227 | ok(!test, "Malformed string 9"); | ||
| 228 | |||
| 229 | test=np_extract_value(",=,=,", "foo"); | ||
| 230 | ok(!test, "Malformed string 10"); | ||
| 231 | |||
| 232 | test=np_extract_value("=,=,=", "foo"); | ||
| 233 | ok(!test, "Malformed string 11"); | ||
| 234 | |||
| 235 | test=np_extract_value(" foo=bar ,\n bar=foo\n , foobar=barfoo \n ", "foo"); | ||
| 236 | ok(test && !strcmp(test, "bar"), "Random spaces and newlines 1"); | ||
| 237 | free(test); | ||
| 238 | |||
| 239 | test=np_extract_value(" foo=bar ,\n bar=foo\n , foobar=barfoo \n ", "bar"); | ||
| 240 | ok(test && !strcmp(test, "foo"), "Random spaces and newlines 2"); | ||
| 241 | free(test); | ||
| 242 | |||
| 243 | test=np_extract_value(" foo=bar ,\n bar=foo\n , foobar=barfoo \n ", "foobar"); | ||
| 244 | ok(test && !strcmp(test, "barfoo"), "Random spaces and newlines 3"); | ||
| 245 | free(test); | ||
| 246 | |||
| 247 | test=np_extract_value(" foo=bar ,\n bar\n \n= \n foo\n , foobar=barfoo \n ", "bar"); | ||
| 248 | ok(test && !strcmp(test, "foo"), "Random spaces and newlines 4"); | ||
| 249 | free(test); | ||
| 250 | |||
| 251 | test=np_extract_value("", "foo"); | ||
| 252 | ok(!test, "Empty string return NULL"); | ||
| 253 | |||
| 175 | return exit_status(); | 254 | return exit_status(); |
| 176 | } | 255 | } |
diff --git a/lib/utils_base.c b/lib/utils_base.c index d6437fc8..a34cc5cc 100644 --- a/lib/utils_base.c +++ b/lib/utils_base.c | |||
| @@ -251,3 +251,60 @@ int np_warn_if_not_root(void) { | |||
| 251 | } | 251 | } |
| 252 | return status; | 252 | return status; |
| 253 | } | 253 | } |
| 254 | |||
| 255 | /* | ||
| 256 | * Extract the value from key/value pairs, or return NULL. The value returned | ||
| 257 | * can be free()ed. | ||
| 258 | * This function can be used to parse NTP control packet data and performance | ||
| 259 | * data strings. | ||
| 260 | */ | ||
| 261 | char *np_extract_value(const char *varlist, const char *name) { | ||
| 262 | char *tmp=NULL, *value=NULL; | ||
| 263 | int i; | ||
| 264 | |||
| 265 | while (1) { | ||
| 266 | /* Strip any leading space */ | ||
| 267 | for (varlist; isspace(varlist[0]); varlist++); | ||
| 268 | |||
| 269 | if (strncmp(name, varlist, strlen(name)) == 0) { | ||
| 270 | varlist += strlen(name); | ||
| 271 | /* strip trailing spaces */ | ||
| 272 | for (varlist; isspace(varlist[0]); varlist++); | ||
| 273 | |||
| 274 | if (varlist[0] == '=') { | ||
| 275 | /* We matched the key, go past the = sign */ | ||
| 276 | varlist++; | ||
| 277 | /* strip leading spaces */ | ||
| 278 | for (varlist; isspace(varlist[0]); varlist++); | ||
| 279 | |||
| 280 | if (tmp = index(varlist, ',')) { | ||
| 281 | /* Value is delimited by a comma */ | ||
| 282 | if (tmp-varlist == 0) continue; | ||
| 283 | value = (char *)malloc(tmp-varlist+1); | ||
| 284 | strncpy(value, varlist, tmp-varlist); | ||
| 285 | value[tmp-varlist] = '\0'; | ||
| 286 | } else { | ||
| 287 | /* Value is delimited by a \0 */ | ||
| 288 | if (strlen(varlist) == 0) continue; | ||
| 289 | value = (char *)malloc(strlen(varlist) + 1); | ||
| 290 | strncpy(value, varlist, strlen(varlist)); | ||
| 291 | value[strlen(varlist)] = '\0'; | ||
| 292 | } | ||
| 293 | break; | ||
| 294 | } | ||
| 295 | } | ||
| 296 | if (tmp = index(varlist, ',')) { | ||
| 297 | /* More keys, keep going... */ | ||
| 298 | varlist = tmp + 1; | ||
| 299 | } else { | ||
| 300 | /* We're done */ | ||
| 301 | break; | ||
| 302 | } | ||
| 303 | } | ||
| 304 | |||
| 305 | /* Clean-up trailing spaces/newlines */ | ||
| 306 | if (value) for (i=strlen(value)-1; isspace(value[i]); i--) value[i] = '\0'; | ||
| 307 | |||
| 308 | return value; | ||
| 309 | } | ||
| 310 | |||
diff --git a/lib/utils_base.h b/lib/utils_base.h index bda76595..c34f0445 100644 --- a/lib/utils_base.h +++ b/lib/utils_base.h | |||
| @@ -50,4 +50,12 @@ int np_check_if_root(void); | |||
| 50 | * code from the above function, in case it's helpful for testing */ | 50 | * code from the above function, in case it's helpful for testing */ |
| 51 | int np_warn_if_not_root(void); | 51 | int np_warn_if_not_root(void); |
| 52 | 52 | ||
| 53 | /* | ||
| 54 | * Extract the value from key/value pairs, or return NULL. The value returned | ||
| 55 | * can be free()ed. | ||
| 56 | * This function can be used to parse NTP control packet data and performance | ||
| 57 | * data strings. | ||
| 58 | */ | ||
| 59 | char *np_extract_value(const char*, const char*); | ||
| 60 | |||
| 53 | #endif /* _UTILS_BASE_ */ | 61 | #endif /* _UTILS_BASE_ */ |
diff --git a/plugins/check_ntp_peer.c b/plugins/check_ntp_peer.c index acca17b5..b40dbfcb 100644 --- a/plugins/check_ntp_peer.c +++ b/plugins/check_ntp_peer.c | |||
| @@ -172,60 +172,6 @@ void print_ntp_control_message(const ntp_control_message *p){ | |||
| 172 | } | 172 | } |
| 173 | } | 173 | } |
| 174 | 174 | ||
| 175 | /* | ||
| 176 | * Extract the value from NTP key/value pairs, or return NULL. | ||
| 177 | * The value returned can be free()ed. | ||
| 178 | */ | ||
| 179 | char *extract_value(const char *varlist, const char *name){ | ||
| 180 | char *tmp=NULL, *value=NULL; | ||
| 181 | int i; | ||
| 182 | |||
| 183 | while (1) { | ||
| 184 | /* Strip any leading space */ | ||
| 185 | for (varlist; isspace(varlist[0]); varlist++); | ||
| 186 | |||
| 187 | if (strncmp(name, varlist, strlen(name)) == 0) { | ||
| 188 | varlist += strlen(name); | ||
| 189 | /* strip trailing spaces */ | ||
| 190 | for (varlist; isspace(varlist[0]); varlist++); | ||
| 191 | |||
| 192 | if (varlist[0] == '=') { | ||
| 193 | /* We matched the key, go past the = sign */ | ||
| 194 | varlist++; | ||
| 195 | /* strip leading spaces */ | ||
| 196 | for (varlist; isspace(varlist[0]); varlist++); | ||
| 197 | |||
| 198 | if (tmp = index(varlist, ',')) { | ||
| 199 | /* Value is delimited by a comma */ | ||
| 200 | if (tmp-varlist == 0) continue; | ||
| 201 | value = (char *)malloc(tmp-varlist+1); | ||
| 202 | strncpy(value, varlist, tmp-varlist); | ||
| 203 | value[tmp-varlist] = '\0'; | ||
| 204 | } else { | ||
| 205 | /* Value is delimited by a \0 */ | ||
| 206 | if (strlen(varlist) == 0) continue; | ||
| 207 | value = (char *)malloc(strlen(varlist) + 1); | ||
| 208 | strncpy(value, varlist, strlen(varlist)); | ||
| 209 | value[strlen(varlist)] = '\0'; | ||
| 210 | } | ||
| 211 | break; | ||
| 212 | } | ||
| 213 | } | ||
| 214 | if (tmp = index(varlist, ',')) { | ||
| 215 | /* More keys, keep going... */ | ||
| 216 | varlist = tmp + 1; | ||
| 217 | } else { | ||
| 218 | /* We're done */ | ||
| 219 | break; | ||
| 220 | } | ||
| 221 | } | ||
| 222 | |||
| 223 | /* Clean-up trailing spaces/newlines */ | ||
| 224 | if (value) for (i=strlen(value)-1; isspace(value[i]); i--) value[i] = '\0'; | ||
| 225 | |||
| 226 | return value; | ||
| 227 | } | ||
| 228 | |||
| 229 | void | 175 | void |
| 230 | setup_control_request(ntp_control_message *p, uint8_t opcode, uint16_t seq){ | 176 | setup_control_request(ntp_control_message *p, uint8_t opcode, uint16_t seq){ |
| 231 | memset(p, 0, sizeof(ntp_control_message)); | 177 | memset(p, 0, sizeof(ntp_control_message)); |
| @@ -387,7 +333,7 @@ int ntp_request(const char *host, double *offset, int *offset_result, double *ji | |||
| 387 | if(verbose) | 333 | if(verbose) |
| 388 | printf("parsing offset from peer %.2x: ", ntohs(peers[i].assoc)); | 334 | printf("parsing offset from peer %.2x: ", ntohs(peers[i].assoc)); |
| 389 | 335 | ||
| 390 | value = extract_value(data, "offset"); | 336 | value = np_extract_value(data, "offset"); |
| 391 | nptr=NULL; | 337 | nptr=NULL; |
| 392 | /* Convert the value if we have one */ | 338 | /* Convert the value if we have one */ |
| 393 | if(value != NULL) | 339 | if(value != NULL) |
| @@ -411,7 +357,7 @@ int ntp_request(const char *host, double *offset, int *offset_result, double *ji | |||
| 411 | if(verbose) { | 357 | if(verbose) { |
| 412 | printf("parsing %s from peer %.2x: ", strstr(getvar, "dispersion") != NULL ? "dispersion" : "jitter", ntohs(peers[i].assoc)); | 358 | printf("parsing %s from peer %.2x: ", strstr(getvar, "dispersion") != NULL ? "dispersion" : "jitter", ntohs(peers[i].assoc)); |
| 413 | } | 359 | } |
| 414 | value = extract_value(data, strstr(getvar, "dispersion") != NULL ? "dispersion" : "jitter"); | 360 | value = np_extract_value(data, strstr(getvar, "dispersion") != NULL ? "dispersion" : "jitter"); |
| 415 | nptr=NULL; | 361 | nptr=NULL; |
| 416 | /* Convert the value if we have one */ | 362 | /* Convert the value if we have one */ |
| 417 | if(value != NULL) | 363 | if(value != NULL) |
| @@ -430,7 +376,7 @@ int ntp_request(const char *host, double *offset, int *offset_result, double *ji | |||
| 430 | if(verbose) { | 376 | if(verbose) { |
| 431 | printf("parsing stratum from peer %.2x: ", ntohs(peers[i].assoc)); | 377 | printf("parsing stratum from peer %.2x: ", ntohs(peers[i].assoc)); |
| 432 | } | 378 | } |
| 433 | value = extract_value(data, "stratum"); | 379 | value = np_extract_value(data, "stratum"); |
| 434 | nptr=NULL; | 380 | nptr=NULL; |
| 435 | /* Convert the value if we have one */ | 381 | /* Convert the value if we have one */ |
| 436 | if(value != NULL) | 382 | if(value != NULL) |
