diff options
| -rw-r--r-- | plugins-root/check_icmp.c | 71 |
1 files changed, 45 insertions, 26 deletions
diff --git a/plugins-root/check_icmp.c b/plugins-root/check_icmp.c index 4c17d239..cab69fda 100644 --- a/plugins-root/check_icmp.c +++ b/plugins-root/check_icmp.c | |||
| @@ -419,7 +419,7 @@ main(int argc, char **argv) | |||
| 419 | * that before pointer magic (esp. on network data) */ | 419 | * that before pointer magic (esp. on network data) */ |
| 420 | icmp_sockerrno = udp_sockerrno = tcp_sockerrno = sockets = 0; | 420 | icmp_sockerrno = udp_sockerrno = tcp_sockerrno = sockets = 0; |
| 421 | 421 | ||
| 422 | address_family = AF_INET; | 422 | address_family = -1; |
| 423 | int icmp_proto = IPPROTO_ICMP; | 423 | int icmp_proto = IPPROTO_ICMP; |
| 424 | 424 | ||
| 425 | /* get calling name the old-fashioned way for portability instead | 425 | /* get calling name the old-fashioned way for portability instead |
| @@ -526,12 +526,10 @@ main(int argc, char **argv) | |||
| 526 | break; | 526 | break; |
| 527 | case '4': | 527 | case '4': |
| 528 | address_family = AF_INET; | 528 | address_family = AF_INET; |
| 529 | icmp_proto = IPPROTO_ICMP; | ||
| 530 | break; | 529 | break; |
| 531 | case '6': | 530 | case '6': |
| 532 | #ifdef USE_IPV6 | 531 | #ifdef USE_IPV6 |
| 533 | address_family = AF_INET6; | 532 | address_family = AF_INET6; |
| 534 | icmp_proto = IPPROTO_ICMPV6; | ||
| 535 | #else | 533 | #else |
| 536 | usage (_("IPv6 support not available\n")); | 534 | usage (_("IPv6 support not available\n")); |
| 537 | #endif | 535 | #endif |
| @@ -540,29 +538,6 @@ main(int argc, char **argv) | |||
| 540 | } | 538 | } |
| 541 | } | 539 | } |
| 542 | 540 | ||
| 543 | if((icmp_sock = socket(address_family, SOCK_RAW, icmp_proto)) != -1) | ||
| 544 | sockets |= HAVE_ICMP; | ||
| 545 | else icmp_sockerrno = errno; | ||
| 546 | |||
| 547 | /* if((udp_sock = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP)) != -1) */ | ||
| 548 | /* sockets |= HAVE_UDP; */ | ||
| 549 | /* else udp_sockerrno = errno; */ | ||
| 550 | |||
| 551 | /* if((tcp_sock = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP)) != -1) */ | ||
| 552 | /* sockets |= HAVE_TCP; */ | ||
| 553 | /* else tcp_sockerrno = errno; */ | ||
| 554 | |||
| 555 | /* now drop privileges (no effect if not setsuid or geteuid() == 0) */ | ||
| 556 | if (setuid(getuid()) == -1) { | ||
| 557 | printf("ERROR: Failed to drop privileges\n"); | ||
| 558 | return 1; | ||
| 559 | } | ||
| 560 | |||
| 561 | #ifdef SO_TIMESTAMP | ||
| 562 | if(setsockopt(icmp_sock, SOL_SOCKET, SO_TIMESTAMP, &on, sizeof(on))) | ||
| 563 | if(debug) printf("Warning: no SO_TIMESTAMP support\n"); | ||
| 564 | #endif // SO_TIMESTAMP | ||
| 565 | |||
| 566 | /* POSIXLY_CORRECT might break things, so unset it (the portable way) */ | 541 | /* POSIXLY_CORRECT might break things, so unset it (the portable way) */ |
| 567 | environ = NULL; | 542 | environ = NULL; |
| 568 | 543 | ||
| @@ -593,6 +568,37 @@ main(int argc, char **argv) | |||
| 593 | exit(3); | 568 | exit(3); |
| 594 | } | 569 | } |
| 595 | 570 | ||
| 571 | // add_target might change address_family | ||
| 572 | switch ( address_family ){ | ||
| 573 | case AF_INET: icmp_proto = IPPROTO_ICMP; | ||
| 574 | break; | ||
| 575 | case AF_INET6: icmp_proto = IPPROTO_ICMPV6; | ||
| 576 | break; | ||
| 577 | default: crash("Address family not supported"); | ||
| 578 | } | ||
| 579 | if((icmp_sock = socket(address_family, SOCK_RAW, icmp_proto)) != -1) | ||
| 580 | sockets |= HAVE_ICMP; | ||
| 581 | else icmp_sockerrno = errno; | ||
| 582 | |||
| 583 | /* if((udp_sock = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP)) != -1) */ | ||
| 584 | /* sockets |= HAVE_UDP; */ | ||
| 585 | /* else udp_sockerrno = errno; */ | ||
| 586 | |||
| 587 | /* if((tcp_sock = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP)) != -1) */ | ||
| 588 | /* sockets |= HAVE_TCP; */ | ||
| 589 | /* else tcp_sockerrno = errno; */ | ||
| 590 | |||
| 591 | #ifdef SO_TIMESTAMP | ||
| 592 | if(setsockopt(icmp_sock, SOL_SOCKET, SO_TIMESTAMP, &on, sizeof(on))) | ||
| 593 | if(debug) printf("Warning: no SO_TIMESTAMP support\n"); | ||
| 594 | #endif // SO_TIMESTAMP | ||
| 595 | |||
| 596 | /* now drop privileges (no effect if not setsuid or geteuid() == 0) */ | ||
| 597 | if (setuid(getuid()) == -1) { | ||
| 598 | printf("ERROR: Failed to drop privileges\n"); | ||
| 599 | return 1; | ||
| 600 | } | ||
| 601 | |||
| 596 | if(!sockets) { | 602 | if(!sockets) { |
| 597 | if(icmp_sock == -1) { | 603 | if(icmp_sock == -1) { |
| 598 | errno = icmp_sockerrno; | 604 | errno = icmp_sockerrno; |
| @@ -1319,6 +1325,19 @@ add_target(char *arg) | |||
| 1319 | struct sockaddr_in6 *sin6; | 1325 | struct sockaddr_in6 *sin6; |
| 1320 | 1326 | ||
| 1321 | switch (address_family) { | 1327 | switch (address_family) { |
| 1328 | case -1: | ||
| 1329 | // -4 and -6 are not specified on cmdline | ||
| 1330 | address_family = AF_INET; | ||
| 1331 | sin = (struct sockaddr_in *)&ip; | ||
| 1332 | result = inet_pton(address_family, arg, &sin->sin_addr); | ||
| 1333 | #ifdef USE_IPV6 | ||
| 1334 | if( result != 1 ){ | ||
| 1335 | address_family = AF_INET6; | ||
| 1336 | sin6 = (struct sockaddr_in6 *)&ip; | ||
| 1337 | result = inet_pton(address_family, arg, &sin6->sin6_addr); | ||
| 1338 | } | ||
| 1339 | #endif | ||
| 1340 | break; | ||
| 1322 | case AF_INET: | 1341 | case AF_INET: |
| 1323 | sin = (struct sockaddr_in *)&ip; | 1342 | sin = (struct sockaddr_in *)&ip; |
| 1324 | result = inet_pton(address_family, arg, &sin->sin_addr); | 1343 | result = inet_pton(address_family, arg, &sin->sin_addr); |
