/mandos/trunk

To get this branch, use:
bzr branch http://bzr.recompile.se/loggerhead/mandos/trunk

« back to all changes in this revision

Viewing changes to plugins.d/mandos-client.c

small stuff

Show diffs side-by-side

added added

removed removed

Lines of Context:
57
57
#include <fcntl.h>              /* open() */
58
58
#include <dirent.h>             /* opendir(), struct dirent, readdir()
59
59
                                 */
60
 
#include <inttypes.h>           /* PRIu16, SCNu16 */
 
60
#include <inttypes.h>           /* PRIu16, intmax_t, SCNdMAX */
61
61
#include <assert.h>             /* assert() */
62
62
#include <errno.h>              /* perror(), errno */
63
 
#include <time.h>               /* time() */
 
63
#include <time.h>               /* time(), nanosleep() */
64
64
#include <net/if.h>             /* ioctl, ifreq, SIOCGIFFLAGS, IFF_UP,
65
65
                                   SIOCSIFFLAGS, if_indextoname(),
66
66
                                   if_nametoindex(), IF_NAMESIZE */
74
74
                                   argp_state, struct argp,
75
75
                                   argp_parse(), ARGP_KEY_ARG,
76
76
                                   ARGP_KEY_END, ARGP_ERR_UNKNOWN */
 
77
#include <sys/klog.h>           /* klogctl() */
77
78
 
78
79
/* Avahi */
79
80
/* All Avahi types, constants and functions
365
366
}
366
367
 
367
368
static const char * safer_gnutls_strerror(int value) {
368
 
  const char *ret = gnutls_strerror(value); /* Spurious warning */
 
369
  const char *ret = gnutls_strerror(value); /* Spurious warning from
 
370
                                               -Wunreachable-code */
369
371
  if(ret == NULL)
370
372
    ret = "(unknown)";
371
373
  return ret;
404
406
  /* OpenPGP credentials */
405
407
  gnutls_certificate_allocate_credentials(&mc->cred);
406
408
  if(ret != GNUTLS_E_SUCCESS){
407
 
    fprintf(stderr, "GnuTLS memory error: %s\n", /* Spurious
408
 
                                                    warning */
 
409
    fprintf(stderr, "GnuTLS memory error: %s\n", /* Spurious warning
 
410
                                                  * from
 
411
                                                  * -Wunreachable-code
 
412
                                                  */
409
413
            safer_gnutls_strerror(ret));
410
414
    gnutls_global_deinit();
411
415
    return -1;
553
557
    fprintf(stderr, "Bad address: %s\n", ip);
554
558
    return -1;
555
559
  }
556
 
  to.in6.sin6_port = htons(port); /* Spurious warning */
 
560
  to.in6.sin6_port = htons(port); /* Spurious warnings from
 
561
                                     -Wconversion and
 
562
                                     -Wunreachable-code */
557
563
  
558
564
  to.in6.sin6_scope_id = (uint32_t)if_index;
559
565
  
749
755
      avahi_address_snprint(ip, sizeof(ip), address);
750
756
      if(debug){
751
757
        fprintf(stderr, "Mandos server \"%s\" found on %s (%s, %"
752
 
                PRIu16 ") on port %d\n", name, host_name, ip,
753
 
                interface, port);
 
758
                PRIdMAX ") on port %" PRIu16 "\n", name, host_name,
 
759
                ip, (intmax_t)interface, port);
754
760
      }
755
761
      int ret = start_mandos_communication(ip, port, interface, mc);
756
762
      if(ret == 0){
816
822
    AvahiSServiceBrowser *sb = NULL;
817
823
    int error;
818
824
    int ret;
 
825
    intmax_t tmpmax;
 
826
    int numchars;
819
827
    int exitcode = EXIT_SUCCESS;
820
828
    const char *interface = "eth0";
821
829
    struct ifreq network;
833
841
                          ":!CTYPE-X.509:+CTYPE-OPENPGP" };
834
842
    bool gnutls_initalized = false;
835
843
    bool gpgme_initalized = false;
 
844
    double delay = 2.5;
836
845
    
837
846
    {
838
847
      struct argp_option options[] = {
864
873
          .arg = "STRING",
865
874
          .doc = "GnuTLS priority string for the TLS handshake",
866
875
          .group = 1 },
 
876
        { .name = "delay", .key = 131,
 
877
          .arg = "SECONDS",
 
878
          .doc = "Maximum delay to wait for interface startup",
 
879
          .group = 2 },
867
880
        { .name = NULL }
868
881
      };
869
882
      
886
899
          pubkey = arg;
887
900
          break;
888
901
        case 129:               /* --dh-bits */
889
 
          ret = sscanf(arg, "%u", &mc.dh_bits);
