root/source4/heimdal/kpasswd/kpasswd.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. usage
  2. change_password
  3. main

   1 /*
   2  * Copyright (c) 1997-2004 Kungliga Tekniska Högskolan
   3  * (Royal Institute of Technology, Stockholm, Sweden).
   4  * All rights reserved.
   5  *
   6  * Redistribution and use in source and binary forms, with or without
   7  * modification, are permitted provided that the following conditions
   8  * are met:
   9  *
  10  * 1. Redistributions of source code must retain the above copyright
  11  *    notice, this list of conditions and the following disclaimer.
  12  *
  13  * 2. Redistributions in binary form must reproduce the above copyright
  14  *    notice, this list of conditions and the following disclaimer in the
  15  *    documentation and/or other materials provided with the distribution.
  16  *
  17  * 3. Neither the name of the Institute nor the names of its contributors
  18  *    may be used to endorse or promote products derived from this software
  19  *    without specific prior written permission.
  20  *
  21  * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
  22  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  23  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  24  * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
  25  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  26  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  27  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  28  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  29  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  30  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  31  * SUCH DAMAGE.
  32  */
  33 
  34 #include "kpasswd_locl.h"
  35 RCSID("$Id$");
  36 
  37 static int version_flag;
  38 static int help_flag;
  39 static char *admin_principal_str;
  40 static char *cred_cache_str;
  41 
  42 static struct getargs args[] = {
  43     { "admin-principal",        0,   arg_string, &admin_principal_str },
  44     { "cache",                  'c', arg_string, &cred_cache_str },
  45     { "version",                0,   arg_flag, &version_flag },
  46     { "help",                   0,   arg_flag, &help_flag }
  47 };
  48 
  49 static void
  50 usage (int ret, struct getargs *a, int num_args)
     /* [<][>][^][v][top][bottom][index][help] */
  51 {
  52     arg_printusage (a, num_args, NULL, "[principal ...]");
  53     exit (ret);
  54 }
  55 
  56 static int
  57 change_password(krb5_context context,
     /* [<][>][^][v][top][bottom][index][help] */
  58                 krb5_principal principal,
  59                 krb5_ccache id)
  60 {
  61     krb5_data result_code_string, result_string;
  62     int result_code;
  63     krb5_error_code ret;
  64     char pwbuf[BUFSIZ];
  65     char *msg, *name;
  66 
  67     krb5_data_zero (&result_code_string);
  68     krb5_data_zero (&result_string);
  69 
  70     name = msg = NULL;
  71     if (principal == NULL)
  72         asprintf(&msg, "New password: ");
  73     else {
  74         ret = krb5_unparse_name(context, principal, &name);
  75         if (ret)
  76             krb5_err(context, 1, ret, "krb5_unparse_name");
  77 
  78         asprintf(&msg, "New password for %s: ", name);
  79     }
  80 
  81     if (msg == NULL)
  82         krb5_errx (context, 1, "out of memory");
  83 
  84     ret = UI_UTIL_read_pw_string (pwbuf, sizeof(pwbuf), msg, 1);
  85     free(msg);
  86     if (name)
  87         free(name);
  88     if (ret != 0) {
  89         return 1;
  90     }
  91 
  92     ret = krb5_set_password_using_ccache (context, id, pwbuf,
  93                                           principal,
  94                                           &result_code,
  95                                           &result_code_string,
  96                                           &result_string);
  97     if (ret) {
  98         krb5_warn (context, ret, "krb5_set_password_using_ccache");
  99         return 1;
 100     }
 101 
 102     printf ("%s%s%.*s\n", krb5_passwd_result_to_string(context, result_code),
 103             result_string.length > 0 ? " : " : "",
 104             (int)result_string.length,
 105             result_string.length > 0 ? (char *)result_string.data : "");
 106 
 107     krb5_data_free (&result_code_string);
 108     krb5_data_free (&result_string);
 109 
 110     return ret != 0;
 111 }
 112 
 113 
 114 int
 115 main (int argc, char **argv)
     /* [<][>][^][v][top][bottom][index][help] */
 116 {
 117     krb5_error_code ret;
 118     krb5_context context;
 119     krb5_principal principal;
 120     int optind = 0;
 121     krb5_get_init_creds_opt *opt;
 122     krb5_ccache id = NULL;
 123     int exit_value;
 124 
 125     optind = krb5_program_setup(&context, argc, argv,
 126                                 args, sizeof(args) / sizeof(args[0]), usage);
 127 
 128     if (help_flag)
 129         usage (0, args, sizeof(args) / sizeof(args[0]));
 130 
 131     if(version_flag){
 132         print_version (NULL);
 133         exit(0);
 134     }
 135 
 136     argc -= optind;
 137     argv += optind;
 138 
 139     ret = krb5_init_context (&context);
 140     if (ret)
 141         errx (1, "krb5_init_context failed: %d", ret);
 142 
 143     ret = krb5_get_init_creds_opt_alloc (context, &opt);
 144     if (ret)
 145         krb5_err(context, 1, ret, "krb5_get_init_creds_opt_alloc");
 146 
 147     krb5_get_init_creds_opt_set_tkt_life (opt, 300);
 148     krb5_get_init_creds_opt_set_forwardable (opt, FALSE);
 149     krb5_get_init_creds_opt_set_proxiable (opt, FALSE);
 150 
 151     if (cred_cache_str) {
 152         ret = krb5_cc_resolve(context, cred_cache_str, &id);
 153         if (ret)
 154             krb5_err (context, 1, ret, "krb5_cc_resolve");
 155     } else {
 156         ret = krb5_cc_gen_new(context, &krb5_mcc_ops, &id);
 157         if (ret)
 158             krb5_err (context, 1, ret, "krb5_cc_gen_new");
 159     }
 160 
 161     if (cred_cache_str == NULL) {
 162         krb5_principal admin_principal = NULL;
 163         krb5_creds cred;
 164 
 165         if (admin_principal_str) {
 166             ret = krb5_parse_name (context, admin_principal_str,
 167                                    &admin_principal);
 168             if (ret)
 169                 krb5_err (context, 1, ret, "krb5_parse_name");
 170         } else if (argc == 1) {
 171             ret = krb5_parse_name (context, argv[0], &admin_principal);
 172             if (ret)
 173                 krb5_err (context, 1, ret, "krb5_parse_name");
 174         } else {
 175             ret = krb5_get_default_principal (context, &admin_principal);
 176             if (ret)
 177                 krb5_err (context, 1, ret, "krb5_get_default_principal");
 178         }
 179 
 180         ret = krb5_get_init_creds_password (context,
 181                                             &cred,
 182                                             admin_principal,
 183                                             NULL,
 184                                             krb5_prompter_posix,
 185                                             NULL,
 186                                             0,
 187                                             "kadmin/changepw",
 188                                             opt);
 189         switch (ret) {
 190         case 0:
 191             break;
 192         case KRB5_LIBOS_PWDINTR :
 193             return 1;
 194         case KRB5KRB_AP_ERR_BAD_INTEGRITY :
 195         case KRB5KRB_AP_ERR_MODIFIED :
 196             krb5_errx(context, 1, "Password incorrect");
 197             break;
 198         default:
 199             krb5_err(context, 1, ret, "krb5_get_init_creds");
 200         }
 201         
 202         krb5_get_init_creds_opt_free(context, opt);
 203         
 204         ret = krb5_cc_initialize(context, id, admin_principal);
 205         krb5_free_principal(context, admin_principal);
 206         if (ret)
 207             krb5_err(context, 1, ret, "krb5_cc_initialize");
 208 
 209         ret = krb5_cc_store_cred(context, id, &cred);
 210         if (ret)
 211             krb5_err(context, 1, ret, "krb5_cc_store_cred");
 212         
 213         krb5_free_cred_contents (context, &cred);
 214     }
 215 
 216     if (argc == 0) {
 217         exit_value = change_password(context, NULL, id);
 218     } else {
 219         exit_value = 0;
 220 
 221         while (argc-- > 0) {
 222 
 223             ret = krb5_parse_name (context, argv[0], &principal);
 224             if (ret)
 225                 krb5_err (context, 1, ret, "krb5_parse_name");
 226 
 227             ret = change_password(context, principal, id);
 228             if (ret)
 229                 exit_value = 1;
 230             krb5_free_principal(context, principal);
 231             argv++;
 232         }
 233     }
 234 
 235     if (cred_cache_str == NULL) {
 236         ret = krb5_cc_destroy(context, id);
 237         if (ret)
 238             krb5_err (context, 1, ret, "krb5_cc_destroy");
 239     } else {
 240         ret = krb5_cc_close(context, id);
 241         if (ret)
 242             krb5_err (context, 1, ret, "krb5_cc_close");
 243     }
 244 
 245     krb5_free_context (context);
 246     return exit_value;
 247 }

/* [<][>][^][v][top][bottom][index][help] */