/* * Translate the sid string ("S-1-...") to the user@domain name, if * possible. */ static PyObject * py_sid_to_name(PyObject *self, PyObject *args) { int isuser, err, flag = IDMAP_REQ_FLG_USE_CACHE; char *name, *sid; idmap_stat stat; uid_t pid; PyObject *ret; if (!PyArg_ParseTuple(args, "si", &sid, &isuser)) return (NULL); err = sid_to_id(sid, isuser, &pid); if (err) { PyErr_SetString(PyExc_KeyError, sid); return (NULL); } if (isuser) stat = idmap_getwinnamebyuid(pid, flag, &name, NULL); else stat = idmap_getwinnamebygid(pid, flag, &name, NULL); if (stat < 0) { PyErr_SetString(PyExc_KeyError, sid); return (NULL); } if (name == NULL) { PyErr_SetString(PyExc_KeyError, sid); return (NULL); } ret = PyString_FromString(name); free(name); return (ret); }
static int getsidname(uid_t who, boolean_t user, char **sidp, boolean_t noresolve) { idmap_get_handle_t *get_hdl = NULL; idmap_stat status; idmap_rid_t rid; int error = IDMAP_ERR_NORESULT; int len; char *domain = NULL; *sidp = NULL; /* * First try and get windows name */ if (!noresolve) { if (user) error = idmap_getwinnamebyuid(who, IDMAP_REQ_FLG_USE_CACHE, sidp, NULL); else error = idmap_getwinnamebygid(who, IDMAP_REQ_FLG_USE_CACHE, sidp, NULL); } if (error != IDMAP_SUCCESS) { if (idmap_get_create(&get_hdl) == IDMAP_SUCCESS) { if (user) error = idmap_get_sidbyuid(get_hdl, who, IDMAP_REQ_FLG_USE_CACHE, &domain, &rid, &status); else error = idmap_get_sidbygid(get_hdl, who, IDMAP_REQ_FLG_USE_CACHE, &domain, &rid, &status); if (error == IDMAP_SUCCESS && idmap_get_mappings(get_hdl) == 0) { if (status == IDMAP_SUCCESS) { len = snprintf(NULL, 0, "%s-%d", domain, rid); if (*sidp = malloc(len + 1)) { (void) snprintf(*sidp, len + 1, "%s-%d", domain, rid); } } } } if (get_hdl) idmap_get_destroy(get_hdl); } free(domain); return (*sidp ? 0 : 1); }
/* ARGSUSED1 */ void nfsmapid_gid_str(struct mapid_arg *argp, size_t arg_size) { struct mapid_res result; struct mapid_res *resp; struct group grp; struct group *grp_ptr; char *grp_buf = NULL; char *idmap_buf = NULL; idmap_stat rc; gid_t gid = argp->u_arg.gid; size_t gid_str_len; char *gr_str; size_t gr_str_len; char *at_str; size_t at_str_len; char dom_str[DNAMEMAX]; size_t dom_str_len; if (gid == (gid_t)-1) { /* * Sentinel gid is not a valid id */ resp = &result; resp->status = NFSMAPID_BADID; resp->u_res.len = 0; goto done; } /* * Make local copy of domain for further manipuation * NOTE: mapid_get_domain() returns a ptr to TSD. */ if (cur_domain_null()) { dom_str_len = 0; dom_str[0] = '\0'; } else { dom_str_len = strlen(mapid_get_domain()); bcopy(mapid_get_domain(), dom_str, dom_str_len); dom_str[dom_str_len] = '\0'; } /* * If gid is ephemeral then resolve it using idmap service */ if (gid > UID_MAX) { rc = idmap_getwinnamebygid(gid, &idmap_buf, NULL); if (rc != IDMAP_SUCCESS) { /* * We don't put stringified ephemeral gids on * the wire. */ resp = &result; resp->status = NFSMAPID_UNMAPPABLE; resp->u_res.len = 0; goto done; } /* * idmap_buf is already in the desired form i.e. name@domain */ gr_str = idmap_buf; gr_str_len = strlen(gr_str); at_str_len = dom_str_len = 0; at_str = ""; dom_str[0] = '\0'; goto gen_result; } /* * Handling non-ephemeral gids * * We want to encode the gid into a literal string... : * * - upon failure to allocate space from the heap * - if there is no current domain configured * - if there is no such gid in the group DB's */ if ((grp_buf = malloc(grp_buflen)) == NULL || dom_str_len == 0 || getgrgid_r(gid, &grp, grp_buf, grp_buflen, &grp_ptr) != 0 || grp_ptr == NULL) { /* * If we could not allocate from the heap, try * allocating from the stack as a last resort. */ if (grp_buf == NULL && (grp_buf = alloca(MAPID_RES_LEN(UID_MAX_STR_LEN))) == NULL) { resp = &result; resp->status = NFSMAPID_INTERNAL; resp->u_res.len = 0; goto done; } /* * Constructing literal string without '@' so that * we'll know that it's not a group, but rather a * gid encoded string. */ gr_str = grp_buf; (void) sprintf(gr_str, "%u", gid); gr_str_len = strlen(gr_str); at_str_len = dom_str_len = 0; at_str = ""; dom_str[0] = '\0'; } else { /* * Otherwise, we construct the "group@domain" string if * it's not already in that form. */ gr_str = grp.gr_name; gr_str_len = strlen(gr_str); if (strchr(gr_str, '@') == NULL) { at_str = "@"; at_str_len = 1; } else { at_str_len = dom_str_len = 0; at_str = ""; dom_str[0] = '\0'; } } gen_result: gid_str_len = gr_str_len + at_str_len + dom_str_len; if ((resp = alloca(MAPID_RES_LEN(gid_str_len))) == NULL) { resp = &result; resp->status = NFSMAPID_INTERNAL; resp->u_res.len = 0; goto done; } /* LINTED format argument to sprintf */ (void) sprintf(resp->str, "%s%s%s", gr_str, at_str, dom_str); resp->u_res.len = gid_str_len; if (grp_buf) free(grp_buf); if (idmap_buf) idmap_free(idmap_buf); resp->status = NFSMAPID_OK; done: /* * There is a chance that the door_return will fail because the * resulting string is too large, try to indicate that if possible */ if (door_return((char *)resp, MAPID_RES_LEN(resp->u_res.len), NULL, 0) == -1) { resp->status = NFSMAPID_INTERNAL; resp->u_res.len = 0; (void) door_return((char *)&result, sizeof (struct mapid_res), NULL, 0); } }