Convert ldap results into a sudoers userspec so we can use the "sudo
-l" output functions in parse.c.
This commit is contained in:
@@ -667,7 +667,7 @@ short *yysslim;
|
|||||||
YYSTYPE *yyvs;
|
YYSTYPE *yyvs;
|
||||||
unsigned int yystacksize;
|
unsigned int yystacksize;
|
||||||
int yyparse(void);
|
int yyparse(void);
|
||||||
#line 898 "gram.y"
|
#line 899 "gram.y"
|
||||||
void
|
void
|
||||||
sudoerserror(const char *s)
|
sudoerserror(const char *s)
|
||||||
{
|
{
|
||||||
@@ -866,12 +866,13 @@ free_members(struct member_list *members)
|
|||||||
void
|
void
|
||||||
free_userspec(struct userspec *us)
|
free_userspec(struct userspec *us)
|
||||||
{
|
{
|
||||||
struct privilege *priv, *next;
|
struct privilege *priv;
|
||||||
|
|
||||||
free_members(&us->users);
|
free_members(&us->users);
|
||||||
TAILQ_FOREACH_SAFE(priv, &us->privileges, entries, next) {
|
while ((priv = TAILQ_FIRST(&us->privileges)) != NULL) {
|
||||||
struct member_list *runasuserlist = NULL, *runasgrouplist = NULL;
|
struct member_list *runasuserlist = NULL, *runasgrouplist = NULL;
|
||||||
struct cmndspec *cs, *cs_next;
|
struct cmndspec *cs;
|
||||||
|
struct defaults *def;
|
||||||
#ifdef HAVE_SELINUX
|
#ifdef HAVE_SELINUX
|
||||||
char *role = NULL, *type = NULL;
|
char *role = NULL, *type = NULL;
|
||||||
#endif /* HAVE_SELINUX */
|
#endif /* HAVE_SELINUX */
|
||||||
@@ -879,8 +880,11 @@ free_userspec(struct userspec *us)
|
|||||||
char *privs = NULL, *limitprivs = NULL;
|
char *privs = NULL, *limitprivs = NULL;
|
||||||
#endif /* HAVE_PRIV_SET */
|
#endif /* HAVE_PRIV_SET */
|
||||||
|
|
||||||
|
TAILQ_REMOVE(&us->privileges, priv, entries);
|
||||||
|
free(priv->ldap_role);
|
||||||
free_members(&priv->hostlist);
|
free_members(&priv->hostlist);
|
||||||
TAILQ_FOREACH_SAFE(cs, &priv->cmndlist, entries, cs_next) {
|
while ((cs = TAILQ_FIRST(&priv->cmndlist)) != NULL) {
|
||||||
|
TAILQ_REMOVE(&priv->cmndlist, cs, entries);
|
||||||
#ifdef HAVE_SELINUX
|
#ifdef HAVE_SELINUX
|
||||||
/* Only free the first instance of a role/type. */
|
/* Only free the first instance of a role/type. */
|
||||||
if (cs->role != role) {
|
if (cs->role != role) {
|
||||||
@@ -917,6 +921,12 @@ free_userspec(struct userspec *us)
|
|||||||
free_member(cs->cmnd);
|
free_member(cs->cmnd);
|
||||||
free(cs);
|
free(cs);
|
||||||
}
|
}
|
||||||
|
while ((def = TAILQ_FIRST(&priv->defaults)) != NULL) {
|
||||||
|
TAILQ_REMOVE(&priv->defaults, def, entries);
|
||||||
|
free(def->var);
|
||||||
|
free(def->val);
|
||||||
|
free(def);
|
||||||
|
}
|
||||||
free(priv);
|
free(priv);
|
||||||
}
|
}
|
||||||
rcstr_delref(us->file);
|
rcstr_delref(us->file);
|
||||||
@@ -1000,7 +1010,7 @@ init_options(struct command_options *opts)
|
|||||||
opts->limitprivs = NULL;
|
opts->limitprivs = NULL;
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
#line 951 "gram.c"
|
#line 961 "gram.c"
|
||||||
/* allocate initial stack or double stack size, up to YYMAXDEPTH */
|
/* allocate initial stack or double stack size, up to YYMAXDEPTH */
|
||||||
#if defined(__cplusplus) || defined(__STDC__)
|
#if defined(__cplusplus) || defined(__STDC__)
|
||||||
static int yygrowstack(void)
|
static int yygrowstack(void)
|
||||||
@@ -1364,6 +1374,7 @@ case 26:
|
|||||||
sudoerserror(N_("unable to allocate memory"));
|
sudoerserror(N_("unable to allocate memory"));
|
||||||
YYERROR;
|
YYERROR;
|
||||||
}
|
}
|
||||||
|
TAILQ_INIT(&p->defaults);
|
||||||
HLTQ_TO_TAILQ(&p->hostlist, yyvsp[-2].member, entries);
|
HLTQ_TO_TAILQ(&p->hostlist, yyvsp[-2].member, entries);
|
||||||
HLTQ_TO_TAILQ(&p->cmndlist, yyvsp[0].cmndspec, entries);
|
HLTQ_TO_TAILQ(&p->cmndlist, yyvsp[0].cmndspec, entries);
|
||||||
HLTQ_INIT(p, entries);
|
HLTQ_INIT(p, entries);
|
||||||
@@ -1371,21 +1382,21 @@ case 26:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 27:
|
case 27:
|
||||||
#line 293 "gram.y"
|
#line 294 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = yyvsp[0].member;
|
yyval.member = yyvsp[0].member;
|
||||||
yyval.member->negated = false;
|
yyval.member->negated = false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 28:
|
case 28:
|
||||||
#line 297 "gram.y"
|
#line 298 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = yyvsp[0].member;
|
yyval.member = yyvsp[0].member;
|
||||||
yyval.member->negated = true;
|
yyval.member->negated = true;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 29:
|
case 29:
|
||||||
#line 303 "gram.y"
|
#line 304 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(yyvsp[0].string, ALIAS);
|
yyval.member = new_member(yyvsp[0].string, ALIAS);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -1395,7 +1406,7 @@ case 29:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 30:
|
case 30:
|
||||||
#line 310 "gram.y"
|
#line 311 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(NULL, ALL);
|
yyval.member = new_member(NULL, ALL);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -1405,7 +1416,7 @@ case 30:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 31:
|
case 31:
|
||||||
#line 317 "gram.y"
|
#line 318 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(yyvsp[0].string, NETGROUP);
|
yyval.member = new_member(yyvsp[0].string, NETGROUP);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -1415,7 +1426,7 @@ case 31:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 32:
|
case 32:
|
||||||
#line 324 "gram.y"
|
#line 325 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(yyvsp[0].string, NTWKADDR);
|
yyval.member = new_member(yyvsp[0].string, NTWKADDR);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -1425,7 +1436,7 @@ case 32:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 33:
|
case 33:
|
||||||
#line 331 "gram.y"
|
#line 332 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(yyvsp[0].string, WORD);
|
yyval.member = new_member(yyvsp[0].string, WORD);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -1435,7 +1446,7 @@ case 33:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 35:
|
case 35:
|
||||||
#line 341 "gram.y"
|
#line 342 "gram.y"
|
||||||
{
|
{
|
||||||
struct cmndspec *prev;
|
struct cmndspec *prev;
|
||||||
prev = HLTQ_LAST(yyvsp[-2].cmndspec, cmndspec, entries);
|
prev = HLTQ_LAST(yyvsp[-2].cmndspec, cmndspec, entries);
|
||||||
@@ -1489,7 +1500,7 @@ case 35:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 36:
|
case 36:
|
||||||
#line 394 "gram.y"
|
#line 395 "gram.y"
|
||||||
{
|
{
|
||||||
struct cmndspec *cs = calloc(1, sizeof(*cs));
|
struct cmndspec *cs = calloc(1, sizeof(*cs));
|
||||||
if (cs == NULL) {
|
if (cs == NULL) {
|
||||||
@@ -1541,7 +1552,7 @@ case 36:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 37:
|
case 37:
|
||||||
#line 445 "gram.y"
|
#line 446 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.digest = new_digest(SUDO_DIGEST_SHA224, yyvsp[0].string);
|
yyval.digest = new_digest(SUDO_DIGEST_SHA224, yyvsp[0].string);
|
||||||
if (yyval.digest == NULL) {
|
if (yyval.digest == NULL) {
|
||||||
@@ -1551,7 +1562,7 @@ case 37:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 38:
|
case 38:
|
||||||
#line 452 "gram.y"
|
#line 453 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.digest = new_digest(SUDO_DIGEST_SHA256, yyvsp[0].string);
|
yyval.digest = new_digest(SUDO_DIGEST_SHA256, yyvsp[0].string);
|
||||||
if (yyval.digest == NULL) {
|
if (yyval.digest == NULL) {
|
||||||
@@ -1561,7 +1572,7 @@ case 38:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 39:
|
case 39:
|
||||||
#line 459 "gram.y"
|
#line 460 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.digest = new_digest(SUDO_DIGEST_SHA384, yyvsp[0].string);
|
yyval.digest = new_digest(SUDO_DIGEST_SHA384, yyvsp[0].string);
|
||||||
if (yyval.digest == NULL) {
|
if (yyval.digest == NULL) {
|
||||||
@@ -1571,7 +1582,7 @@ case 39:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 40:
|
case 40:
|
||||||
#line 466 "gram.y"
|
#line 467 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.digest = new_digest(SUDO_DIGEST_SHA512, yyvsp[0].string);
|
yyval.digest = new_digest(SUDO_DIGEST_SHA512, yyvsp[0].string);
|
||||||
if (yyval.digest == NULL) {
|
if (yyval.digest == NULL) {
|
||||||
@@ -1581,13 +1592,13 @@ case 40:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 41:
|
case 41:
|
||||||
#line 475 "gram.y"
|
#line 476 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = yyvsp[0].member;
|
yyval.member = yyvsp[0].member;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 42:
|
case 42:
|
||||||
#line 478 "gram.y"
|
#line 479 "gram.y"
|
||||||
{
|
{
|
||||||
if (yyvsp[0].member->type != COMMAND) {
|
if (yyvsp[0].member->type != COMMAND) {
|
||||||
sudoerserror(N_("a digest requires a path name"));
|
sudoerserror(N_("a digest requires a path name"));
|
||||||
@@ -1599,75 +1610,75 @@ case 42:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 43:
|
case 43:
|
||||||
#line 489 "gram.y"
|
#line 490 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = yyvsp[0].member;
|
yyval.member = yyvsp[0].member;
|
||||||
yyval.member->negated = false;
|
yyval.member->negated = false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 44:
|
case 44:
|
||||||
#line 493 "gram.y"
|
#line 494 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = yyvsp[0].member;
|
yyval.member = yyvsp[0].member;
|
||||||
yyval.member->negated = true;
|
yyval.member->negated = true;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 45:
|
case 45:
|
||||||
#line 499 "gram.y"
|
#line 500 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.string = yyvsp[0].string;
|
yyval.string = yyvsp[0].string;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 46:
|
case 46:
|
||||||
#line 504 "gram.y"
|
#line 505 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.string = yyvsp[0].string;
|
yyval.string = yyvsp[0].string;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 47:
|
case 47:
|
||||||
#line 508 "gram.y"
|
#line 509 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.string = yyvsp[0].string;
|
yyval.string = yyvsp[0].string;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 48:
|
case 48:
|
||||||
#line 513 "gram.y"
|
#line 514 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.string = yyvsp[0].string;
|
yyval.string = yyvsp[0].string;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 49:
|
case 49:
|
||||||
#line 518 "gram.y"
|
#line 519 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.string = yyvsp[0].string;
|
yyval.string = yyvsp[0].string;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 50:
|
case 50:
|
||||||
#line 523 "gram.y"
|
#line 524 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.string = yyvsp[0].string;
|
yyval.string = yyvsp[0].string;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 51:
|
case 51:
|
||||||
#line 527 "gram.y"
|
#line 528 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.string = yyvsp[0].string;
|
yyval.string = yyvsp[0].string;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 52:
|
case 52:
|
||||||
#line 532 "gram.y"
|
#line 533 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.runas = NULL;
|
yyval.runas = NULL;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 53:
|
case 53:
|
||||||
#line 535 "gram.y"
|
#line 536 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.runas = yyvsp[-1].runas;
|
yyval.runas = yyvsp[-1].runas;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 54:
|
case 54:
|
||||||
#line 540 "gram.y"
|
#line 541 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.runas = calloc(1, sizeof(struct runascontainer));
|
yyval.runas = calloc(1, sizeof(struct runascontainer));
|
||||||
if (yyval.runas != NULL) {
|
if (yyval.runas != NULL) {
|
||||||
@@ -1685,7 +1696,7 @@ case 54:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 55:
|
case 55:
|
||||||
#line 555 "gram.y"
|
#line 556 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.runas = calloc(1, sizeof(struct runascontainer));
|
yyval.runas = calloc(1, sizeof(struct runascontainer));
|
||||||
if (yyval.runas == NULL) {
|
if (yyval.runas == NULL) {
|
||||||
@@ -1697,7 +1708,7 @@ case 55:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 56:
|
case 56:
|
||||||
#line 564 "gram.y"
|
#line 565 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.runas = calloc(1, sizeof(struct runascontainer));
|
yyval.runas = calloc(1, sizeof(struct runascontainer));
|
||||||
if (yyval.runas == NULL) {
|
if (yyval.runas == NULL) {
|
||||||
@@ -1709,7 +1720,7 @@ case 56:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 57:
|
case 57:
|
||||||
#line 573 "gram.y"
|
#line 574 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.runas = calloc(1, sizeof(struct runascontainer));
|
yyval.runas = calloc(1, sizeof(struct runascontainer));
|
||||||
if (yyval.runas == NULL) {
|
if (yyval.runas == NULL) {
|
||||||
@@ -1721,7 +1732,7 @@ case 57:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 58:
|
case 58:
|
||||||
#line 582 "gram.y"
|
#line 583 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.runas = calloc(1, sizeof(struct runascontainer));
|
yyval.runas = calloc(1, sizeof(struct runascontainer));
|
||||||
if (yyval.runas != NULL) {
|
if (yyval.runas != NULL) {
|
||||||
@@ -1739,13 +1750,13 @@ case 58:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 59:
|
case 59:
|
||||||
#line 599 "gram.y"
|
#line 600 "gram.y"
|
||||||
{
|
{
|
||||||
init_options(&yyval.options);
|
init_options(&yyval.options);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 60:
|
case 60:
|
||||||
#line 602 "gram.y"
|
#line 603 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.options.notbefore = parse_gentime(yyvsp[0].string);
|
yyval.options.notbefore = parse_gentime(yyvsp[0].string);
|
||||||
free(yyvsp[0].string);
|
free(yyvsp[0].string);
|
||||||
@@ -1756,7 +1767,7 @@ case 60:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 61:
|
case 61:
|
||||||
#line 610 "gram.y"
|
#line 611 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.options.notafter = parse_gentime(yyvsp[0].string);
|
yyval.options.notafter = parse_gentime(yyvsp[0].string);
|
||||||
free(yyvsp[0].string);
|
free(yyvsp[0].string);
|
||||||
@@ -1767,7 +1778,7 @@ case 61:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 62:
|
case 62:
|
||||||
#line 618 "gram.y"
|
#line 619 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.options.timeout = parse_timeout(yyvsp[0].string);
|
yyval.options.timeout = parse_timeout(yyvsp[0].string);
|
||||||
free(yyvsp[0].string);
|
free(yyvsp[0].string);
|
||||||
@@ -1781,7 +1792,7 @@ case 62:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 63:
|
case 63:
|
||||||
#line 629 "gram.y"
|
#line 630 "gram.y"
|
||||||
{
|
{
|
||||||
#ifdef HAVE_SELINUX
|
#ifdef HAVE_SELINUX
|
||||||
free(yyval.options.role);
|
free(yyval.options.role);
|
||||||
@@ -1790,7 +1801,7 @@ case 63:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 64:
|
case 64:
|
||||||
#line 635 "gram.y"
|
#line 636 "gram.y"
|
||||||
{
|
{
|
||||||
#ifdef HAVE_SELINUX
|
#ifdef HAVE_SELINUX
|
||||||
free(yyval.options.type);
|
free(yyval.options.type);
|
||||||
@@ -1799,7 +1810,7 @@ case 64:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 65:
|
case 65:
|
||||||
#line 641 "gram.y"
|
#line 642 "gram.y"
|
||||||
{
|
{
|
||||||
#ifdef HAVE_PRIV_SET
|
#ifdef HAVE_PRIV_SET
|
||||||
free(yyval.options.privs);
|
free(yyval.options.privs);
|
||||||
@@ -1808,7 +1819,7 @@ case 65:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 66:
|
case 66:
|
||||||
#line 647 "gram.y"
|
#line 648 "gram.y"
|
||||||
{
|
{
|
||||||
#ifdef HAVE_PRIV_SET
|
#ifdef HAVE_PRIV_SET
|
||||||
free(yyval.options.limitprivs);
|
free(yyval.options.limitprivs);
|
||||||
@@ -1817,97 +1828,97 @@ case 66:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 67:
|
case 67:
|
||||||
#line 655 "gram.y"
|
#line 656 "gram.y"
|
||||||
{
|
{
|
||||||
TAGS_INIT(yyval.tag);
|
TAGS_INIT(yyval.tag);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 68:
|
case 68:
|
||||||
#line 658 "gram.y"
|
#line 659 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.nopasswd = true;
|
yyval.tag.nopasswd = true;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 69:
|
case 69:
|
||||||
#line 661 "gram.y"
|
#line 662 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.nopasswd = false;
|
yyval.tag.nopasswd = false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 70:
|
case 70:
|
||||||
#line 664 "gram.y"
|
#line 665 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.noexec = true;
|
yyval.tag.noexec = true;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 71:
|
case 71:
|
||||||
#line 667 "gram.y"
|
#line 668 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.noexec = false;
|
yyval.tag.noexec = false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 72:
|
case 72:
|
||||||
#line 670 "gram.y"
|
#line 671 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.setenv = true;
|
yyval.tag.setenv = true;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 73:
|
case 73:
|
||||||
#line 673 "gram.y"
|
#line 674 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.setenv = false;
|
yyval.tag.setenv = false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 74:
|
case 74:
|
||||||
#line 676 "gram.y"
|
#line 677 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.log_input = true;
|
yyval.tag.log_input = true;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 75:
|
case 75:
|
||||||
#line 679 "gram.y"
|
#line 680 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.log_input = false;
|
yyval.tag.log_input = false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 76:
|
case 76:
|
||||||
#line 682 "gram.y"
|
#line 683 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.log_output = true;
|
yyval.tag.log_output = true;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 77:
|
case 77:
|
||||||
#line 685 "gram.y"
|
#line 686 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.log_output = false;
|
yyval.tag.log_output = false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 78:
|
case 78:
|
||||||
#line 688 "gram.y"
|
#line 689 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.follow = true;
|
yyval.tag.follow = true;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 79:
|
case 79:
|
||||||
#line 691 "gram.y"
|
#line 692 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.follow = false;
|
yyval.tag.follow = false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 80:
|
case 80:
|
||||||
#line 694 "gram.y"
|
#line 695 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.send_mail = true;
|
yyval.tag.send_mail = true;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 81:
|
case 81:
|
||||||
#line 697 "gram.y"
|
#line 698 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.tag.send_mail = false;
|
yyval.tag.send_mail = false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 82:
|
case 82:
|
||||||
#line 702 "gram.y"
|
#line 703 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(NULL, ALL);
|
yyval.member = new_member(NULL, ALL);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -1917,7 +1928,7 @@ case 82:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 83:
|
case 83:
|
||||||
#line 709 "gram.y"
|
#line 710 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(yyvsp[0].string, ALIAS);
|
yyval.member = new_member(yyvsp[0].string, ALIAS);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -1927,7 +1938,7 @@ case 83:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 84:
|
case 84:
|
||||||
#line 716 "gram.y"
|
#line 717 "gram.y"
|
||||||
{
|
{
|
||||||
struct sudo_command *c = calloc(1, sizeof(*c));
|
struct sudo_command *c = calloc(1, sizeof(*c));
|
||||||
if (c == NULL) {
|
if (c == NULL) {
|
||||||
@@ -1945,7 +1956,7 @@ case 84:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 87:
|
case 87:
|
||||||
#line 737 "gram.y"
|
#line 738 "gram.y"
|
||||||
{
|
{
|
||||||
const char *s;
|
const char *s;
|
||||||
s = alias_add(yyvsp[-2].string, HOSTALIAS, sudoers, this_lineno, yyvsp[0].member);
|
s = alias_add(yyvsp[-2].string, HOSTALIAS, sudoers, this_lineno, yyvsp[0].member);
|
||||||
@@ -1956,14 +1967,14 @@ case 87:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 89:
|
case 89:
|
||||||
#line 748 "gram.y"
|
#line 749 "gram.y"
|
||||||
{
|
{
|
||||||
HLTQ_CONCAT(yyvsp[-2].member, yyvsp[0].member, entries);
|
HLTQ_CONCAT(yyvsp[-2].member, yyvsp[0].member, entries);
|
||||||
yyval.member = yyvsp[-2].member;
|
yyval.member = yyvsp[-2].member;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 92:
|
case 92:
|
||||||
#line 758 "gram.y"
|
#line 759 "gram.y"
|
||||||
{
|
{
|
||||||
const char *s;
|
const char *s;
|
||||||
s = alias_add(yyvsp[-2].string, CMNDALIAS, sudoers, this_lineno, yyvsp[0].member);
|
s = alias_add(yyvsp[-2].string, CMNDALIAS, sudoers, this_lineno, yyvsp[0].member);
|
||||||
@@ -1974,14 +1985,14 @@ case 92:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 94:
|
case 94:
|
||||||
#line 769 "gram.y"
|
#line 770 "gram.y"
|
||||||
{
|
{
|
||||||
HLTQ_CONCAT(yyvsp[-2].member, yyvsp[0].member, entries);
|
HLTQ_CONCAT(yyvsp[-2].member, yyvsp[0].member, entries);
|
||||||
yyval.member = yyvsp[-2].member;
|
yyval.member = yyvsp[-2].member;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 97:
|
case 97:
|
||||||
#line 779 "gram.y"
|
#line 780 "gram.y"
|
||||||
{
|
{
|
||||||
const char *s;
|
const char *s;
|
||||||
s = alias_add(yyvsp[-2].string, RUNASALIAS, sudoers, this_lineno, yyvsp[0].member);
|
s = alias_add(yyvsp[-2].string, RUNASALIAS, sudoers, this_lineno, yyvsp[0].member);
|
||||||
@@ -1992,7 +2003,7 @@ case 97:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 100:
|
case 100:
|
||||||
#line 793 "gram.y"
|
#line 794 "gram.y"
|
||||||
{
|
{
|
||||||
const char *s;
|
const char *s;
|
||||||
s = alias_add(yyvsp[-2].string, USERALIAS, sudoers, this_lineno, yyvsp[0].member);
|
s = alias_add(yyvsp[-2].string, USERALIAS, sudoers, this_lineno, yyvsp[0].member);
|
||||||
@@ -2003,28 +2014,28 @@ case 100:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 102:
|
case 102:
|
||||||
#line 804 "gram.y"
|
#line 805 "gram.y"
|
||||||
{
|
{
|
||||||
HLTQ_CONCAT(yyvsp[-2].member, yyvsp[0].member, entries);
|
HLTQ_CONCAT(yyvsp[-2].member, yyvsp[0].member, entries);
|
||||||
yyval.member = yyvsp[-2].member;
|
yyval.member = yyvsp[-2].member;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 103:
|
case 103:
|
||||||
#line 810 "gram.y"
|
#line 811 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = yyvsp[0].member;
|
yyval.member = yyvsp[0].member;
|
||||||
yyval.member->negated = false;
|
yyval.member->negated = false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 104:
|
case 104:
|
||||||
#line 814 "gram.y"
|
#line 815 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = yyvsp[0].member;
|
yyval.member = yyvsp[0].member;
|
||||||
yyval.member->negated = true;
|
yyval.member->negated = true;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 105:
|
case 105:
|
||||||
#line 820 "gram.y"
|
#line 821 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(yyvsp[0].string, ALIAS);
|
yyval.member = new_member(yyvsp[0].string, ALIAS);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -2034,7 +2045,7 @@ case 105:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 106:
|
case 106:
|
||||||
#line 827 "gram.y"
|
#line 828 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(NULL, ALL);
|
yyval.member = new_member(NULL, ALL);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -2044,7 +2055,7 @@ case 106:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 107:
|
case 107:
|
||||||
#line 834 "gram.y"
|
#line 835 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(yyvsp[0].string, NETGROUP);
|
yyval.member = new_member(yyvsp[0].string, NETGROUP);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -2054,7 +2065,7 @@ case 107:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 108:
|
case 108:
|
||||||
#line 841 "gram.y"
|
#line 842 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(yyvsp[0].string, USERGROUP);
|
yyval.member = new_member(yyvsp[0].string, USERGROUP);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -2064,7 +2075,7 @@ case 108:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 109:
|
case 109:
|
||||||
#line 848 "gram.y"
|
#line 849 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(yyvsp[0].string, WORD);
|
yyval.member = new_member(yyvsp[0].string, WORD);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -2074,28 +2085,28 @@ case 109:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 111:
|
case 111:
|
||||||
#line 858 "gram.y"
|
#line 859 "gram.y"
|
||||||
{
|
{
|
||||||
HLTQ_CONCAT(yyvsp[-2].member, yyvsp[0].member, entries);
|
HLTQ_CONCAT(yyvsp[-2].member, yyvsp[0].member, entries);
|
||||||
yyval.member = yyvsp[-2].member;
|
yyval.member = yyvsp[-2].member;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 112:
|
case 112:
|
||||||
#line 864 "gram.y"
|
#line 865 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = yyvsp[0].member;
|
yyval.member = yyvsp[0].member;
|
||||||
yyval.member->negated = false;
|
yyval.member->negated = false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 113:
|
case 113:
|
||||||
#line 868 "gram.y"
|
#line 869 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = yyvsp[0].member;
|
yyval.member = yyvsp[0].member;
|
||||||
yyval.member->negated = true;
|
yyval.member->negated = true;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 114:
|
case 114:
|
||||||
#line 874 "gram.y"
|
#line 875 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(yyvsp[0].string, ALIAS);
|
yyval.member = new_member(yyvsp[0].string, ALIAS);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -2105,7 +2116,7 @@ case 114:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 115:
|
case 115:
|
||||||
#line 881 "gram.y"
|
#line 882 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(NULL, ALL);
|
yyval.member = new_member(NULL, ALL);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -2115,7 +2126,7 @@ case 115:
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 116:
|
case 116:
|
||||||
#line 888 "gram.y"
|
#line 889 "gram.y"
|
||||||
{
|
{
|
||||||
yyval.member = new_member(yyvsp[0].string, WORD);
|
yyval.member = new_member(yyvsp[0].string, WORD);
|
||||||
if (yyval.member == NULL) {
|
if (yyval.member == NULL) {
|
||||||
@@ -2124,7 +2135,7 @@ case 116:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
#line 2075 "gram.c"
|
#line 2086 "gram.c"
|
||||||
}
|
}
|
||||||
yyssp -= yym;
|
yyssp -= yym;
|
||||||
yystate = *yyssp;
|
yystate = *yyssp;
|
||||||
|
@@ -283,6 +283,7 @@ privilege : hostlist '=' cmndspeclist {
|
|||||||
sudoerserror(N_("unable to allocate memory"));
|
sudoerserror(N_("unable to allocate memory"));
|
||||||
YYERROR;
|
YYERROR;
|
||||||
}
|
}
|
||||||
|
TAILQ_INIT(&p->defaults);
|
||||||
HLTQ_TO_TAILQ(&p->hostlist, $1, entries);
|
HLTQ_TO_TAILQ(&p->hostlist, $1, entries);
|
||||||
HLTQ_TO_TAILQ(&p->cmndlist, $3, entries);
|
HLTQ_TO_TAILQ(&p->cmndlist, $3, entries);
|
||||||
HLTQ_INIT(p, entries);
|
HLTQ_INIT(p, entries);
|
||||||
@@ -1093,12 +1094,13 @@ free_members(struct member_list *members)
|
|||||||
void
|
void
|
||||||
free_userspec(struct userspec *us)
|
free_userspec(struct userspec *us)
|
||||||
{
|
{
|
||||||
struct privilege *priv, *next;
|
struct privilege *priv;
|
||||||
|
|
||||||
free_members(&us->users);
|
free_members(&us->users);
|
||||||
TAILQ_FOREACH_SAFE(priv, &us->privileges, entries, next) {
|
while ((priv = TAILQ_FIRST(&us->privileges)) != NULL) {
|
||||||
struct member_list *runasuserlist = NULL, *runasgrouplist = NULL;
|
struct member_list *runasuserlist = NULL, *runasgrouplist = NULL;
|
||||||
struct cmndspec *cs, *cs_next;
|
struct cmndspec *cs;
|
||||||
|
struct defaults *def;
|
||||||
#ifdef HAVE_SELINUX
|
#ifdef HAVE_SELINUX
|
||||||
char *role = NULL, *type = NULL;
|
char *role = NULL, *type = NULL;
|
||||||
#endif /* HAVE_SELINUX */
|
#endif /* HAVE_SELINUX */
|
||||||
@@ -1106,8 +1108,11 @@ free_userspec(struct userspec *us)
|
|||||||
char *privs = NULL, *limitprivs = NULL;
|
char *privs = NULL, *limitprivs = NULL;
|
||||||
#endif /* HAVE_PRIV_SET */
|
#endif /* HAVE_PRIV_SET */
|
||||||
|
|
||||||
|
TAILQ_REMOVE(&us->privileges, priv, entries);
|
||||||
|
free(priv->ldap_role);
|
||||||
free_members(&priv->hostlist);
|
free_members(&priv->hostlist);
|
||||||
TAILQ_FOREACH_SAFE(cs, &priv->cmndlist, entries, cs_next) {
|
while ((cs = TAILQ_FIRST(&priv->cmndlist)) != NULL) {
|
||||||
|
TAILQ_REMOVE(&priv->cmndlist, cs, entries);
|
||||||
#ifdef HAVE_SELINUX
|
#ifdef HAVE_SELINUX
|
||||||
/* Only free the first instance of a role/type. */
|
/* Only free the first instance of a role/type. */
|
||||||
if (cs->role != role) {
|
if (cs->role != role) {
|
||||||
@@ -1144,6 +1149,12 @@ free_userspec(struct userspec *us)
|
|||||||
free_member(cs->cmnd);
|
free_member(cs->cmnd);
|
||||||
free(cs);
|
free(cs);
|
||||||
}
|
}
|
||||||
|
while ((def = TAILQ_FIRST(&priv->defaults)) != NULL) {
|
||||||
|
TAILQ_REMOVE(&priv->defaults, def, entries);
|
||||||
|
free(def->var);
|
||||||
|
free(def->val);
|
||||||
|
free(def);
|
||||||
|
}
|
||||||
free(priv);
|
free(priv);
|
||||||
}
|
}
|
||||||
rcstr_delref(us->file);
|
rcstr_delref(us->file);
|
||||||
|
@@ -59,6 +59,7 @@
|
|||||||
|
|
||||||
#include "sudoers.h"
|
#include "sudoers.h"
|
||||||
#include "parse.h"
|
#include "parse.h"
|
||||||
|
#include "gram.h"
|
||||||
#include "sudo_lbuf.h"
|
#include "sudo_lbuf.h"
|
||||||
#include "sudo_dso.h"
|
#include "sudo_dso.h"
|
||||||
|
|
||||||
@@ -2370,13 +2371,10 @@ sudo_ldap_get_first_rdn(LDAP *ld, LDAPMessage *entry)
|
|||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
sudo_ldap_print_quoted3(struct sudo_lbuf *lbuf, const char *prefix, const char *str, const char *suffix)
|
sudo_ldap_print_quoted(struct sudo_lbuf *lbuf, const char *str)
|
||||||
{
|
{
|
||||||
const char *name = str;
|
const char *name = str;
|
||||||
|
debug_decl(sudo_ldap_print_quoted, SUDOERS_DEBUG_LDAP)
|
||||||
/* Prefix is not quoted. */
|
|
||||||
if (prefix != NULL)
|
|
||||||
sudo_lbuf_append(lbuf, "%s", prefix);
|
|
||||||
|
|
||||||
/* Do not quote UID/GID, all others get quoted. */
|
/* Do not quote UID/GID, all others get quoted. */
|
||||||
while (*name == '!')
|
while (*name == '!')
|
||||||
@@ -2392,21 +2390,7 @@ sudo_ldap_print_quoted3(struct sudo_lbuf *lbuf, const char *prefix, const char *
|
|||||||
sudo_lbuf_append_quoted(lbuf, SUDOERS_QUOTED, "%s", str);
|
sudo_lbuf_append_quoted(lbuf, SUDOERS_QUOTED, "%s", str);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Suffix is not quoted. */
|
debug_return;
|
||||||
if (suffix != NULL)
|
|
||||||
sudo_lbuf_append(lbuf, "%s", suffix);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
sudo_ldap_print_quoted2(struct sudo_lbuf *lbuf, const char *prefix, const char *str)
|
|
||||||
{
|
|
||||||
return sudo_ldap_print_quoted3(lbuf, prefix, str, NULL);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
|
||||||
sudo_ldap_print_quoted(struct sudo_lbuf *lbuf, const char *str)
|
|
||||||
{
|
|
||||||
return sudo_ldap_print_quoted3(lbuf, NULL, str, NULL);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -2484,237 +2468,311 @@ sudo_ldap_display_bound_defaults(struct sudo_nss *nss, struct passwd *pw,
|
|||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Print a record in the short form, ala file sudoers.
|
* Convert an array of struct berval to a member list.
|
||||||
*/
|
*/
|
||||||
static int
|
static struct member_list *
|
||||||
sudo_ldap_display_entry_short(LDAP *ld, LDAPMessage *entry, struct passwd *pw,
|
bv_to_member_list(struct berval **bv)
|
||||||
struct sudo_lbuf *lbuf)
|
|
||||||
{
|
{
|
||||||
struct berval **bv, **p;
|
struct member_list *members;
|
||||||
bool no_runas_user = true;
|
struct berval **p;
|
||||||
int count = 0;
|
struct member *m;
|
||||||
debug_decl(sudo_ldap_display_entry_short, SUDOERS_DEBUG_LDAP)
|
debug_decl(bv_to_member_list, SUDOERS_DEBUG_LDAP)
|
||||||
|
|
||||||
sudo_lbuf_append(lbuf, " (");
|
if ((members = calloc(1, sizeof(*members))) == NULL)
|
||||||
|
return NULL;
|
||||||
|
TAILQ_INIT(members);
|
||||||
|
|
||||||
/* get the RunAsUser Values from the entry */
|
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoRunAsUser");
|
|
||||||
if (bv == NULL)
|
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoRunAs");
|
|
||||||
if (bv != NULL) {
|
|
||||||
for (p = bv; *p != NULL; p++) {
|
for (p = bv; *p != NULL; p++) {
|
||||||
sudo_ldap_print_quoted2(lbuf, p != bv ? ", " : "",
|
if ((m = calloc(1, sizeof(*m))) == NULL)
|
||||||
(*p)->bv_val[0] ? (*p)->bv_val : user_name);
|
goto bad;
|
||||||
}
|
|
||||||
ldap_value_free_len(bv);
|
|
||||||
no_runas_user = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* get the RunAsGroup Values from the entry */
|
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoRunAsGroup");
|
|
||||||
if (bv != NULL) {
|
|
||||||
if (no_runas_user) {
|
|
||||||
/* finish printing sudoRunAs */
|
|
||||||
sudo_ldap_print_quoted(lbuf, pw->pw_name);
|
|
||||||
}
|
|
||||||
sudo_lbuf_append(lbuf, " : ");
|
|
||||||
for (p = bv; *p != NULL; p++) {
|
|
||||||
sudo_ldap_print_quoted2(lbuf, p != bv ? ", " : "", (*p)->bv_val);
|
|
||||||
}
|
|
||||||
ldap_value_free_len(bv);
|
|
||||||
} else {
|
|
||||||
if (no_runas_user) {
|
|
||||||
/* finish printing sudoRunAs */
|
|
||||||
sudo_ldap_print_quoted(lbuf, def_runas_default);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
sudo_lbuf_append(lbuf, ") ");
|
|
||||||
|
|
||||||
/* Get the sudoNotBefore and sudoNotAfter Values from the entry */
|
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoNotBefore");
|
|
||||||
if (bv != NULL) {
|
|
||||||
for (p = bv; *p != NULL; p++) {
|
|
||||||
sudo_ldap_print_quoted3(lbuf, "NOTBEFORE=", (*p)->bv_val, " ");
|
|
||||||
}
|
|
||||||
ldap_value_free_len(bv);
|
|
||||||
}
|
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoNotAfter");
|
|
||||||
if (bv != NULL) {
|
|
||||||
for (p = bv; *p != NULL; p++) {
|
|
||||||
sudo_ldap_print_quoted3(lbuf, "NOTAFTER=", (*p)->bv_val, " ");
|
|
||||||
}
|
|
||||||
ldap_value_free_len(bv);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* get the Option Values from the entry */
|
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoOption");
|
|
||||||
if (bv != NULL) {
|
|
||||||
for (p = bv; *p != NULL; p++) {
|
|
||||||
char *val = (*p)->bv_val;
|
char *val = (*p)->bv_val;
|
||||||
bool negated = sudo_ldap_is_negated(&val);
|
switch (val[0]) {
|
||||||
if (strcmp(val, "authenticate") == 0)
|
case '\0':
|
||||||
sudo_lbuf_append(lbuf, negated ? "NOPASSWD: " : "PASSWD: ");
|
/* Empty RunAsUser means run as the invoking user. */
|
||||||
else if (strcmp(val, "sudoedit_follow") == 0)
|
m->type = MYSELF;
|
||||||
sudo_lbuf_append(lbuf, negated ? "NOFOLLOW: " : "FOLLOW: ");
|
break;
|
||||||
else if (strcmp(val, "noexec") == 0)
|
case 'A':
|
||||||
sudo_lbuf_append(lbuf, negated ? "EXEC: " : "NOEXEC: ");
|
if (strcmp(val, "ALL") == 0) {
|
||||||
else if (strcmp(val, "setenv") == 0)
|
m->type = ALL;
|
||||||
sudo_lbuf_append(lbuf, negated ? "NOSETENV: " : "SETENV: ");
|
break;
|
||||||
else if (strcmp(val, "mail_all_cmnds") == 0 || strcmp(val, "mail_always") == 0)
|
|
||||||
sudo_lbuf_append(lbuf, negated ? "NOMAIL: " : "MAIL: ");
|
|
||||||
else if (!negated && strncmp(val, "command_timeout=", 16) == 0)
|
|
||||||
sudo_ldap_print_quoted3(lbuf, "TIMEOUT=", val + 16, " ");
|
|
||||||
#ifdef HAVE_SELINUX
|
|
||||||
else if (!negated && strncmp(val, "role=", 5) == 0)
|
|
||||||
sudo_ldap_print_quoted3(lbuf, "ROLE=", val + 5, " ");
|
|
||||||
else if (!negated && strncmp(val, "type=", 5) == 0)
|
|
||||||
sudo_ldap_print_quoted3(lbuf, "TYPE=", val + 5, " ");
|
|
||||||
#endif /* HAVE_SELINUX */
|
|
||||||
#ifdef HAVE_PRIV_SET
|
|
||||||
else if (!negated && strncmp(val, "privs=", 6) == 0)
|
|
||||||
sudo_ldap_print_quoted3(lbuf, "PRIVS=", val + 6, " ");
|
|
||||||
else if (!negated && strncmp(val, "limitprivs=", 11) == 0)
|
|
||||||
sudo_ldap_print_quoted3(lbuf, "LIMITPRIVS=", val + 11, " ");
|
|
||||||
#endif /* HAVE_PRIV_SET */
|
|
||||||
}
|
}
|
||||||
ldap_value_free_len(bv);
|
/* FALLTHROUGH */
|
||||||
|
default:
|
||||||
|
m->type = WORD;
|
||||||
|
m->name = strdup(val);
|
||||||
|
if (m->name == NULL) {
|
||||||
|
free(m);
|
||||||
|
goto bad;
|
||||||
}
|
}
|
||||||
|
break;
|
||||||
/* get the Command Values from the entry */
|
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoCommand");
|
|
||||||
if (bv != NULL) {
|
|
||||||
for (p = bv; *p != NULL; p++) {
|
|
||||||
char *args = strpbrk((*p)->bv_val, " \t");
|
|
||||||
if (args != NULL)
|
|
||||||
*args++ = '\0';
|
|
||||||
if (p != bv)
|
|
||||||
sudo_lbuf_append(lbuf, ", ");
|
|
||||||
sudo_lbuf_append_quoted(lbuf, SUDOERS_QUOTED" \t", "%s",
|
|
||||||
(*p)->bv_val);
|
|
||||||
if (args != NULL) {
|
|
||||||
sudo_lbuf_append(lbuf, " ");
|
|
||||||
sudo_lbuf_append_quoted(lbuf, SUDOERS_QUOTED, "%s", args);
|
|
||||||
}
|
}
|
||||||
count++;
|
TAILQ_INSERT_TAIL(members, m, entries);
|
||||||
}
|
}
|
||||||
ldap_value_free_len(bv);
|
debug_return_ptr(members);
|
||||||
|
bad:
|
||||||
|
while ((m = TAILQ_FIRST(members)) != NULL) {
|
||||||
|
TAILQ_REMOVE(members, m, entries);
|
||||||
|
free(m->name);
|
||||||
|
free(m);
|
||||||
}
|
}
|
||||||
sudo_lbuf_append(lbuf, "\n");
|
free(members);
|
||||||
|
debug_return_ptr(NULL);
|
||||||
debug_return_int(count);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
static struct userspec_list *
|
||||||
* Print a record in the long form.
|
ldap2sudoers(LDAP *ld, struct ldap_result *lres)
|
||||||
*/
|
|
||||||
static int
|
|
||||||
sudo_ldap_display_entry_long(LDAP *ld, LDAPMessage *entry, struct passwd *pw,
|
|
||||||
struct sudo_lbuf *lbuf)
|
|
||||||
{
|
{
|
||||||
|
struct userspec_list *ldap_userspecs;
|
||||||
|
struct cmndspec *cmndspec = NULL;
|
||||||
|
struct sudo_command *c;
|
||||||
|
struct privilege *priv;
|
||||||
|
struct userspec *us;
|
||||||
|
struct member *m;
|
||||||
struct berval **bv, **p;
|
struct berval **bv, **p;
|
||||||
bool no_runas_user = true;
|
struct berval **cmnd_bv, **cmnd; /* XXX - naming */
|
||||||
char *rdn;
|
char *cn;
|
||||||
int count = 0;
|
unsigned int i;
|
||||||
debug_decl(sudo_ldap_display_entry_long, SUDOERS_DEBUG_LDAP)
|
debug_decl(ldap2sudoers, SUDOERS_DEBUG_LDAP)
|
||||||
|
|
||||||
/* extract the dn, only show the first rdn */
|
if ((ldap_userspecs = calloc(1, sizeof(*ldap_userspecs))) == NULL)
|
||||||
rdn = sudo_ldap_get_first_rdn(ld, entry);
|
goto oom;
|
||||||
if (rdn != NULL)
|
TAILQ_INIT(ldap_userspecs);
|
||||||
sudo_lbuf_append(lbuf, _("\nLDAP Role: %s\n"), rdn);
|
|
||||||
else
|
|
||||||
sudo_lbuf_append(lbuf, _("\nLDAP Role: UNKNOWN\n"));
|
|
||||||
if (rdn)
|
|
||||||
ldap_memfree(rdn);
|
|
||||||
|
|
||||||
/* get the RunAsUser Values from the entry */
|
/* We only have a single userspec */
|
||||||
sudo_lbuf_append(lbuf, " RunAsUsers: ");
|
if ((us = calloc(1, sizeof(*us))) == NULL)
|
||||||
|
goto oom;
|
||||||
|
TAILQ_INIT(&us->users);
|
||||||
|
TAILQ_INIT(&us->privileges);
|
||||||
|
TAILQ_INSERT_TAIL(ldap_userspecs, us, entries);
|
||||||
|
|
||||||
|
/* The user has already matched, use ALL as wildcard. */
|
||||||
|
if ((m = calloc(1, sizeof(*m))) == NULL)
|
||||||
|
goto oom;
|
||||||
|
m->type = ALL;
|
||||||
|
TAILQ_INSERT_TAIL(&us->users, m, entries);
|
||||||
|
|
||||||
|
/* Treat each sudoRole as a separate privilege. */
|
||||||
|
for (i = 0; i < lres->nentries; i++) {
|
||||||
|
struct cmndspec *prev_cmndspec = NULL;
|
||||||
|
LDAPMessage *entry = lres->entries[i].entry;
|
||||||
|
|
||||||
|
/* Ignore sudoRole without sudoCommand. */
|
||||||
|
cmnd_bv = ldap_get_values_len(ld, entry, "sudoCommand");
|
||||||
|
if (cmnd_bv == NULL)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if ((priv = calloc(1, sizeof(*priv))) == NULL)
|
||||||
|
goto oom;
|
||||||
|
TAILQ_INIT(&priv->hostlist);
|
||||||
|
TAILQ_INIT(&priv->cmndlist);
|
||||||
|
TAILQ_INIT(&priv->defaults);
|
||||||
|
TAILQ_INSERT_TAIL(&us->privileges, priv, entries);
|
||||||
|
|
||||||
|
/* Get the entry's dn for long format printing. */
|
||||||
|
cn = sudo_ldap_get_first_rdn(ld, entry);
|
||||||
|
priv->ldap_role = strdup(cn ? cn : "UNKNOWN");
|
||||||
|
if (cn != NULL)
|
||||||
|
ldap_memfree(cn);
|
||||||
|
if (priv->ldap_role == NULL)
|
||||||
|
goto oom;
|
||||||
|
|
||||||
|
/* The host has already matched, use ALL as wildcard. */
|
||||||
|
if ((m = calloc(1, sizeof(*m))) == NULL)
|
||||||
|
goto oom;
|
||||||
|
m->type = ALL;
|
||||||
|
TAILQ_INSERT_TAIL(&priv->hostlist, m, entries);
|
||||||
|
|
||||||
|
/* Parse sudoCommands and add to cmndlist. */
|
||||||
|
for (cmnd = cmnd_bv; *cmnd != NULL; cmnd++) {
|
||||||
|
char *args;
|
||||||
|
|
||||||
|
/* Allocate storage upfront. */
|
||||||
|
cmndspec = calloc(1, sizeof(*cmndspec));
|
||||||
|
c = calloc(1, sizeof(*c));
|
||||||
|
m = calloc(1, sizeof(*m));
|
||||||
|
if (cmndspec == NULL || c == NULL || m == NULL) {
|
||||||
|
free(c);
|
||||||
|
free(m);
|
||||||
|
goto oom;
|
||||||
|
}
|
||||||
|
TAILQ_INSERT_TAIL(&priv->cmndlist, cmndspec, entries);
|
||||||
|
|
||||||
|
/* Initialize cmndspec */
|
||||||
|
TAGS_INIT(cmndspec->tags);
|
||||||
|
cmndspec->notbefore = UNSPEC;
|
||||||
|
cmndspec->notafter = UNSPEC;
|
||||||
|
cmndspec->timeout = UNSPEC;
|
||||||
|
|
||||||
|
/* Fill in command. */
|
||||||
|
if ((args = strpbrk((*cmnd)->bv_val, " \t")) != NULL) {
|
||||||
|
*args++ = '\0';
|
||||||
|
if ((c->args = strdup(args)) == NULL) {
|
||||||
|
free(c);
|
||||||
|
free(m);
|
||||||
|
goto oom;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if ((c->cmnd = strdup((*cmnd)->bv_val)) == NULL) {
|
||||||
|
free(c->args);
|
||||||
|
free(c);
|
||||||
|
free(m);
|
||||||
|
goto oom;
|
||||||
|
}
|
||||||
|
m->type = COMMAND;
|
||||||
|
m->name = (char *)c;
|
||||||
|
cmndspec->cmnd = m;
|
||||||
|
|
||||||
|
if (prev_cmndspec != NULL) {
|
||||||
|
/* Inherit values from prior cmndspec */
|
||||||
|
cmndspec->runasuserlist = prev_cmndspec->runasuserlist;
|
||||||
|
cmndspec->runasgrouplist = prev_cmndspec->runasgrouplist;
|
||||||
|
cmndspec->notbefore = prev_cmndspec->notbefore;
|
||||||
|
cmndspec->notafter = prev_cmndspec->notafter;
|
||||||
|
cmndspec->tags = prev_cmndspec->tags;
|
||||||
|
} else {
|
||||||
|
/* Parse sudoRunAsUser / sudoRunAs */
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoRunAsUser");
|
bv = ldap_get_values_len(ld, entry, "sudoRunAsUser");
|
||||||
if (bv == NULL)
|
if (bv == NULL)
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoRunAs");
|
bv = ldap_get_values_len(ld, entry, "sudoRunAs"); /* old style */
|
||||||
if (bv != NULL) {
|
if (bv != NULL) {
|
||||||
for (p = bv; *p != NULL; p++) {
|
cmndspec->runasuserlist = bv_to_member_list(bv);
|
||||||
sudo_lbuf_append(lbuf, "%s%s", p != bv ? ", " : "", (*p)->bv_val);
|
if (cmndspec->runasuserlist == NULL)
|
||||||
}
|
goto oom;
|
||||||
ldap_value_free_len(bv);
|
ldap_value_free_len(bv);
|
||||||
no_runas_user = false;
|
bv = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* get the RunAsGroup Values from the entry */
|
/* Parse sudoRunAsGroup */
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoRunAsGroup");
|
bv = ldap_get_values_len(ld, entry, "sudoRunAsGroup");
|
||||||
if (bv != NULL) {
|
if (bv != NULL) {
|
||||||
if (no_runas_user) {
|
cmndspec->runasgrouplist = bv_to_member_list(bv);
|
||||||
/* finish printing sudoRunAs */
|
if (cmndspec->runasgrouplist == NULL)
|
||||||
sudo_lbuf_append(lbuf, "%s", pw->pw_name);
|
goto oom;
|
||||||
}
|
|
||||||
sudo_lbuf_append(lbuf, "\n RunAsGroups: ");
|
|
||||||
for (p = bv; *p != NULL; p++) {
|
|
||||||
sudo_lbuf_append(lbuf, "%s%s", p != bv ? ", " : "", (*p)->bv_val);
|
|
||||||
}
|
|
||||||
ldap_value_free_len(bv);
|
ldap_value_free_len(bv);
|
||||||
sudo_lbuf_append(lbuf, "\n");
|
bv = NULL;
|
||||||
} else {
|
|
||||||
if (no_runas_user) {
|
|
||||||
/* finish printing sudoRunAs */
|
|
||||||
sudo_lbuf_append(lbuf, "%s", def_runas_default);
|
|
||||||
}
|
|
||||||
sudo_lbuf_append(lbuf, "\n");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Get the sudoNotBefore and sudoNotAfter Values from the entry */
|
/* Parse sudoNotBefore */
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoNotBefore");
|
bv = ldap_get_values_len(ld, entry, "sudoNotBefore");
|
||||||
if (bv != NULL) {
|
if (bv != NULL) {
|
||||||
sudo_lbuf_append(lbuf, " NotBefore: ");
|
/* Only takes the last entry. */
|
||||||
for (p = bv; *p != NULL; p++) {
|
for (p = bv; *p != NULL; p++) {
|
||||||
sudo_lbuf_append(lbuf, "%s%s", p != bv ? ", " : "", (*p)->bv_val);
|
cmndspec->notbefore = parse_gentime((*p)->bv_val);
|
||||||
}
|
}
|
||||||
ldap_value_free_len(bv);
|
ldap_value_free_len(bv);
|
||||||
sudo_lbuf_append(lbuf, "\n");
|
bv = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Parse sudoNotAfter */
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoNotAfter");
|
bv = ldap_get_values_len(ld, entry, "sudoNotAfter");
|
||||||
if (bv != NULL) {
|
if (bv != NULL) {
|
||||||
sudo_lbuf_append(lbuf, " NotAfter: ");
|
/* Only takes the last entry. */
|
||||||
for (p = bv; *p != NULL; p++) {
|
for (p = bv; *p != NULL; p++) {
|
||||||
sudo_lbuf_append(lbuf, "%s%s", p != bv ? ", " : "", (*p)->bv_val);
|
cmndspec->notafter = parse_gentime((*p)->bv_val);
|
||||||
}
|
}
|
||||||
ldap_value_free_len(bv);
|
ldap_value_free_len(bv);
|
||||||
sudo_lbuf_append(lbuf, "\n");
|
bv = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* get the Option Values from the entry */
|
/* Parse sudoOptions. */
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoOption");
|
bv = ldap_get_values_len(ld, entry, "sudoOption");
|
||||||
if (bv != NULL) {
|
if (bv != NULL) {
|
||||||
sudo_lbuf_append(lbuf, " Options: ");
|
|
||||||
for (p = bv; *p != NULL; p++) {
|
for (p = bv; *p != NULL; p++) {
|
||||||
sudo_lbuf_append(lbuf, "%s%s", p != bv ? ", " : "", (*p)->bv_val);
|
char *var, *val;
|
||||||
|
int op;
|
||||||
|
|
||||||
|
op = sudo_ldap_parse_option((*p)->bv_val, &var, &val);
|
||||||
|
if (strcmp(var, "command_timeout") == 0) {
|
||||||
|
if (op == '=')
|
||||||
|
cmndspec->timeout = parse_timeout(val);
|
||||||
|
#ifdef HAVE_SELINUX
|
||||||
|
} else if (strcmp(var, "role") == 0) {
|
||||||
|
if (op == '=') {
|
||||||
|
if ((cmndspec->role = strdup(val)) == NULL)
|
||||||
|
goto oom;
|
||||||
|
}
|
||||||
|
} else if (strcmp(var, "type") == 0) {
|
||||||
|
if (op == '=') {
|
||||||
|
if ((cmndspec->type = strdup(val)) == NULL)
|
||||||
|
goto oom;
|
||||||
|
}
|
||||||
|
#endif /* HAVE_SELINUX */
|
||||||
|
#ifdef HAVE_PRIV_SET
|
||||||
|
} else if (strcmp(var, "privs") == 0) {
|
||||||
|
if (op == '=') {
|
||||||
|
if ((cmndspec->privs = strdup(val)) == NULL)
|
||||||
|
goto oom;
|
||||||
|
}
|
||||||
|
} else if (strcmp(val, "limitprivs") == 0) {
|
||||||
|
if (op == '=') {
|
||||||
|
if ((cmndspec->limitprivs = strdup(val)) == NULL)
|
||||||
|
goto oom;
|
||||||
|
}
|
||||||
|
#endif /* HAVE_PRIV_SET */
|
||||||
|
} else if (long_list) {
|
||||||
|
struct defaults *def = calloc(1, sizeof(*def));
|
||||||
|
if (def == NULL)
|
||||||
|
goto oom;
|
||||||
|
def->op = op;
|
||||||
|
if ((def->var = strdup(var)) == NULL) {
|
||||||
|
free(def);
|
||||||
|
goto oom;
|
||||||
|
}
|
||||||
|
if (val != NULL) {
|
||||||
|
if ((def->val = strdup(val)) == NULL) {
|
||||||
|
free(def->var);
|
||||||
|
free(def);
|
||||||
|
goto oom;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
TAILQ_INSERT_TAIL(&priv->defaults, def, entries);
|
||||||
|
} else {
|
||||||
|
/* Convert to tags. */
|
||||||
|
if (op != true && op != false)
|
||||||
|
continue;
|
||||||
|
if (strcmp(var, "authenticate") == 0) {
|
||||||
|
cmndspec->tags.nopasswd = op == false;
|
||||||
|
} else if (strcmp(var, "sudoedit_follow") == 0) {
|
||||||
|
cmndspec->tags.follow = op == true;
|
||||||
|
} else if (strcmp(var, "noexec") == 0) {
|
||||||
|
cmndspec->tags.noexec = op == true;
|
||||||
|
} else if (strcmp(var, "setenv") == 0) {
|
||||||
|
cmndspec->tags.setenv = op == true;
|
||||||
|
} else if (strcmp(var, "mail_all_cmnds") == 0 ||
|
||||||
|
strcmp(var, "mail_always") == 0) {
|
||||||
|
cmndspec->tags.send_mail = op == true;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
ldap_value_free_len(bv);
|
ldap_value_free_len(bv);
|
||||||
sudo_lbuf_append(lbuf, "\n");
|
bv = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/* So we can inherit previous values. */
|
||||||
* Display order attribute if present. This attribute is single valued,
|
prev_cmndspec = cmndspec;
|
||||||
* so there is no need for a loop.
|
|
||||||
*/
|
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoOrder");
|
|
||||||
if (bv != NULL) {
|
|
||||||
if (*bv != NULL) {
|
|
||||||
sudo_lbuf_append(lbuf, _(" Order: %s\n"), (*bv)->bv_val);
|
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
ldap_value_free_len(cmnd_bv);
|
||||||
|
cmnd_bv = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
debug_return_ptr(ldap_userspecs);
|
||||||
|
|
||||||
|
oom:
|
||||||
|
sudo_warnx(U_("%s: %s"), __func__, U_("unable to allocate memory"));
|
||||||
|
if (cmnd_bv != NULL)
|
||||||
|
ldap_value_free_len(cmnd_bv);
|
||||||
|
if (bv != NULL)
|
||||||
ldap_value_free_len(bv);
|
ldap_value_free_len(bv);
|
||||||
|
if (ldap_userspecs != NULL) {
|
||||||
|
while ((us = TAILQ_FIRST(ldap_userspecs)) != NULL) {
|
||||||
|
TAILQ_REMOVE(ldap_userspecs, us, entries);
|
||||||
|
free_userspec(us);
|
||||||
}
|
}
|
||||||
|
free(ldap_userspecs);
|
||||||
/* Get the command values from the entry. */
|
|
||||||
bv = ldap_get_values_len(ld, entry, "sudoCommand");
|
|
||||||
if (bv != NULL) {
|
|
||||||
sudo_lbuf_append(lbuf, _(" Commands:\n"));
|
|
||||||
for (p = bv; *p != NULL; p++) {
|
|
||||||
sudo_lbuf_append(lbuf, "\t%s\n", (*p)->bv_val);
|
|
||||||
count++;
|
|
||||||
}
|
}
|
||||||
ldap_value_free_len(bv);
|
debug_return_ptr(NULL);
|
||||||
}
|
|
||||||
|
|
||||||
debug_return_int(count);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -2725,10 +2783,10 @@ sudo_ldap_display_privs(struct sudo_nss *nss, struct passwd *pw,
|
|||||||
struct sudo_lbuf *lbuf)
|
struct sudo_lbuf *lbuf)
|
||||||
{
|
{
|
||||||
struct sudo_ldap_handle *handle = nss->handle;
|
struct sudo_ldap_handle *handle = nss->handle;
|
||||||
LDAP *ld;
|
struct userspec_list *ldap_userspecs = NULL;
|
||||||
struct ldap_result *lres;
|
struct ldap_result *lres;
|
||||||
LDAPMessage *entry;
|
LDAP *ld;
|
||||||
unsigned int i, count = 0;
|
int ret = 0;
|
||||||
debug_decl(sudo_ldap_display_privs, SUDOERS_DEBUG_LDAP)
|
debug_decl(sudo_ldap_display_privs, SUDOERS_DEBUG_LDAP)
|
||||||
|
|
||||||
if (handle == NULL || handle->ld == NULL)
|
if (handle == NULL || handle->ld == NULL)
|
||||||
@@ -2740,19 +2798,27 @@ sudo_ldap_display_privs(struct sudo_nss *nss, struct passwd *pw,
|
|||||||
if (lres == NULL)
|
if (lres == NULL)
|
||||||
goto done;
|
goto done;
|
||||||
|
|
||||||
/* Display all matching entries. */
|
/* Convert to sudoers parse tree. */
|
||||||
for (i = 0; i < lres->nentries; i++) {
|
if ((ldap_userspecs = ldap2sudoers(ld, lres)) == NULL) {
|
||||||
entry = lres->entries[i].entry;
|
ret = -1;
|
||||||
if (long_list)
|
goto done;
|
||||||
count += sudo_ldap_display_entry_long(ld, entry, pw, lbuf);
|
|
||||||
else
|
|
||||||
count += sudo_ldap_display_entry_short(ld, entry, pw, lbuf);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Call common display code. */
|
||||||
|
ret = sudo_display_userspecs(ldap_userspecs, pw, lbuf);
|
||||||
|
|
||||||
done:
|
done:
|
||||||
|
if (ldap_userspecs != NULL) {
|
||||||
|
struct userspec *us;
|
||||||
|
while ((us = TAILQ_FIRST(ldap_userspecs)) != NULL) {
|
||||||
|
TAILQ_REMOVE(ldap_userspecs, us, entries);
|
||||||
|
free_userspec(us);
|
||||||
|
}
|
||||||
|
free(ldap_userspecs);
|
||||||
|
}
|
||||||
if (sudo_lbuf_error(lbuf))
|
if (sudo_lbuf_error(lbuf))
|
||||||
debug_return_int(-1);
|
debug_return_int(-1);
|
||||||
debug_return_int(count);
|
debug_return_int(ret);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int
|
static int
|
||||||
|
@@ -373,6 +373,8 @@ sudo_file_append_cmnd(struct cmndspec *cs, struct cmndtag *tags,
|
|||||||
{
|
{
|
||||||
debug_decl(sudo_file_append_cmnd, SUDOERS_DEBUG_NSS)
|
debug_decl(sudo_file_append_cmnd, SUDOERS_DEBUG_NSS)
|
||||||
|
|
||||||
|
/* XXX - should not print privs/limitprivs, role/type, timeout
|
||||||
|
or notbefore/after if unchanged from prior cs */
|
||||||
#ifdef HAVE_PRIV_SET
|
#ifdef HAVE_PRIV_SET
|
||||||
if (cs->privs)
|
if (cs->privs)
|
||||||
sudo_lbuf_append(lbuf, "PRIVS=\"%s\" ", cs->privs);
|
sudo_lbuf_append(lbuf, "PRIVS=\"%s\" ", cs->privs);
|
||||||
@@ -438,6 +440,29 @@ sudo_file_append_cmnd(struct cmndspec *cs, struct cmndtag *tags,
|
|||||||
debug_return_bool(!sudo_lbuf_error(lbuf));
|
debug_return_bool(!sudo_lbuf_error(lbuf));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Format and append a defaults entry to the specified lbuf.
|
||||||
|
*/
|
||||||
|
static void
|
||||||
|
sudo_file_append_default(struct sudo_lbuf *lbuf, struct defaults *d)
|
||||||
|
{
|
||||||
|
debug_decl(sudo_file_append_default, SUDOERS_DEBUG_NSS)
|
||||||
|
|
||||||
|
if (d->val != NULL) {
|
||||||
|
sudo_lbuf_append(lbuf, "%s%s", d->var,
|
||||||
|
d->op == '+' ? "+=" : d->op == '-' ? "-=" : "=");
|
||||||
|
if (strpbrk(d->val, " \t") != NULL) {
|
||||||
|
sudo_lbuf_append(lbuf, "\"");
|
||||||
|
sudo_lbuf_append_quoted(lbuf, "\"", "%s", d->val);
|
||||||
|
sudo_lbuf_append(lbuf, "\"");
|
||||||
|
} else
|
||||||
|
sudo_lbuf_append_quoted(lbuf, SUDOERS_QUOTED, "%s", d->val);
|
||||||
|
} else {
|
||||||
|
sudo_lbuf_append(lbuf, "%s%s", d->op == false ? "!" : "", d->var);
|
||||||
|
}
|
||||||
|
debug_return;
|
||||||
|
}
|
||||||
|
|
||||||
static int
|
static int
|
||||||
sudo_file_display_priv_short(struct passwd *pw, struct userspec *us,
|
sudo_file_display_priv_short(struct passwd *pw, struct userspec *us,
|
||||||
struct sudo_lbuf *lbuf)
|
struct sudo_lbuf *lbuf)
|
||||||
@@ -451,6 +476,9 @@ sudo_file_display_priv_short(struct passwd *pw, struct userspec *us,
|
|||||||
|
|
||||||
/* gcc -Wuninitialized false positive */
|
/* gcc -Wuninitialized false positive */
|
||||||
TAGS_INIT(tags);
|
TAGS_INIT(tags);
|
||||||
|
/* XXX - should init tags for each privilege */
|
||||||
|
/* XXX - does runas change inheriting? */
|
||||||
|
/* XXX - what about time and timeout inheriting? */
|
||||||
TAILQ_FOREACH(priv, &us->privileges, entries) {
|
TAILQ_FOREACH(priv, &us->privileges, entries) {
|
||||||
if (hostlist_matches(pw, &priv->hostlist) != ALLOW)
|
if (hostlist_matches(pw, &priv->hostlist) != ALLOW)
|
||||||
continue;
|
continue;
|
||||||
@@ -519,6 +547,10 @@ new_long_entry(struct cmndspec *cs, struct cmndspec *prev_cs)
|
|||||||
#endif /* HAVE_SELINUX */
|
#endif /* HAVE_SELINUX */
|
||||||
if (cs->timeout != prev_cs->timeout)
|
if (cs->timeout != prev_cs->timeout)
|
||||||
return true;
|
return true;
|
||||||
|
if (cs->notbefore != prev_cs->notbefore)
|
||||||
|
return true;
|
||||||
|
if (cs->notafter != prev_cs->notafter)
|
||||||
|
return true;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -527,8 +559,9 @@ sudo_file_display_priv_long(struct passwd *pw, struct userspec *us,
|
|||||||
struct sudo_lbuf *lbuf)
|
struct sudo_lbuf *lbuf)
|
||||||
{
|
{
|
||||||
struct cmndspec *cs, *prev_cs;
|
struct cmndspec *cs, *prev_cs;
|
||||||
struct member *m;
|
|
||||||
struct privilege *priv;
|
struct privilege *priv;
|
||||||
|
struct defaults *def;
|
||||||
|
struct member *m;
|
||||||
int nfound = 0, olen;
|
int nfound = 0, olen;
|
||||||
debug_decl(sudo_file_display_priv_long, SUDOERS_DEBUG_NSS)
|
debug_decl(sudo_file_display_priv_long, SUDOERS_DEBUG_NSS)
|
||||||
|
|
||||||
@@ -538,7 +571,12 @@ sudo_file_display_priv_long(struct passwd *pw, struct userspec *us,
|
|||||||
prev_cs = NULL;
|
prev_cs = NULL;
|
||||||
TAILQ_FOREACH(cs, &priv->cmndlist, entries) {
|
TAILQ_FOREACH(cs, &priv->cmndlist, entries) {
|
||||||
if (new_long_entry(cs, prev_cs)) {
|
if (new_long_entry(cs, prev_cs)) {
|
||||||
|
if (priv->ldap_role != NULL) {
|
||||||
|
sudo_lbuf_append(lbuf, _("\nLDAP Role: %s\n"),
|
||||||
|
priv->ldap_role);
|
||||||
|
} else {
|
||||||
sudo_lbuf_append(lbuf, _("\nSudoers entry:\n"));
|
sudo_lbuf_append(lbuf, _("\nSudoers entry:\n"));
|
||||||
|
}
|
||||||
sudo_lbuf_append(lbuf, _(" RunAsUsers: "));
|
sudo_lbuf_append(lbuf, _(" RunAsUsers: "));
|
||||||
if (cs->runasuserlist != NULL) {
|
if (cs->runasuserlist != NULL) {
|
||||||
TAILQ_FOREACH(m, cs->runasuserlist, entries) {
|
TAILQ_FOREACH(m, cs->runasuserlist, entries) {
|
||||||
@@ -563,6 +601,10 @@ sudo_file_display_priv_long(struct passwd *pw, struct userspec *us,
|
|||||||
}
|
}
|
||||||
olen = lbuf->len;
|
olen = lbuf->len;
|
||||||
sudo_lbuf_append(lbuf, _(" Options: "));
|
sudo_lbuf_append(lbuf, _(" Options: "));
|
||||||
|
TAILQ_FOREACH(def, &priv->defaults, entries) {
|
||||||
|
sudo_file_append_default(lbuf, def);
|
||||||
|
sudo_lbuf_append(lbuf, ", ");
|
||||||
|
}
|
||||||
if (TAG_SET(cs->tags.setenv))
|
if (TAG_SET(cs->tags.setenv))
|
||||||
sudo_lbuf_append(lbuf, "%ssetenv, ", cs->tags.setenv ? "" : "!");
|
sudo_lbuf_append(lbuf, "%ssetenv, ", cs->tags.setenv ? "" : "!");
|
||||||
if (TAG_SET(cs->tags.noexec))
|
if (TAG_SET(cs->tags.noexec))
|
||||||
@@ -624,21 +666,16 @@ sudo_file_display_priv_long(struct passwd *pw, struct userspec *us,
|
|||||||
debug_return_int(nfound);
|
debug_return_int(nfound);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/* XXX - better naming */
|
||||||
* Returns the number of matching privileges or -1 on error.
|
|
||||||
*/
|
|
||||||
int
|
int
|
||||||
sudo_file_display_privs(struct sudo_nss *nss, struct passwd *pw,
|
sudo_display_userspecs(struct userspec_list *usl, struct passwd *pw,
|
||||||
struct sudo_lbuf *lbuf)
|
struct sudo_lbuf *lbuf)
|
||||||
{
|
{
|
||||||
struct userspec *us;
|
struct userspec *us;
|
||||||
int nfound = 0;
|
int nfound = 0;
|
||||||
debug_decl(sudo_file_display_priv, SUDOERS_DEBUG_NSS)
|
debug_decl(sudo_display_userspecs, SUDOERS_DEBUG_NSS)
|
||||||
|
|
||||||
if (nss->handle == NULL)
|
TAILQ_FOREACH(us, usl, entries) {
|
||||||
goto done;
|
|
||||||
|
|
||||||
TAILQ_FOREACH(us, &userspecs, entries) {
|
|
||||||
if (userlist_matches(pw, &us->users) != ALLOW)
|
if (userlist_matches(pw, &us->users) != ALLOW)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
@@ -649,10 +686,24 @@ sudo_file_display_privs(struct sudo_nss *nss, struct passwd *pw,
|
|||||||
}
|
}
|
||||||
if (sudo_lbuf_error(lbuf))
|
if (sudo_lbuf_error(lbuf))
|
||||||
debug_return_int(-1);
|
debug_return_int(-1);
|
||||||
done:
|
|
||||||
debug_return_int(nfound);
|
debug_return_int(nfound);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Returns the number of matching privileges or -1 on error.
|
||||||
|
*/
|
||||||
|
static int
|
||||||
|
sudo_file_display_privs(struct sudo_nss *nss, struct passwd *pw,
|
||||||
|
struct sudo_lbuf *lbuf)
|
||||||
|
{
|
||||||
|
debug_decl(sudo_file_display_priv, SUDOERS_DEBUG_NSS)
|
||||||
|
|
||||||
|
if (nss->handle == NULL)
|
||||||
|
debug_return_int(0);
|
||||||
|
|
||||||
|
debug_return_int(sudo_display_userspecs(&userspecs, pw, lbuf));
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Display matching Defaults entries for the given user on this host.
|
* Display matching Defaults entries for the given user on this host.
|
||||||
*/
|
*/
|
||||||
@@ -687,18 +738,8 @@ sudo_file_display_defaults(struct sudo_nss *nss, struct passwd *pw,
|
|||||||
case DEFAULTS_CMND:
|
case DEFAULTS_CMND:
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
if (d->val != NULL) {
|
sudo_lbuf_append(lbuf, "%s", prefix);
|
||||||
sudo_lbuf_append(lbuf, "%s%s%s", prefix, d->var,
|
sudo_file_append_default(lbuf, d);
|
||||||
d->op == '+' ? "+=" : d->op == '-' ? "-=" : "=");
|
|
||||||
if (strpbrk(d->val, " \t") != NULL) {
|
|
||||||
sudo_lbuf_append(lbuf, "\"");
|
|
||||||
sudo_lbuf_append_quoted(lbuf, "\"", "%s", d->val);
|
|
||||||
sudo_lbuf_append(lbuf, "\"");
|
|
||||||
} else
|
|
||||||
sudo_lbuf_append_quoted(lbuf, SUDOERS_QUOTED, "%s", d->val);
|
|
||||||
} else
|
|
||||||
sudo_lbuf_append(lbuf, "%s%s%s", prefix,
|
|
||||||
d->op == false ? "!" : "", d->var);
|
|
||||||
prefix = ", ";
|
prefix = ", ";
|
||||||
nfound++;
|
nfound++;
|
||||||
}
|
}
|
||||||
@@ -778,11 +819,7 @@ display_bound_defaults(int deftype, struct sudo_lbuf *lbuf)
|
|||||||
}
|
}
|
||||||
} else
|
} else
|
||||||
sudo_lbuf_append(lbuf, ", ");
|
sudo_lbuf_append(lbuf, ", ");
|
||||||
if (d->val != NULL) {
|
sudo_file_append_default(lbuf, d);
|
||||||
sudo_lbuf_append(lbuf, "%s%s%s", d->var, d->op == '+' ? "+=" :
|
|
||||||
d->op == '-' ? "-=" : "=", d->val);
|
|
||||||
} else
|
|
||||||
sudo_lbuf_append(lbuf, "%s%s", d->op == false ? "!" : "", d->var);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (sudo_lbuf_error(lbuf))
|
if (sudo_lbuf_error(lbuf))
|
||||||
|
@@ -167,8 +167,10 @@ struct userspec {
|
|||||||
*/
|
*/
|
||||||
struct privilege {
|
struct privilege {
|
||||||
TAILQ_ENTRY(privilege) entries;
|
TAILQ_ENTRY(privilege) entries;
|
||||||
|
char *ldap_role; /* LDAP sudoRole */
|
||||||
struct member_list hostlist; /* list of hosts */
|
struct member_list hostlist; /* list of hosts */
|
||||||
struct cmndspec_list cmndlist; /* list of Cmnd_Specs */
|
struct cmndspec_list cmndlist; /* list of Cmnd_Specs */
|
||||||
|
struct defaults_list defaults; /* list of sudoOptions */
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -302,4 +304,8 @@ unsigned char *sudo_filedigest(int fd, const char *file, int digest_type, size_t
|
|||||||
/* digestname.c */
|
/* digestname.c */
|
||||||
const char *digest_type_to_name(int digest_type);
|
const char *digest_type_to_name(int digest_type);
|
||||||
|
|
||||||
|
/* parse.c */
|
||||||
|
struct sudo_lbuf;
|
||||||
|
int sudo_display_userspecs(struct userspec_list *usl, struct passwd *pw, struct sudo_lbuf *lbuf);
|
||||||
|
|
||||||
#endif /* SUDOERS_PARSE_H */
|
#endif /* SUDOERS_PARSE_H */
|
||||||
|
Reference in New Issue
Block a user