890
 
          if(ret != 1){
 
902
          ret = sscanf(arg, "%" SCNdMAX "%n", &tmpmax, &numchars);
 
903
          if(ret < 1 or tmpmax != (typeof(mc.dh_bits))tmpmax
 
904
             or arg[numchars] != '\0'){
891
905
            fprintf(stderr, "Bad number of DH bits\n");
892
906
            exit(EXIT_FAILURE);
893
907
          }
 
908
          mc.dh_bits = (typeof(mc.dh_bits))tmpmax;
894
909
          break;
895
910
        case 130:               /* --priority */
896
911
          mc.priority = arg;
897
912
          break;
 
913
        case 131:               /* --delay */
 
914
          ret = sscanf(arg, "%lf%n", &delay, &numchars);
 
915
          if(ret < 1 or arg[numchars] != '\0'){
 
916
            fprintf(stderr, "Bad delay\n");
 
917
            exit(EXIT_FAILURE);
 
918
          }
 
919
          break;
898
920
        case ARGP_KEY_ARG:
899
921
          argp_usage(state);
900
922
        case ARGP_KEY_END:
919
941
    
920
942
    /* If the interface is down, bring it up */
921
943
    {
 
944
      // Lower kernel loglevel to KERN_NOTICE to avoid
 
945
      // KERN_INFO messages to mess up the prompt
 
946
      ret = klogctl(8, NULL, 5);
 
947
      if(ret == -1){
 
948
        perror("klogctl");
 
949
      }
 
950
 
922
951
      sd = socket(PF_INET6, SOCK_DGRAM, IPPROTO_IP);
923
952
      if(sd < 0) {
924
953
        perror("socket");
925
954
        exitcode = EXIT_FAILURE;
 
955
        ret = klogctl(7, NULL, 0);
 
956
        if(ret == -1){
 
957
          perror("klogctl");
 
958
        }
926
959
        goto end;
927
960
      }
928
961
      strcpy(network.ifr_name, interface);
929
962
      ret = ioctl(sd, SIOCGIFFLAGS, &network);
930
963
      if(ret == -1){
931
964
        perror("ioctl SIOCGIFFLAGS");
 
965
        ret = klogctl(7, NULL, 0);
 
966
        if(ret == -1){
 
967
          perror("klogctl");
 
968
        }
932
969
        exitcode = EXIT_FAILURE;
933
970
        goto end;
934
971
      }
938
975
        if(ret == -1){
939
976
          perror("ioctl SIOCSIFFLAGS");
940
977
          exitcode = EXIT_FAILURE;
 
978
          ret = klogctl(7, NULL, 0);
 
979
          if(ret == -1){
 
980
            perror("klogctl");
 
981
          }
941
982
          goto end;
942
983
        }
943
984
      }
 
985
      // sleep checking until interface is running
 
986
      for(int i=0; i < delay * 4; i++){
 
987
        ret = ioctl(sd, SIOCGIFFLAGS, &network);
 
988
        if(ret == -1){
 
989
          perror("ioctl SIOCGIFFLAGS");
 
990
        } else if(network.ifr_flags & IFF_RUNNING){
 
991
          break;
 
992
        }
 
993
        struct timespec sleeptime = { .tv_nsec = 250000000 };
 
994
        nanosleep(&sleeptime, NULL);
 
995
      }
944
996
      ret = (int)TEMP_FAILURE_RETRY(close(sd));
945
997
      if(ret == -1){
946
998
        perror("close");
947
999
      }
 
1000
      // Restores kernel loglevel to default
 
1001
      ret = klogctl(7, NULL, 0);
 
1002
      if(ret == -1){
 
1003
        perror("klogctl");
 
1004
      }
948
1005
    }
949
1006
    
950
1007
    uid = getuid();
999
1056
        goto end;
1000
1057
      }
1001
1058
      uint16_t port;
1002
 
      ret = sscanf(address+1, "%" SCNu16, &port);
1003
 
      if(ret != 1){
 
1059
      ret = sscanf(address+1, "%" SCNdMAX "%n", &tmpmax, &numchars);
 
1060
      if(ret < 1 or tmpmax != (uint16_t)tmpmax
 
1061
         or address[numchars+1] != '\0'){
1004
1062
        fprintf(stderr, "Bad port number\n");
1005
1063
        exitcode = EXIT_FAILURE;
1006
1064
        goto end;
1007
1065
      }
 
1066
      port = (uint16_t)tmpmax;
1008
1067
      *address = '\0';
1009
1068
      address = connect_to;
1010
1069
      ret = start_mandos_communication(address, port, if_index, &mc);
1075
1134
    if(debug){
1076
1135
      fprintf(stderr, "Starting Avahi loop search\n");
1077
1136
    }
1078
 
    
 
1137
 
1079
1138
    avahi_simple_poll_loop(mc.simple_poll);
1080
1139
    
1081
1140
 end: