static void get_kernel_supported_enctypes(void) { FILE *s_e; int ret; char buffer[MYBUFLEN + 1]; memset(buffer, '\0', sizeof(buffer)); s_e = fopen(supported_enctypes_filename, "r"); if (s_e == NULL) goto out_clean_parsed; ret = fread(buffer, 1, MYBUFLEN, s_e); if (ret < 0) { fclose(s_e); goto out_clean_parsed; } fclose(s_e); if (parse_enctypes(buffer)) { goto out_clean_parsed; } out: return; out_clean_parsed: if (parsed_enctypes != NULL) { free(parsed_enctypes); parsed_num_enctypes = 0; } goto out; }
void handle_gssd_upcall(struct clnt_info *clp) { uid_t uid; char lbuf[RPC_CHAN_BUF_SIZE]; int lbuflen = 0; char *p; char *mech = NULL; char *uidstr = NULL; char *target = NULL; char *service = NULL; char *enctypes = NULL; lbuflen = read(clp->gssd_fd, lbuf, sizeof(lbuf)); if (lbuflen <= 0 || lbuf[lbuflen-1] != '\n') { printerr(0, "WARNING: handle_gssd_upcall: " "failed reading request\n"); return; } lbuf[lbuflen-1] = 0; printerr(2, "\n%s: '%s' (%s)\n", __func__, lbuf, clp->relpath); for (p = strtok(lbuf, " "); p; p = strtok(NULL, " ")) { if (!strncmp(p, "mech=", strlen("mech="))) mech = p + strlen("mech="); else if (!strncmp(p, "uid=", strlen("uid="))) uidstr = p + strlen("uid="); else if (!strncmp(p, "enctypes=", strlen("enctypes="))) enctypes = p + strlen("enctypes="); else if (!strncmp(p, "target=", strlen("target="))) target = p + strlen("target="); else if (!strncmp(p, "service=", strlen("service="))) service = p + strlen("service="); } if (!mech || strlen(mech) < 1) { printerr(0, "WARNING: handle_gssd_upcall: " "failed to find gss mechanism name " "in upcall string '%s'\n", lbuf); return; } if (uidstr) { uid = (uid_t)strtol(uidstr, &p, 10); if (p == uidstr || *p != '\0') uidstr = NULL; } if (!uidstr) { printerr(0, "WARNING: handle_gssd_upcall: " "failed to find uid " "in upcall string '%s'\n", lbuf); return; } if (enctypes && parse_enctypes(enctypes) != 0) { printerr(0, "WARNING: handle_gssd_upcall: " "parsing encryption types failed: errno %d\n", errno); return; } if (target && strlen(target) < 1) { printerr(0, "WARNING: handle_gssd_upcall: " "failed to parse target name " "in upcall string '%s'\n", lbuf); return; } /* * The presence of attribute "service=" indicates that machine * credentials should be used for this request. If the value * is "*", then any machine credentials available can be used. * If the value is anything else, then machine credentials for * the specified service name (always "nfs" for now) should be * used. */ if (service && strlen(service) < 1) { printerr(0, "WARNING: handle_gssd_upcall: " "failed to parse service type " "in upcall string '%s'\n", lbuf); return; } if (strcmp(mech, "krb5") == 0 && clp->servername) process_krb5_upcall(clp, uid, clp->gssd_fd, target, service); else { if (clp->servername) printerr(0, "WARNING: handle_gssd_upcall: " "received unknown gss mech '%s'\n", mech); do_error_downcall(clp->gssd_fd, uid, -EACCES); } }