summaryrefslogtreecommitdiffstats
path: root/server/providers/krb5/krb5_auth.c
diff options
context:
space:
mode:
Diffstat (limited to 'server/providers/krb5/krb5_auth.c')
-rw-r--r--server/providers/krb5/krb5_auth.c74
1 files changed, 37 insertions, 37 deletions
diff --git a/server/providers/krb5/krb5_auth.c b/server/providers/krb5/krb5_auth.c
index a02147e45..d3e05e120 100644
--- a/server/providers/krb5/krb5_auth.c
+++ b/server/providers/krb5/krb5_auth.c
@@ -43,36 +43,6 @@
#define KRB5_CHILD SSSD_LIBEXEC_PATH"/krb5_child"
#endif
-static errno_t become_user(uid_t uid, gid_t gid)
-{
- int ret;
- ret = setgid(gid);
- if (ret == -1) {
- DEBUG(1, ("setgid failed [%d][%s].\n", errno, strerror(errno)));
- return errno;
- }
-
- ret = setuid(uid);
- if (ret == -1) {
- DEBUG(1, ("setuid failed [%d][%s].\n", errno, strerror(errno)));
- return errno;
- }
-
- ret = setegid(gid);
- if (ret == -1) {
- DEBUG(1, ("setegid failed [%d][%s].\n", errno, strerror(errno)));
- return errno;
- }
-
- ret = seteuid(uid);
- if (ret == -1) {
- DEBUG(1, ("seteuid failed [%d][%s].\n", errno, strerror(errno)));
- return errno;
- }
-
- return EOK;
-}
-
struct io_buffer {
uint8_t *data;
size_t size;
@@ -82,6 +52,16 @@ errno_t create_send_buffer(struct krb5child_req *kr, struct io_buffer **io_buf)
{
struct io_buffer *buf;
size_t rp;
+ const char *keytab;
+ uint32_t validate;
+
+ keytab = dp_opt_get_cstring(kr->krb5_ctx->opts, KRB5_KEYTAB);
+ if (keytab == NULL) {
+ DEBUG(1, ("Missing keytab option.\n"));
+ return EINVAL;
+ }
+
+ validate = dp_opt_get_bool(kr->krb5_ctx->opts, KRB5_VALIDATE) ? 1 : 0;
buf = talloc(kr, struct io_buffer);
if (buf == NULL) {
@@ -89,10 +69,11 @@ errno_t create_send_buffer(struct krb5child_req *kr, struct io_buffer **io_buf)
return ENOMEM;
}
- buf->size = 4*sizeof(int) + strlen(kr->pd->upn) + strlen(kr->ccname) +
+ buf->size = 8*sizeof(uint32_t) + strlen(kr->pd->upn) + strlen(kr->ccname) +
+ strlen(keytab) +
kr->pd->authtok_size;
if (kr->pd->cmd == SSS_PAM_CHAUTHTOK) {
- buf->size += sizeof(int) + kr->pd->newauthtok_size;
+ buf->size += sizeof(uint32_t) + kr->pd->newauthtok_size;
}
buf->data = talloc_size(kr, buf->size);
@@ -106,6 +87,15 @@ errno_t create_send_buffer(struct krb5child_req *kr, struct io_buffer **io_buf)
((uint32_t *)(&buf->data[rp]))[0] = kr->pd->cmd;
rp += sizeof(uint32_t);
+ ((uint32_t *)(&buf->data[rp]))[0] = kr->pd->pw_uid;
+ rp += sizeof(uint32_t);
+
+ ((uint32_t *)(&buf->data[rp]))[0] = kr->pd->gr_gid;
+ rp += sizeof(uint32_t);
+
+ ((uint32_t *)(&buf->data[rp]))[0] = validate;
+ rp += sizeof(uint32_t);
+
((uint32_t *)(&buf->data[rp]))[0] = (uint32_t) strlen(kr->pd->upn);
rp += sizeof(uint32_t);
@@ -118,6 +108,12 @@ errno_t create_send_buffer(struct krb5child_req *kr, struct io_buffer **io_buf)
memcpy(&buf->data[rp], kr->ccname, strlen(kr->ccname));
rp += strlen(kr->ccname);
+ ((uint32_t *)(&buf->data[rp]))[0] = (uint32_t) strlen(keytab);
+ rp += sizeof(uint32_t);
+
+ memcpy(&buf->data[rp], keytab, strlen(keytab));
+ rp += strlen(keytab);
+
((uint32_t *)(&buf->data[rp]))[0] = kr->pd->authtok_size;
rp += sizeof(uint32_t);
@@ -436,13 +432,17 @@ static errno_t fork_child(struct krb5child_req *kr)
return err;
}
- ret = become_user(kr->pd->pw_uid, kr->pd->gr_gid);
- if (ret != EOK) {
- DEBUG(1, ("become_user failed.\n"));
- return ret;
+ /* We need to keep the root privileges to read the keytab file if
+ * validation is enabled, otherwise we can drop them here and run
+ * krb5_child with user privileges. */
+ if (!dp_opt_get_bool(kr->krb5_ctx->opts, KRB5_VALIDATE)) {
+ ret = become_user(kr->pd->pw_uid, kr->pd->gr_gid);
+ if (ret != EOK) {
+ DEBUG(1, ("become_user failed.\n"));
+ return ret;
+ }
}
-
close(pipefd_to_child[1]);
ret = dup2(pipefd_to_child[0],STDIN_FILENO);
if (ret == -1) {