Ejemplo n.º 1
0
int main(int argc, char **argv)
{
  char c;
  char *flags=0;

  optind = 0;
  while ((c = getopt(argc, argv, "vi:x:Mp:")) !=EOF) {
    switch (c) {
      case 'i':
        cfile = optarg;
	insert = 1;
        break;
      case 'x':
        extract = 1;
        cfile = optarg;
        break;
      case 'M':
        makemagic = 1;
        break;
      case 'v':
        view = 1;
        break;
      case 'p':
        setflags = 1;
        flags = optarg;
        break;
      default: usage();
    }
  }

  dexefile = argv[optind];
  if (!dexefile) usage();

  if ((insert || extract) && !cfile) usage();

  if (insert) {
    putconf();
    if (setflags) changeflags(flags);
  }
  else if (view) viewconf();
  else if (setflags) changeflags(flags);
  else if (extract) getconf();
  else usage();

  return 0;
}
Ejemplo n.º 2
0
int main(int argc, char *argv[]) {
    int opt;
    int opt_list = 0;
    char *conf_file = CONF_FILE;

    // parse arguments
    while ((opt = getopt(argc, argv, "c:l")) != -1) {
        switch (opt) {
            case 'c':
                conf_file = optarg;
                break;
            case 'l':
                opt_list = 1;
                break;
        }
    }
    if (optind >= argc) {
        fprintf(stderr, "ERROR: no hostname given\n");
        exit(1);
    }

    // open config file
    char data[DATA_SIZE];
    FILE *f = fopen(conf_file, "r");
    if (f == NULL) {
        fprintf(stderr, "ERROR: config file %s does not exist\n", conf_file);
        exit(1);
    }

    // store default configuration
    putconf("alias_last -last");
    putconf("alias_text unavailable");
    putconf("data_port 4411");
    putconf("data_timeout 2");
    putconf("relay_port 22");

    // store config settings
    while (fgets(data, DATA_SIZE, f) != NULL) {
        if (strlen(data) == DATA_SIZE - 1) {
            fprintf(stderr, "ERROR: config entry \"%s\" too long\n", data);
            exit(1);
        }
        if (data[strlen(data) - 1] == '\n') data[strlen(data) - 1] = 0;
        if (data[strlen(data) - 1] == '\r') data[strlen(data) - 1] = 0;
        putconf(data);
    }
    fclose(f);

    // check required config settings
    for (int i = 0; i < sizeof(conf_req) / sizeof(char *); i++) {
        char *tmp = getconf(conf_req[i]);
        if (tmp == NULL) {
            fprintf(stderr, "ERROR: config parameter %s is not defined\n",
                conf_req[i]);
            exit(1);
        }
    }

    // copy argument
    char arg[strlen(argv[optind]) + 1];
    strcpy(arg, argv[optind]);
    // chop off domain
    char *alias_domain = getconf("alias_domain");
    char *tmp = strstr(arg, alias_domain);
    if (tmp == arg + strlen(arg) - strlen(alias_domain)) tmp[0] = 0;
    // chop off last
    int last = 0;
    char *alias_last = getconf("alias_last");
    tmp = strstr(arg, alias_last);
    if (tmp == arg + strlen(arg) - strlen(alias_last)) {
        tmp[0] = 0;
        last = 1;
    }

    // find default hosts for given alias
    char hosts_alias[strlen(arg) + 7];
    sprintf(hosts_alias, "hosts_%s", arg);
    char *defaults = getconf(hosts_alias);

    if (defaults != NULL) {
        // given host matches defined alias, so load balance
        // construct balancing request
        char sdata[DATA_SIZE];
        snprintf(sdata, DATA_SIZE, "%s%s %d", arg, 
            last ? getconf("alias_last") : "", getuid());
        // concatenate optional arguments to request
        for (int i = optind + 1; i < argc; i++) {
            if (strlen(argv[i]) + 2 > DATA_SIZE - strlen(sdata)) {
                fprintf(stderr, "ERROR: excessive argument length\n");
                exit(1);
            }
            strncat(sdata, argv[i], DATA_SIZE - strlen(sdata) - 2);
        }
        strcat(sdata, "\n");

        // retrieve least loaded hosts from data server or time out
        signal(SIGALRM, timeout);
        char *host = strdup(getconf("data_host"));
        for (host = strtok(host, " "); host; host = strtok(NULL, " ")) {
            // resolve host name outside alarm to avoid reentrancy issues
            struct addrinfo *ainfo = resolve(host);
            alarm(igetconf("data_timeout"));
            if (sigsetjmp(env, 1) != SIGALRM && !getdata(sdata, data, ainfo)) break;
            // loop to try alternate data servers on failure
            alarm(0);
        }
        alarm(0);
        if (host == NULL) {
            // copy default data on failed retrieval for strtok
            strncpy(data, defaults, DATA_SIZE - 1);
            data[DATA_SIZE - 1] = 0;
        }
        if (strspn(data, " ") == strlen(data)) {
            // data is empty so no hosts available
            fprintf(stderr, "ERROR: all hosts for alias %s are %s\n",
                arg, getconf("alias_text"));
            exit(1);
        }

        // count number of hosts in data
        host = data;
        long n = 1;
        while ((host = strchr(host + 1, ' ')) != NULL) n++;

        // pick random host from data
        srand(time(NULL));
        n = rand() % n;
        for (host = strtok(data, " "); n-- > 0; host = strtok(NULL, " "));
        if (opt_list) {
            // print chosen host
            printf("%s\n", host);
            exit(0);
        } else {
            // connect to chosen host
            execl(getconf("relay_path"), getconf("relay_path"), host,
                getconf("relay_port"), NULL);
            // does not return
        }
    }

    // given host does not match alias, so pass through untouched
    if (opt_list) {
        // print given host
        printf("%s\n", argv[optind]);
    } else {
        // connect to given host
        execl(getconf("relay_path"), getconf("relay_path"), argv[optind],
            getconf("relay_port"), NULL);
        // does not return
    }
}