|
Packit |
fd8b60 |
/* -*- mode: c; c-basic-offset: 4; indent-tabs-mode: nil -*- */
|
|
Packit |
fd8b60 |
/*
|
|
Packit |
fd8b60 |
* Copyright (c) 1994 by the University of Southern California
|
|
Packit |
fd8b60 |
*
|
|
Packit |
fd8b60 |
* EXPORT OF THIS SOFTWARE from the United States of America may
|
|
Packit |
fd8b60 |
* require a specific license from the United States Government.
|
|
Packit |
fd8b60 |
* It is the responsibility of any person or organization contemplating
|
|
Packit |
fd8b60 |
* export to obtain such a license before exporting.
|
|
Packit |
fd8b60 |
*
|
|
Packit |
fd8b60 |
* WITHIN THAT CONSTRAINT, permission to copy, modify, and distribute
|
|
Packit |
fd8b60 |
* this software and its documentation in source and binary forms is
|
|
Packit |
fd8b60 |
* hereby granted, provided that any documentation or other materials
|
|
Packit |
fd8b60 |
* related to such distribution or use acknowledge that the software
|
|
Packit |
fd8b60 |
* was developed by the University of Southern California.
|
|
Packit |
fd8b60 |
*
|
|
Packit |
fd8b60 |
* DISCLAIMER OF WARRANTY. THIS SOFTWARE IS PROVIDED "AS IS". The
|
|
Packit |
fd8b60 |
* University of Southern California MAKES NO REPRESENTATIONS OR
|
|
Packit |
fd8b60 |
* WARRANTIES, EXPRESS OR IMPLIED. By way of example, but not
|
|
Packit |
fd8b60 |
* limitation, the University of Southern California MAKES NO
|
|
Packit |
fd8b60 |
* REPRESENTATIONS OR WARRANTIES OF MERCHANTABILITY OR FITNESS FOR ANY
|
|
Packit |
fd8b60 |
* PARTICULAR PURPOSE. The University of Southern
|
|
Packit |
fd8b60 |
* California shall not be held liable for any liability nor for any
|
|
Packit |
fd8b60 |
* direct, indirect, or consequential damages with respect to any
|
|
Packit |
fd8b60 |
* claim by the user or distributor of the ksu software.
|
|
Packit |
fd8b60 |
*
|
|
Packit |
fd8b60 |
* KSU was writen by: Ari Medvinsky, ari@isi.edu
|
|
Packit |
fd8b60 |
*/
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
#include "ksu.h"
|
|
Packit |
fd8b60 |
#include "adm_proto.h"
|
|
Packit |
fd8b60 |
#include <sys/types.h>
|
|
Packit |
fd8b60 |
#include <sys/wait.h>
|
|
Packit |
fd8b60 |
#include <signal.h>
|
|
Packit |
fd8b60 |
#include <grp.h>
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* globals */
|
|
Packit |
fd8b60 |
char * prog_name;
|
|
Packit |
fd8b60 |
int auth_debug =0;
|
|
Packit |
fd8b60 |
char k5login_path[MAXPATHLEN];
|
|
Packit |
fd8b60 |
char k5users_path[MAXPATHLEN];
|
|
Packit |
fd8b60 |
char * gb_err = NULL;
|
|
Packit |
fd8b60 |
int quiet = 0;
|
|
Packit |
fd8b60 |
/***********/
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
#define KS_TEMPORARY_CACHE "MEMORY:_ksu"
|
|
Packit |
fd8b60 |
#define KS_TEMPORARY_PRINC "_ksu/_ksu@_ksu"
|
|
Packit |
fd8b60 |
#define _DEF_CSH "/bin/csh"
|
|
Packit |
fd8b60 |
static int set_env_var (char *, char *);
|
|
Packit |
fd8b60 |
static void sweep_up (krb5_context, krb5_ccache);
|
|
Packit |
fd8b60 |
static char * ontty (void);
|
|
Packit |
fd8b60 |
static krb5_error_code init_ksu_context(krb5_context *);
|
|
Packit |
fd8b60 |
static krb5_error_code set_ccname_env(krb5_context, krb5_ccache);
|
|
Packit |
fd8b60 |
static void print_status( const char *fmt, ...)
|
|
Packit |
fd8b60 |
#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 7)
|
|
Packit |
fd8b60 |
__attribute__ ((__format__ (__printf__, 1, 2)))
|
|
Packit |
fd8b60 |
#endif
|
|
Packit |
fd8b60 |
;
|
|
Packit |
fd8b60 |
static krb5_error_code resolve_target_cache(krb5_context ksu_context,
|
|
Packit |
fd8b60 |
krb5_principal princ,
|
|
Packit |
fd8b60 |
krb5_ccache *ccache_out,
|
|
Packit |
fd8b60 |
krb5_boolean *ccache_reused);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* Note -e and -a options are mutually exclusive */
|
|
Packit |
fd8b60 |
/* insure the proper specification of target user as well as catching
|
|
Packit |
fd8b60 |
ill specified arguments to commands */
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
void usage (){
|
|
Packit |
fd8b60 |
fprintf(stderr,
|
|
Packit |
fd8b60 |
_("Usage: %s [target user] [-n principal] [-c source cachename] "
|
|
Packit |
fd8b60 |
"[-k] [-r time] [-p|-P] [-f|-F] [-l lifetime] [-zZ] [-q] "
|
|
Packit |
fd8b60 |
"[-e command [args... ] ] [-a [args... ] ]\n"), prog_name);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* for Ultrix and friends ... */
|
|
Packit |
fd8b60 |
#ifndef MAXHOSTNAMELEN
|
|
Packit |
fd8b60 |
#define MAXHOSTNAMELEN 64
|
|
Packit |
fd8b60 |
#endif
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* These are file static so sweep_up can get to them*/
|
|
Packit |
fd8b60 |
static uid_t source_uid, target_uid;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
int
|
|
Packit |
fd8b60 |
main (argc, argv)
|
|
Packit |
fd8b60 |
int argc;
|
|
Packit |
fd8b60 |
char ** argv;
|
|
Packit |
fd8b60 |
{
|
|
Packit |
fd8b60 |
int hp =0;
|
|
Packit |
fd8b60 |
int some_rest_copy = 0;
|
|
Packit |
fd8b60 |
int all_rest_copy = 0;
|
|
Packit |
fd8b60 |
char *localhostname = NULL;
|
|
Packit |
fd8b60 |
krb5_get_init_creds_opt *options = NULL;
|
|
Packit |
fd8b60 |
int option=0;
|
|
Packit |
fd8b60 |
int statusp=0;
|
|
Packit |
fd8b60 |
krb5_error_code retval = 0;
|
|
Packit |
fd8b60 |
krb5_principal client = NULL, tmp_princ = NULL;
|
|
Packit |
fd8b60 |
krb5_ccache cc_tmp = NULL, cc_target = NULL;
|
|
Packit |
fd8b60 |
krb5_context ksu_context;
|
|
Packit |
fd8b60 |
char * cc_target_tag = NULL;
|
|
Packit |
fd8b60 |
char * target_user = NULL;
|
|
Packit |
fd8b60 |
char * source_user;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
krb5_ccache cc_source = NULL;
|
|
Packit |
fd8b60 |
const char * cc_source_tag = NULL;
|
|
Packit |
fd8b60 |
const char * cc_source_tag_tmp = NULL;
|
|
Packit |
fd8b60 |
char * cmd = NULL, * exec_cmd = NULL;
|
|
Packit |
fd8b60 |
int errflg = 0;
|
|
Packit |
fd8b60 |
krb5_boolean auth_val;
|
|
Packit |
fd8b60 |
krb5_boolean authorization_val = FALSE;
|
|
Packit |
fd8b60 |
int path_passwd = 0;
|
|
Packit |
fd8b60 |
int done =0,i,j;
|
|
Packit |
fd8b60 |
uid_t ruid = getuid ();
|
|
Packit |
fd8b60 |
struct passwd *pwd=NULL, *target_pwd ;
|
|
Packit |
fd8b60 |
char * shell;
|
|
Packit |
fd8b60 |
char ** params;
|
|
Packit |
fd8b60 |
int keep_target_cache = 0;
|
|
Packit |
fd8b60 |
int child_pid, child_pgrp, ret_pid;
|
|
Packit |
fd8b60 |
extern char * getpass(), *crypt();
|
|
Packit |
fd8b60 |
int pargc;
|
|
Packit |
fd8b60 |
char ** pargv;
|
|
Packit |
fd8b60 |
krb5_boolean stored = FALSE, cc_reused = FALSE, given_princ = FALSE;
|
|
Packit |
fd8b60 |
krb5_boolean zero_password;
|
|
Packit |
fd8b60 |
krb5_boolean restrict_creds;
|
|
Packit |
fd8b60 |
krb5_deltat lifetime, rlife;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (argc == 0)
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
params = (char **) xcalloc (2, sizeof (char *));
|
|
Packit |
fd8b60 |
params[1] = NULL;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
unsetenv ("KRB5_CONFIG");
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
retval = init_ksu_context(&ksu_context);
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
com_err(argv[0], retval, _("while initializing krb5"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
retval = krb5_get_init_creds_opt_alloc(ksu_context, &options);
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
com_err(argv[0], retval, _("while initializing krb5"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (strrchr(argv[0], '/'))
|
|
Packit |
fd8b60 |
argv[0] = strrchr(argv[0], '/')+1;
|
|
Packit |
fd8b60 |
prog_name = argv[0];
|
|
Packit |
fd8b60 |
if (strlen (prog_name) > 50) {
|
|
Packit |
fd8b60 |
/* this many chars *after* last / ?? */
|
|
Packit |
fd8b60 |
com_err(prog_name, 0,
|
|
Packit |
fd8b60 |
_("program name too long - quitting to avoid triggering "
|
|
Packit |
fd8b60 |
"system logging bugs"));
|
|
Packit |
fd8b60 |
exit (1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
#ifndef LOG_NDELAY
|
|
Packit |
fd8b60 |
#define LOG_NDELAY 0
|
|
Packit |
fd8b60 |
#endif
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
#ifndef LOG_AUTH /* 4.2 syslog */
|
|
Packit |
fd8b60 |
openlog(prog_name, LOG_PID|LOG_NDELAY);
|
|
Packit |
fd8b60 |
#else
|
|
Packit |
fd8b60 |
openlog(prog_name, LOG_PID | LOG_NDELAY, LOG_AUTH);
|
|
Packit |
fd8b60 |
#endif /* 4.2 syslog */
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (( argc == 1) || (argv[1][0] == '-')){
|
|
Packit |
fd8b60 |
target_user = xstrdup("root");
|
|
Packit |
fd8b60 |
pargc = argc;
|
|
Packit |
fd8b60 |
pargv = argv;
|
|
Packit |
fd8b60 |
} else {
|
|
Packit |
fd8b60 |
target_user = xstrdup(argv[1]);
|
|
Packit |
fd8b60 |
pargc = argc -1;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if ((pargv =(char **) calloc(pargc +1,sizeof(char *)))==NULL){
|
|
Packit |
fd8b60 |
com_err(prog_name, errno, _("while allocating memory"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
pargv[pargc] = NULL;
|
|
Packit |
fd8b60 |
pargv[0] = argv[0];
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
for(i =1; i< pargc; i ++){
|
|
Packit |
fd8b60 |
pargv[i] = argv[i + 1];
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (krb5_seteuid (ruid)) {
|
|
Packit |
fd8b60 |
com_err (prog_name, errno, _("while setting euid to source user"));
|
|
Packit |
fd8b60 |
exit (1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
while (!done &&
|
|
Packit |
fd8b60 |
(option = getopt(pargc, pargv,"n:c:r:a:zZDfFpPkql:e:")) != -1) {
|
|
Packit |
fd8b60 |
switch (option) {
|
|
Packit |
fd8b60 |
case 'r':
|
|
Packit |
fd8b60 |
if (strlen (optarg) >= 14)
|
|
Packit |
fd8b60 |
optarg = "bad-time";
|
|
Packit |
fd8b60 |
retval = krb5_string_to_deltat(optarg, &rlife);
|
|
Packit |
fd8b60 |
if (retval != 0 || rlife == 0) {
|
|
Packit |
fd8b60 |
fprintf(stderr, _("Bad lifetime value (%s hours?)\n"), optarg);
|
|
Packit |
fd8b60 |
errflg++;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
krb5_get_init_creds_opt_set_renew_life(options, rlife);
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
case 'a':
|
|
Packit |
fd8b60 |
/* when integrating this remember to pass in pargc, pargv and
|
|
Packit |
fd8b60 |
take care of params argument */
|
|
Packit |
fd8b60 |
optind --;
|
|
Packit |
fd8b60 |
if (auth_debug){printf("Before get_params optind=%d\n", optind);}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if ((retval = get_params( & optind, pargc, pargv, ¶ms))){
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("when gathering parameters"));
|
|
Packit |
fd8b60 |
errflg++;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
if(auth_debug){ printf("After get_params optind=%d\n", optind);}
|
|
Packit |
fd8b60 |
done = 1;
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
case 'p':
|
|
Packit |
fd8b60 |
krb5_get_init_creds_opt_set_proxiable(options, 1);
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
case 'P':
|
|
Packit |
fd8b60 |
krb5_get_init_creds_opt_set_proxiable(options, 0);
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
case 'f':
|
|
Packit |
fd8b60 |
krb5_get_init_creds_opt_set_forwardable(options, 1);
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
case 'F':
|
|
Packit |
fd8b60 |
krb5_get_init_creds_opt_set_forwardable(options, 0);
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
case 'k':
|
|
Packit |
fd8b60 |
keep_target_cache =1;
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
case 'q':
|
|
Packit |
fd8b60 |
quiet =1;
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
case 'l':
|
|
Packit |
fd8b60 |
if (strlen (optarg) >= 14)
|
|
Packit |
fd8b60 |
optarg = "bad-time";
|
|
Packit |
fd8b60 |
retval = krb5_string_to_deltat(optarg, &lifetime);
|
|
Packit |
fd8b60 |
if (retval != 0 || lifetime == 0) {
|
|
Packit |
fd8b60 |
fprintf(stderr, _("Bad lifetime value (%s hours?)\n"), optarg);
|
|
Packit |
fd8b60 |
errflg++;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
krb5_get_init_creds_opt_set_tkt_life(options, lifetime);
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
case 'n':
|
|
Packit |
fd8b60 |
if ((retval = krb5_parse_name(ksu_context, optarg, &client))){
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("when parsing name %s"), optarg);
|
|
Packit |
fd8b60 |
errflg++;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
given_princ = TRUE;
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
#ifdef DEBUG
|
|
Packit |
fd8b60 |
case 'D':
|
|
Packit |
fd8b60 |
auth_debug = 1;
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
#endif
|
|
Packit |
fd8b60 |
case 'z':
|
|
Packit |
fd8b60 |
some_rest_copy = 1;
|
|
Packit |
fd8b60 |
if(all_rest_copy) {
|
|
Packit |
fd8b60 |
fprintf(stderr,
|
|
Packit |
fd8b60 |
_("-z option is mutually exclusive with -Z.\n"));
|
|
Packit |
fd8b60 |
errflg++;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
case 'Z':
|
|
Packit |
fd8b60 |
all_rest_copy = 1;
|
|
Packit |
fd8b60 |
if(some_rest_copy) {
|
|
Packit |
fd8b60 |
fprintf(stderr,
|
|
Packit |
fd8b60 |
_("-Z option is mutually exclusive with -z.\n"));
|
|
Packit |
fd8b60 |
errflg++;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
case 'c':
|
|
Packit |
fd8b60 |
if (cc_source_tag == NULL) {
|
|
Packit |
fd8b60 |
cc_source_tag = xstrdup(optarg);
|
|
Packit |
fd8b60 |
if ( strchr(cc_source_tag, ':')){
|
|
Packit |
fd8b60 |
cc_source_tag_tmp = strchr(cc_source_tag, ':') + 1;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (!ks_ccache_name_is_initialized(ksu_context,
|
|
Packit |
fd8b60 |
cc_source_tag)) {
|
|
Packit |
fd8b60 |
com_err(prog_name, errno,
|
|
Packit |
fd8b60 |
_("while looking for credentials cache %s"),
|
|
Packit |
fd8b60 |
cc_source_tag_tmp);
|
|
Packit |
fd8b60 |
exit (1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
else {
|
|
Packit |
fd8b60 |
fprintf(stderr, _("malformed credential cache name %s\n"),
|
|
Packit |
fd8b60 |
cc_source_tag);
|
|
Packit |
fd8b60 |
errflg++;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
} else {
|
|
Packit |
fd8b60 |
fprintf(stderr, _("Only one -c option allowed\n"));
|
|
Packit |
fd8b60 |
errflg++;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
case 'e':
|
|
Packit |
fd8b60 |
cmd = xstrdup(optarg);
|
|
Packit |
fd8b60 |
if(auth_debug){printf("Before get_params optind=%d\n", optind);}
|
|
Packit |
fd8b60 |
if ((retval = get_params( & optind, pargc, pargv, ¶ms))){
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("when gathering parameters"));
|
|
Packit |
fd8b60 |
errflg++;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
if(auth_debug){printf("After get_params optind=%d\n", optind);}
|
|
Packit |
fd8b60 |
done = 1;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (auth_debug){
|
|
Packit |
fd8b60 |
fprintf(stderr,"Command to be executed: %s\n", cmd);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
case '?':
|
|
Packit |
fd8b60 |
default:
|
|
Packit |
fd8b60 |
errflg++;
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (errflg) {
|
|
Packit |
fd8b60 |
usage();
|
|
Packit |
fd8b60 |
exit(2);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (optind != pargc ){
|
|
Packit |
fd8b60 |
usage();
|
|
Packit |
fd8b60 |
exit(2);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (auth_debug){
|
|
Packit |
fd8b60 |
for(j=1; params[j] != NULL; j++){
|
|
Packit |
fd8b60 |
fprintf (stderr,"params[%d]= %s\n", j,params[j]);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/***********************************/
|
|
Packit |
fd8b60 |
source_user = getlogin(); /*checks for the the login name in /etc/utmp*/
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* verify that that the user exists and get his passwd structure */
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (source_user == NULL ||(pwd = getpwnam(source_user)) == NULL ||
|
|
Packit |
fd8b60 |
pwd->pw_uid != ruid){
|
|
Packit |
fd8b60 |
pwd = getpwuid(ruid);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (pwd == NULL) {
|
|
Packit |
fd8b60 |
fprintf(stderr, _("ksu: who are you?\n"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
if (pwd->pw_uid != ruid) {
|
|
Packit |
fd8b60 |
fprintf (stderr, _("Your uid doesn't match your passwd entry?!\n"));
|
|
Packit |
fd8b60 |
exit (1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
/* Okay, now we have *some* passwd entry that matches the
|
|
Packit |
fd8b60 |
current real uid. */
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* allocate space and copy the usernamane there */
|
|
Packit |
fd8b60 |
source_user = xstrdup(pwd->pw_name);
|
|
Packit |
fd8b60 |
source_uid = pwd->pw_uid;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (!strcmp(SOURCE_USER_LOGIN, target_user)){
|
|
Packit |
fd8b60 |
target_user = xstrdup (source_user);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if ((target_pwd = getpwnam(target_user)) == NULL){
|
|
Packit |
fd8b60 |
fprintf(stderr, _("ksu: unknown login %s\n"), target_user);
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
target_uid = target_pwd->pw_uid;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
init_auth_names(target_pwd->pw_dir);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/***********************************/
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (cc_source_tag == NULL){
|
|
Packit |
fd8b60 |
cc_source_tag = krb5_cc_default_name(ksu_context);
|
|
Packit |
fd8b60 |
cc_source_tag_tmp = strchr(cc_source_tag, ':');
|
|
Packit |
fd8b60 |
if (cc_source_tag_tmp == 0)
|
|
Packit |
fd8b60 |
cc_source_tag_tmp = cc_source_tag;
|
|
Packit |
fd8b60 |
else
|
|
Packit |
fd8b60 |
cc_source_tag_tmp++;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* get a handle for the cache */
|
|
Packit |
fd8b60 |
if ((retval = krb5_cc_resolve(ksu_context, cc_source_tag, &cc_source))){
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("while getting source cache"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if ((retval = get_best_princ_for_target(ksu_context, source_uid,
|
|
Packit |
fd8b60 |
target_uid, source_user,
|
|
Packit |
fd8b60 |
target_user, cc_source,
|
|
Packit |
fd8b60 |
options, cmd, localhostname,
|
|
Packit |
fd8b60 |
&client, &hp))){
|
|
Packit |
fd8b60 |
com_err(prog_name,retval, _("while selecting the best principal"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* We may be running as either source or target, depending on
|
|
Packit |
fd8b60 |
what happened; become source.*/
|
|
Packit |
fd8b60 |
if ( geteuid() != source_uid) {
|
|
Packit |
fd8b60 |
if (krb5_seteuid(0) || krb5_seteuid(source_uid) ) {
|
|
Packit |
fd8b60 |
com_err(prog_name, errno, _("while returning to source uid after "
|
|
Packit |
fd8b60 |
"finding best principal"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (auth_debug){
|
|
Packit |
fd8b60 |
if (hp){
|
|
Packit |
fd8b60 |
fprintf(stderr,
|
|
Packit |
fd8b60 |
"GET_best_princ_for_target result: NOT AUTHORIZED\n");
|
|
Packit |
fd8b60 |
}else{
|
|
Packit |
fd8b60 |
fprintf(stderr,
|
|
Packit |
fd8b60 |
"GET_best_princ_for_target result-best principal ");
|
|
Packit |
fd8b60 |
plain_dump_principal (ksu_context, client);
|
|
Packit |
fd8b60 |
fprintf(stderr,"\n");
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (hp){
|
|
Packit |
fd8b60 |
if (gb_err) fprintf(stderr, "%s", gb_err);
|
|
Packit |
fd8b60 |
fprintf(stderr, _("account %s: authorization failed\n"), target_user);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (cmd != NULL) {
|
|
Packit |
fd8b60 |
syslog(LOG_WARNING,
|
|
Packit |
fd8b60 |
"Account %s: authorization for %s for execution of %s failed",
|
|
Packit |
fd8b60 |
target_user, source_user, cmd);
|
|
Packit |
fd8b60 |
} else {
|
|
Packit |
fd8b60 |
syslog(LOG_WARNING, "Account %s: authorization of %s failed",
|
|
Packit |
fd8b60 |
target_user, source_user);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (auth_debug)
|
|
Packit |
fd8b60 |
fprintf(stderr, " source cache = %s\n", cc_source_tag);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/*
|
|
Packit |
fd8b60 |
* After proper authentication and authorization, populate a cache for the
|
|
Packit |
fd8b60 |
* target user.
|
|
Packit |
fd8b60 |
*/
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/*
|
|
Packit |
fd8b60 |
* We read the set of creds we want to copy from the source ccache as the
|
|
Packit |
fd8b60 |
* source uid, become root for authentication, and then become the target
|
|
Packit |
fd8b60 |
* user to handle authorization and creating the target user's cache.
|
|
Packit |
fd8b60 |
*/
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* if root ksu's to a regular user, then
|
|
Packit |
fd8b60 |
then only the credentials for that particular user
|
|
Packit |
fd8b60 |
should be copied */
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
restrict_creds = (source_uid == 0) && (target_uid != 0);
|
|
Packit |
fd8b60 |
retval = krb5_parse_name(ksu_context, KS_TEMPORARY_PRINC, &tmp_princ);
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("while parsing temporary name"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
retval = krb5_cc_resolve(ksu_context, KS_TEMPORARY_CACHE, &cc_tmp);
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("while creating temporary cache"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
retval = krb5_ccache_copy(ksu_context, cc_source, tmp_princ, cc_tmp,
|
|
Packit |
fd8b60 |
restrict_creds, client, &stored);
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("while copying cache %s to %s"),
|
|
Packit |
fd8b60 |
krb5_cc_get_name(ksu_context, cc_source), KS_TEMPORARY_CACHE);
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
krb5_cc_close(ksu_context, cc_source);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
krb5_get_init_creds_opt_set_out_ccache(ksu_context, options, cc_tmp);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* Become root for authentication*/
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (krb5_seteuid(0)) {
|
|
Packit |
fd8b60 |
com_err(prog_name, errno, _("while reclaiming root uid"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if ((source_uid == 0) || (target_uid == source_uid)){
|
|
Packit |
fd8b60 |
#ifdef GET_TGT_VIA_PASSWD
|
|
Packit |
fd8b60 |
if (!all_rest_copy && given_princ && client != NULL && !stored) {
|
|
Packit |
fd8b60 |
fprintf(stderr, _("WARNING: Your password may be exposed if you "
|
|
Packit |
fd8b60 |
"enter it here and are logged\n"));
|
|
Packit |
fd8b60 |
fprintf(stderr, _(" in remotely using an unsecure "
|
|
Packit |
fd8b60 |
"(non-encrypted) channel.\n"));
|
|
Packit |
fd8b60 |
if (ksu_get_tgt_via_passwd(ksu_context, client, options,
|
|
Packit |
fd8b60 |
&zero_password, NULL) == FALSE) {
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (zero_password == FALSE){
|
|
Packit |
fd8b60 |
fprintf(stderr, _("Goodbye\n"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
fprintf(stderr, _("Could not get a tgt for "));
|
|
Packit |
fd8b60 |
plain_dump_principal (ksu_context, client);
|
|
Packit |
fd8b60 |
fprintf(stderr, "\n");
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
stored = TRUE;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
#endif /* GET_TGT_VIA_PASSWD */
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* if the user is root or same uid then authentication is not neccesary,
|
|
Packit |
fd8b60 |
root gets in automatically */
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (source_uid && (source_uid != target_uid)) {
|
|
Packit |
fd8b60 |
char * client_name;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
auth_val = krb5_auth_check(ksu_context, client, localhostname,
|
|
Packit |
fd8b60 |
options, target_user, cc_tmp,
|
|
Packit |
fd8b60 |
&path_passwd, target_uid);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* if Kerberos authentication failed then exit */
|
|
Packit |
fd8b60 |
if (auth_val ==FALSE){
|
|
Packit |
fd8b60 |
fprintf(stderr, _("Authentication failed.\n"));
|
|
Packit |
fd8b60 |
syslog(LOG_WARNING, "'%s %s' authentication failed for %s%s",
|
|
Packit |
fd8b60 |
prog_name,target_user,source_user,ontty());
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
stored = TRUE;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if ((retval = krb5_unparse_name(ksu_context, client, &client_name))) {
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("When unparsing name"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
print_status(_("Authenticated %s\n"), client_name);
|
|
Packit |
fd8b60 |
syslog(LOG_NOTICE,"'%s %s' authenticated %s for %s%s",
|
|
Packit |
fd8b60 |
prog_name,target_user,client_name,
|
|
Packit |
fd8b60 |
source_user,ontty());
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* Run authorization as target.*/
|
|
Packit |
fd8b60 |
if (krb5_seteuid(target_uid)) {
|
|
Packit |
fd8b60 |
com_err(prog_name, errno, _("while switching to target for "
|
|
Packit |
fd8b60 |
"authorization check"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if ((retval = krb5_authorization(ksu_context, client,target_user,
|
|
Packit |
fd8b60 |
cmd, &authorization_val, &exec_cmd))){
|
|
Packit |
fd8b60 |
com_err(prog_name,retval, _("while checking authorization"));
|
|
Packit |
fd8b60 |
krb5_seteuid(0); /*So we have some chance of sweeping up*/
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (krb5_seteuid(0)) {
|
|
Packit |
fd8b60 |
com_err(prog_name, errno, _("while switching back from target "
|
|
Packit |
fd8b60 |
"after authorization check"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
if (authorization_val == TRUE){
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (cmd) {
|
|
Packit |
fd8b60 |
print_status(_("Account %s: authorization for %s for "
|
|
Packit |
fd8b60 |
"execution of\n"), target_user, client_name);
|
|
Packit |
fd8b60 |
print_status(_(" %s successful\n"), exec_cmd);
|
|
Packit |
fd8b60 |
syslog(LOG_NOTICE,
|
|
Packit |
fd8b60 |
"Account %s: authorization for %s for execution of %s successful",
|
|
Packit |
fd8b60 |
target_user, client_name, exec_cmd);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
}else{
|
|
Packit |
fd8b60 |
print_status(_("Account %s: authorization for %s "
|
|
Packit |
fd8b60 |
"successful\n"), target_user, client_name);
|
|
Packit |
fd8b60 |
syslog(LOG_NOTICE,
|
|
Packit |
fd8b60 |
"Account %s: authorization for %s successful",
|
|
Packit |
fd8b60 |
target_user, client_name);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}else {
|
|
Packit |
fd8b60 |
if (cmd){
|
|
Packit |
fd8b60 |
if (exec_cmd){ /* was used to pass back the error msg */
|
|
Packit |
fd8b60 |
fprintf(stderr, "%s", exec_cmd );
|
|
Packit |
fd8b60 |
syslog(LOG_WARNING, "%s",exec_cmd);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
fprintf(stderr, _("Account %s: authorization for %s for "
|
|
Packit |
fd8b60 |
"execution of %s failed\n"),
|
|
Packit |
fd8b60 |
target_user, client_name, cmd );
|
|
Packit |
fd8b60 |
syslog(LOG_WARNING,
|
|
Packit |
fd8b60 |
"Account %s: authorization for %s for execution of %s failed",
|
|
Packit |
fd8b60 |
target_user, client_name, cmd );
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
}else{
|
|
Packit |
fd8b60 |
fprintf(stderr, _("Account %s: authorization of %s failed\n"),
|
|
Packit |
fd8b60 |
target_user, client_name);
|
|
Packit |
fd8b60 |
syslog(LOG_WARNING,
|
|
Packit |
fd8b60 |
"Account %s: authorization of %s failed",
|
|
Packit |
fd8b60 |
target_user, client_name);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if( some_rest_copy){
|
|
Packit |
fd8b60 |
retval = krb5_ccache_filter(ksu_context, cc_tmp, client);
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
com_err(prog_name,retval, _("while calling cc_filter"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (all_rest_copy){
|
|
Packit |
fd8b60 |
retval = krb5_cc_initialize(ksu_context, cc_tmp, tmp_princ);
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("while erasing target cache"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
stored = FALSE;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* get the shell of the user, this will be the shell used by su */
|
|
Packit |
fd8b60 |
target_pwd = getpwnam(target_user);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (target_pwd->pw_shell)
|
|
Packit |
fd8b60 |
shell = xstrdup(target_pwd->pw_shell);
|
|
Packit |
fd8b60 |
else {
|
|
Packit |
fd8b60 |
shell = _DEF_CSH; /* default is cshell */
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
#ifdef HAVE_GETUSERSHELL
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* insist that the target login uses a standard shell (root is omited) */
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (!standard_shell(target_pwd->pw_shell) && source_uid) {
|
|
Packit |
fd8b60 |
fprintf(stderr, _("ksu: permission denied (shell).\n"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
#endif /* HAVE_GETUSERSHELL */
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (target_pwd->pw_uid){
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if(set_env_var("USER", target_pwd->pw_name)){
|
|
Packit |
fd8b60 |
fprintf(stderr,
|
|
Packit |
fd8b60 |
_("ksu: couldn't set environment variable USER\n"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if(set_env_var( "HOME", target_pwd->pw_dir)){
|
|
Packit |
fd8b60 |
fprintf(stderr, _("ksu: couldn't set environment variable HOME\n"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if(set_env_var( "SHELL", shell)){
|
|
Packit |
fd8b60 |
fprintf(stderr, _("ksu: couldn't set environment variable SHELL\n"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* set permissions */
|
|
Packit |
fd8b60 |
if (setgid(target_pwd->pw_gid) < 0) {
|
|
Packit |
fd8b60 |
perror("ksu: setgid");
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (initgroups(target_user, target_pwd->pw_gid)) {
|
|
Packit |
fd8b60 |
fprintf(stderr, _("ksu: initgroups failed.\n"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if ( ! strcmp(target_user, source_user)){
|
|
Packit |
fd8b60 |
print_status(_("Leaving uid as %s (%ld)\n"),
|
|
Packit |
fd8b60 |
target_user, (long) target_pwd->pw_uid);
|
|
Packit |
fd8b60 |
}else{
|
|
Packit |
fd8b60 |
print_status(_("Changing uid to %s (%ld)\n"),
|
|
Packit |
fd8b60 |
target_user, (long) target_pwd->pw_uid);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
#ifdef HAVE_SETLUID
|
|
Packit |
fd8b60 |
/*
|
|
Packit |
fd8b60 |
* If we're on a system which keeps track of login uids, then
|
|
Packit |
fd8b60 |
* set the login uid. If this fails this opens up a problem on DEC OSF
|
|
Packit |
fd8b60 |
* with C2 enabled.
|
|
Packit |
fd8b60 |
*/
|
|
Packit |
fd8b60 |
if (setluid((uid_t) pwd->pw_uid) < 0) {
|
|
Packit |
fd8b60 |
perror("setluid");
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
#endif /* HAVE_SETLUID */
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (setuid(target_pwd->pw_uid) < 0) {
|
|
Packit |
fd8b60 |
perror("ksu: setuid");
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
retval = resolve_target_cache(ksu_context, client, &cc_target, &cc_reused);
|
|
Packit |
fd8b60 |
if (retval)
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
retval = krb5_cc_get_full_name(ksu_context, cc_target, &cc_target_tag);
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("while getting name of target ccache"));
|
|
Packit |
fd8b60 |
sweep_up(ksu_context, cc_target);
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
if (auth_debug)
|
|
Packit |
fd8b60 |
fprintf(stderr, " target cache = %s\n", cc_target_tag);
|
|
Packit |
fd8b60 |
if (cc_reused)
|
|
Packit |
fd8b60 |
keep_target_cache = TRUE;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (stored) {
|
|
Packit |
fd8b60 |
retval = krb5_ccache_copy(ksu_context, cc_tmp, client, cc_target,
|
|
Packit |
fd8b60 |
FALSE, client, &stored);
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("while copying cache %s to %s"),
|
|
Packit |
fd8b60 |
KS_TEMPORARY_CACHE, cc_target_tag);
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (!ks_ccache_is_initialized(ksu_context, cc_target)) {
|
|
Packit |
fd8b60 |
com_err(prog_name, errno,
|
|
Packit |
fd8b60 |
_("%s does not have correct permissions for %s, "
|
|
Packit |
fd8b60 |
"%s aborted"), target_user, cc_target_tag, prog_name);
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
krb5_free_string(ksu_context, cc_target_tag);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* Set the cc env name to target. */
|
|
Packit |
fd8b60 |
retval = set_ccname_env(ksu_context, cc_target);
|
|
Packit |
fd8b60 |
if (retval != 0) {
|
|
Packit |
fd8b60 |
sweep_up(ksu_context, cc_target);
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (cmd){
|
|
Packit |
fd8b60 |
if ((source_uid == 0) || (source_uid == target_uid )){
|
|
Packit |
fd8b60 |
exec_cmd = cmd;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if( !exec_cmd){
|
|
Packit |
fd8b60 |
fprintf(stderr, _("Internal error: command %s did not get "
|
|
Packit |
fd8b60 |
"resolved\n"), cmd);
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
params[0] = exec_cmd;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
else{
|
|
Packit |
fd8b60 |
params[0] = shell;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (auth_debug){
|
|
Packit |
fd8b60 |
fprintf(stderr, "program to be execed %s\n",params[0]);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit Service |
a81408 |
if( keep_target_cache ) {
|
|
Packit |
fd8b60 |
execv(params[0], params);
|
|
Packit |
fd8b60 |
com_err(prog_name, errno, _("while trying to execv %s"), params[0]);
|
|
Packit |
fd8b60 |
sweep_up(ksu_context, cc_target);
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}else{
|
|
Packit |
fd8b60 |
statusp = 1;
|
|
Packit |
fd8b60 |
switch ((child_pid = fork())) {
|
|
Packit |
fd8b60 |
default:
|
|
Packit |
fd8b60 |
if (auth_debug){
|
|
Packit |
fd8b60 |
printf(" The child pid is %ld\n", (long) child_pid);
|
|
Packit |
fd8b60 |
printf(" The parent pid is %ld\n", (long) getpid());
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
while ((ret_pid = waitpid(child_pid, &statusp, WUNTRACED)) != -1) {
|
|
Packit |
fd8b60 |
if (WIFSTOPPED(statusp)) {
|
|
Packit |
fd8b60 |
child_pgrp = tcgetpgrp(1);
|
|
Packit |
fd8b60 |
kill(getpid(), SIGSTOP);
|
|
Packit |
fd8b60 |
tcsetpgrp(1, child_pgrp);
|
|
Packit |
fd8b60 |
kill(child_pid, SIGCONT);
|
|
Packit |
fd8b60 |
statusp = 1;
|
|
Packit |
fd8b60 |
continue;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
break;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
if (auth_debug){
|
|
Packit |
fd8b60 |
printf("The exit status of the child is %d\n", statusp);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
if (ret_pid == -1) {
|
|
Packit |
fd8b60 |
com_err(prog_name, errno, _("while calling waitpid"));
|
|
Packit |
fd8b60 |
}
|
|
Packit Service |
a81408 |
sweep_up(ksu_context, cc_target);
|
|
Packit |
fd8b60 |
exit (statusp);
|
|
Packit |
fd8b60 |
case -1:
|
|
Packit |
fd8b60 |
com_err(prog_name, errno, _("while trying to fork."));
|
|
Packit |
fd8b60 |
sweep_up(ksu_context, cc_target);
|
|
Packit |
fd8b60 |
exit (1);
|
|
Packit |
fd8b60 |
case 0:
|
|
Packit |
fd8b60 |
execv(params[0], params);
|
|
Packit |
fd8b60 |
com_err(prog_name, errno, _("while trying to execv %s"),
|
|
Packit |
fd8b60 |
params[0]);
|
|
Packit |
fd8b60 |
exit (1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
static krb5_error_code
|
|
Packit |
fd8b60 |
init_ksu_context(krb5_context *context_out)
|
|
Packit |
fd8b60 |
{
|
|
Packit |
fd8b60 |
krb5_error_code retval;
|
|
Packit |
fd8b60 |
const char *env_ccname;
|
|
Packit |
fd8b60 |
krb5_context context;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
*context_out = NULL;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
retval = krb5_init_secure_context(&context);
|
|
Packit |
fd8b60 |
if (retval)
|
|
Packit |
fd8b60 |
return retval;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* We want to obey KRB5CCNAME in this context even though this is a setuid
|
|
Packit |
fd8b60 |
* program. (It will only be used when operating as the real uid.) */
|
|
Packit |
fd8b60 |
env_ccname = getenv(KRB5_ENV_CCNAME);
|
|
Packit |
fd8b60 |
if (env_ccname != NULL) {
|
|
Packit |
fd8b60 |
retval = krb5_cc_set_default_name(context, env_ccname);
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
krb5_free_context(context);
|
|
Packit |
fd8b60 |
return retval;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
*context_out = context;
|
|
Packit |
fd8b60 |
return 0;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* Set KRB5CCNAME in the environment to point to ccache. Print an error
|
|
Packit |
fd8b60 |
* message on failure. */
|
|
Packit |
fd8b60 |
static krb5_error_code
|
|
Packit |
fd8b60 |
set_ccname_env(krb5_context ksu_context, krb5_ccache ccache)
|
|
Packit |
fd8b60 |
{
|
|
Packit |
fd8b60 |
krb5_error_code retval;
|
|
Packit |
fd8b60 |
char *ccname;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
retval = krb5_cc_get_full_name(ksu_context, ccache, &ccname);
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("while reading cache name from ccache"));
|
|
Packit |
fd8b60 |
return retval;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
if (set_env_var(KRB5_ENV_CCNAME, ccname)) {
|
|
Packit |
fd8b60 |
retval = errno;
|
|
Packit |
fd8b60 |
fprintf(stderr,
|
|
Packit |
fd8b60 |
_("ksu: couldn't set environment variable %s\n"),
|
|
Packit |
fd8b60 |
KRB5_ENV_CCNAME);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
krb5_free_string(ksu_context, ccname);
|
|
Packit |
fd8b60 |
return retval;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/*
|
|
Packit |
fd8b60 |
* Get the configured default ccache name. Unset KRB5CCNAME and force a
|
|
Packit |
fd8b60 |
* recomputation so we don't use values for the source user. Print an error
|
|
Packit |
fd8b60 |
* message on failure.
|
|
Packit |
fd8b60 |
*/
|
|
Packit |
fd8b60 |
static krb5_error_code
|
|
Packit |
fd8b60 |
get_configured_defccname(krb5_context context, char **target_out)
|
|
Packit |
fd8b60 |
{
|
|
Packit |
fd8b60 |
krb5_error_code retval;
|
|
Packit |
fd8b60 |
const char *defname;
|
|
Packit |
fd8b60 |
char *target = NULL;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
*target_out = NULL;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
unsetenv(KRB5_ENV_CCNAME);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* Make sure we don't have a cached value for a different uid. */
|
|
Packit |
fd8b60 |
retval = krb5_cc_set_default_name(context, NULL);
|
|
Packit |
fd8b60 |
if (retval != 0) {
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("while resetting target ccache name"));
|
|
Packit |
fd8b60 |
return retval;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
defname = krb5_cc_default_name(context);
|
|
Packit |
fd8b60 |
if (defname != NULL) {
|
|
Packit |
fd8b60 |
if (strchr(defname, ':') != NULL) {
|
|
Packit |
fd8b60 |
target = strdup(defname);
|
|
Packit |
fd8b60 |
} else {
|
|
Packit |
fd8b60 |
if (asprintf(&target, "FILE:%s", defname) < 0)
|
|
Packit |
fd8b60 |
target = NULL;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
if (target == NULL) {
|
|
Packit |
fd8b60 |
com_err(prog_name, ENOMEM, _("while determining target ccache name"));
|
|
Packit |
fd8b60 |
return ENOMEM;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
*target_out = target;
|
|
Packit |
fd8b60 |
return 0;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* Determine where the target user's creds should be stored. Print an error
|
|
Packit |
fd8b60 |
* message on failure. */
|
|
Packit |
fd8b60 |
static krb5_error_code
|
|
Packit |
fd8b60 |
resolve_target_cache(krb5_context context, krb5_principal princ,
|
|
Packit |
fd8b60 |
krb5_ccache *ccache_out, krb5_boolean *ccache_reused)
|
|
Packit |
fd8b60 |
{
|
|
Packit |
fd8b60 |
krb5_error_code retval;
|
|
Packit |
fd8b60 |
krb5_boolean switchable, reused = FALSE;
|
|
Packit |
fd8b60 |
krb5_ccache ccache = NULL;
|
|
Packit |
fd8b60 |
char *sep, *ccname = NULL, *sym = NULL, *target;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
*ccache_out = NULL;
|
|
Packit |
fd8b60 |
*ccache_reused = FALSE;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
retval = get_configured_defccname(context, &target);
|
|
Packit |
fd8b60 |
if (retval != 0)
|
|
Packit |
fd8b60 |
return retval;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/* Check if the configured default name uses a switchable type. */
|
|
Packit |
fd8b60 |
sep = strchr(target, ':');
|
|
Packit |
fd8b60 |
*sep = '\0';
|
|
Packit |
fd8b60 |
switchable = krb5_cc_support_switch(context, target);
|
|
Packit |
fd8b60 |
*sep = ':';
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (!switchable) {
|
|
Packit |
fd8b60 |
/* Try to avoid destroying an in-use target ccache by coming up with
|
|
Packit |
fd8b60 |
* the name of a cache that doesn't exist yet. */
|
|
Packit |
fd8b60 |
do {
|
|
Packit |
fd8b60 |
free(ccname);
|
|
Packit |
fd8b60 |
retval = gen_sym(context, &sym);
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
com_err(prog_name, retval,
|
|
Packit |
fd8b60 |
_("while generating part of the target ccache name"));
|
|
Packit |
fd8b60 |
return retval;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
if (asprintf(&ccname, "%s.%s", target, sym) < 0) {
|
|
Packit |
fd8b60 |
retval = ENOMEM;
|
|
Packit |
fd8b60 |
free(sym);
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("while allocating memory for the "
|
|
Packit |
fd8b60 |
"target ccache name"));
|
|
Packit |
fd8b60 |
goto cleanup;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
free(sym);
|
|
Packit |
fd8b60 |
} while (ks_ccache_name_is_initialized(context, ccname));
|
|
Packit |
fd8b60 |
retval = krb5_cc_resolve(context, ccname, &ccache);
|
|
Packit |
fd8b60 |
} else {
|
|
Packit |
fd8b60 |
/* Look for a cache in the collection that we can reuse. */
|
|
Packit |
fd8b60 |
retval = krb5_cc_cache_match(context, princ, &ccache);
|
|
Packit |
fd8b60 |
if (retval == 0) {
|
|
Packit |
fd8b60 |
reused = TRUE;
|
|
Packit |
fd8b60 |
} else {
|
|
Packit |
fd8b60 |
/* There isn't one, so create a new one. */
|
|
Packit |
fd8b60 |
*sep = '\0';
|
|
Packit |
fd8b60 |
retval = krb5_cc_new_unique(context, target, NULL, &ccache);
|
|
Packit |
fd8b60 |
*sep = ':';
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
com_err(prog_name, retval,
|
|
Packit |
fd8b60 |
_("while creating new target ccache"));
|
|
Packit |
fd8b60 |
goto cleanup;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
retval = krb5_cc_initialize(context, ccache, princ);
|
|
Packit |
fd8b60 |
if (retval) {
|
|
Packit |
fd8b60 |
com_err(prog_name, retval,
|
|
Packit |
fd8b60 |
_("while initializing target cache"));
|
|
Packit |
fd8b60 |
goto cleanup;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
*ccache_out = ccache;
|
|
Packit |
fd8b60 |
*ccache_reused = reused;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
cleanup:
|
|
Packit |
fd8b60 |
free(target);
|
|
Packit |
fd8b60 |
return retval;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
#ifdef HAVE_GETUSERSHELL
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
int standard_shell(sh)
|
|
Packit |
fd8b60 |
char *sh;
|
|
Packit |
fd8b60 |
{
|
|
Packit |
fd8b60 |
char *cp;
|
|
Packit |
fd8b60 |
char *getusershell();
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
while ((cp = getusershell()) != NULL)
|
|
Packit |
fd8b60 |
if (!strcmp(cp, sh))
|
|
Packit |
fd8b60 |
return (1);
|
|
Packit |
fd8b60 |
return (0);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
#endif /* HAVE_GETUSERSHELL */
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
static char * ontty()
|
|
Packit |
fd8b60 |
{
|
|
Packit |
fd8b60 |
char *p;
|
|
Packit |
fd8b60 |
static char buf[MAXPATHLEN + 5];
|
|
Packit |
fd8b60 |
int result;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
buf[0] = 0;
|
|
Packit |
fd8b60 |
if ((p = ttyname(STDERR_FILENO))) {
|
|
Packit |
fd8b60 |
result = snprintf(buf, sizeof(buf), " on %s", p);
|
|
Packit |
fd8b60 |
if (SNPRINTF_OVERFLOW(result, sizeof(buf))) {
|
|
Packit |
fd8b60 |
fprintf(stderr, _("terminal name %s too long\n"), p);
|
|
Packit |
fd8b60 |
exit (1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
return (buf);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
static int set_env_var(name, value)
|
|
Packit |
fd8b60 |
char *name;
|
|
Packit |
fd8b60 |
char *value;
|
|
Packit |
fd8b60 |
{
|
|
Packit |
fd8b60 |
char * env_var_buf;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
asprintf(&env_var_buf,"%s=%s",name, value);
|
|
Packit |
fd8b60 |
return putenv(env_var_buf);
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
static void sweep_up(context, cc)
|
|
Packit |
fd8b60 |
krb5_context context;
|
|
Packit |
fd8b60 |
krb5_ccache cc;
|
|
Packit |
fd8b60 |
{
|
|
Packit |
fd8b60 |
krb5_error_code retval;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
krb5_seteuid(0);
|
|
Packit |
fd8b60 |
if (krb5_seteuid(target_uid) < 0) {
|
|
Packit |
fd8b60 |
com_err(prog_name, errno,
|
|
Packit |
fd8b60 |
_("while changing to target uid for destroying ccache"));
|
|
Packit |
fd8b60 |
exit(1);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if (ks_ccache_is_initialized(context, cc)) {
|
|
Packit |
fd8b60 |
if ((retval = krb5_cc_destroy(context, cc)))
|
|
Packit |
fd8b60 |
com_err(prog_name, retval, _("while destroying cache"));
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
/*****************************************************************
|
|
Packit |
fd8b60 |
get_params is to be called for the -a option or -e option to
|
|
Packit |
fd8b60 |
collect all params passed in for the shell or for
|
|
Packit |
fd8b60 |
cmd. An aray is returned containing all params.
|
|
Packit |
fd8b60 |
optindex is incremented accordingly and the first
|
|
Packit |
fd8b60 |
element in the returned array is reserved for the
|
|
Packit |
fd8b60 |
name of the command to be executed or the name of the
|
|
Packit |
fd8b60 |
shell.
|
|
Packit |
fd8b60 |
*****************************************************************/
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
krb5_error_code
|
|
Packit |
fd8b60 |
get_params(optindex, pargc, pargv, params)
|
|
Packit |
fd8b60 |
int *optindex;
|
|
Packit |
fd8b60 |
int pargc;
|
|
Packit |
fd8b60 |
char **pargv;
|
|
Packit |
fd8b60 |
char ***params;
|
|
Packit |
fd8b60 |
{
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
int i,j;
|
|
Packit |
fd8b60 |
char ** ret_params;
|
|
Packit |
fd8b60 |
int size = pargc - *optindex + 2;
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
if ((ret_params = (char **) calloc(size, sizeof (char *)))== NULL ){
|
|
Packit |
fd8b60 |
return ENOMEM;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
for (i = *optindex, j=1; i < pargc; i++,j++){
|
|
Packit |
fd8b60 |
ret_params[j] = pargv[i];
|
|
Packit |
fd8b60 |
*optindex = *optindex + 1;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
ret_params[size-1] = NULL;
|
|
Packit |
fd8b60 |
*params = ret_params;
|
|
Packit |
fd8b60 |
return 0;
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
static
|
|
Packit |
fd8b60 |
void print_status(const char *fmt, ...)
|
|
Packit |
fd8b60 |
{
|
|
Packit |
fd8b60 |
va_list ap;
|
|
Packit |
fd8b60 |
if (! quiet){
|
|
Packit |
fd8b60 |
va_start(ap, fmt);
|
|
Packit |
fd8b60 |
vfprintf(stderr, fmt, ap);
|
|
Packit |
fd8b60 |
va_end(ap);
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
}
|
|
Packit |
fd8b60 |
|
|
Packit |
fd8b60 |
krb5_error_code
|
|
Packit |
fd8b60 |
ksu_tgtname(context, server, client, tgtprinc)
|
|
Packit |
fd8b60 |
krb5_context context;
|
|
Packit |
fd8b60 |
const krb5_data *server, *client;
|
|
Packit |
fd8b60 |
krb5_principal *tgtprinc;
|
|
Packit |
fd8b60 |
{
|
|
Packit |
fd8b60 |
return krb5_build_principal_ext(context, tgtprinc, client->length, client->data,
|
|
Packit |
fd8b60 |
KRB5_TGS_NAME_SIZE, KRB5_TGS_NAME,
|
|
Packit |
fd8b60 |
server->length, server->data,
|
|
Packit |
fd8b60 |
0);
|
|
Packit |
fd8b60 |
}
|