1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License, Version 1.0 only 6 * (the "License"). You may not use this file except in compliance 7 * with the License. 8 * 9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 10 * or http://www.opensolaris.org/os/licensing. 11 * See the License for the specific language governing permissions 12 * and limitations under the License. 13 * 14 * When distributing Covered Code, include this CDDL HEADER in each 15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 16 * If applicable, add the following below this CDDL HEADER, with the 17 * fields enclosed by brackets "[]" replaced with your own identifying 18 * information: Portions Copyright [yyyy] [name of copyright owner] 19 * 20 * CDDL HEADER END 21 */ 22 /* 23 * Copyright 2003 Sun Microsystems, Inc. All rights reserved. 24 * Use is subject to license terms. 25 */ 26 27 #pragma ident "%Z%%M% %I% %E% SMI" 28 29 #include <sys/types.h> 30 #include <sys/time.h> 31 #include <string.h> 32 #include <thread.h> 33 #include <unistd.h> 34 #include <stdlib.h> 35 #include <crypt.h> 36 #include <pwd.h> 37 #include <shadow.h> 38 39 #include <deflt.h> 40 41 #include "passwdutil.h" 42 43 #define PWADMIN "/etc/default/passwd" 44 45 #define MINWEEKS -1 46 #define MAXWEEKS -1 47 #define WARNWEEKS -1 48 49 void 50 free_pwd(struct passwd *pw) 51 { 52 if (pw->pw_name) free(pw->pw_name); 53 if (pw->pw_passwd) free(pw->pw_passwd); 54 if (pw->pw_gecos) free(pw->pw_gecos); 55 if (pw->pw_dir) free(pw->pw_dir); 56 if (pw->pw_shell) free(pw->pw_shell); 57 free(pw); 58 } 59 60 void 61 free_spwd(struct spwd *spw) 62 { 63 if (spw->sp_namp) free(spw->sp_namp); 64 if (spw->sp_pwdp) free(spw->sp_pwdp); 65 free(spw); 66 } 67 68 int 69 dup_pw(struct passwd **d, struct passwd *s) 70 { 71 if (s == NULL) { 72 *d = NULL; 73 return (PWU_NOT_FOUND); 74 } 75 if ((*d = calloc(1, sizeof (**d))) == NULL) 76 return (PWU_NOMEM); 77 78 if (s->pw_name) { 79 if (((*d)->pw_name = strdup(s->pw_name)) == NULL) 80 goto no_mem; 81 } 82 if (s->pw_passwd) { 83 if (((*d)->pw_passwd = strdup(s->pw_passwd)) == NULL) 84 goto no_mem; 85 } 86 (*d)->pw_uid = s->pw_uid; 87 (*d)->pw_gid = s->pw_gid; 88 89 if (s->pw_gecos) { 90 if (((*d)->pw_gecos = strdup(s->pw_gecos)) == NULL) 91 goto no_mem; 92 } 93 if (s->pw_dir) { 94 if (((*d)->pw_dir = strdup(s->pw_dir)) == NULL) 95 goto no_mem; 96 } 97 if (s->pw_shell) { 98 if (((*d)->pw_shell = strdup(s->pw_shell)) == NULL) 99 goto no_mem; 100 } 101 102 return (PWU_SUCCESS); 103 104 no_mem: 105 free_pwd(*d); 106 *d = NULL; 107 return (PWU_NOMEM); 108 } 109 110 int 111 dup_spw(struct spwd **d, struct spwd *s) 112 { 113 if (s == NULL) { 114 *d = NULL; 115 return (PWU_NOT_FOUND); 116 } 117 if ((*d = calloc(1, sizeof (**d))) == NULL) 118 return (PWU_NOMEM); 119 120 **d = *s; 121 122 if (s->sp_namp) 123 if (((*d)->sp_namp = strdup(s->sp_namp)) == NULL) 124 goto no_mem; 125 if (s->sp_pwdp) 126 if (((*d)->sp_pwdp = strdup(s->sp_pwdp)) == NULL) 127 goto no_mem; 128 return (PWU_SUCCESS); 129 130 no_mem: 131 free_spwd(*d); 132 return (PWU_NOMEM); 133 } 134 135 /* 136 * read a value from the defaults file, and return it if it is 137 * a positive integer. If the value is not defined, or negative, 138 * return the supplied default value 139 */ 140 int 141 def_getuint(char *name, int defvalue) 142 { 143 char *p; 144 int val = -1; /* -1 is a guard to catch undefined values */ 145 146 if (p = defread(name)) 147 val = atoi(p); 148 149 return (val >= 0 ? val : defvalue); 150 } 151 152 void 153 turn_on_default_aging(struct spwd *spw) 154 { 155 int minweeks; 156 int maxweeks; 157 int warnweeks; 158 159 if (defopen(PWADMIN) != 0) { 160 minweeks = MINWEEKS; 161 maxweeks = MAXWEEKS; 162 warnweeks = WARNWEEKS; 163 } else { 164 minweeks = def_getuint("MINWEEKS=", MINWEEKS); 165 maxweeks = def_getuint("MAXWEEKS=", MAXWEEKS); 166 warnweeks = def_getuint("WARNWEEKS=", WARNWEEKS); 167 (void) defopen(NULL); 168 } 169 170 /* 171 * The values specified in /etc/default/passwd are interpreted 172 * in a specific way. Special cases are 173 * MINWEEKS==0 (results in sp_min = -1) 174 * MAXWEEKS==0 (results in sp_max = default) 175 */ 176 spw->sp_min = 7 * minweeks; 177 if (spw->sp_min <= 0) 178 spw->sp_min = -1; 179 180 spw->sp_max = 7 * maxweeks; 181 if (spw->sp_max == 0) 182 spw->sp_max = 7 * MAXWEEKS; 183 if (spw->sp_max < 0) 184 spw->sp_max = -1; 185 186 spw->sp_warn = 7 * warnweeks; 187 if (spw->sp_warn <= 0) 188 spw->sp_warn = -1; 189 } 190 191 /* 192 * open and read a value from the defaults file, 193 * return value found or default value if not found. 194 */ 195 int 196 def_getint(char *name, int defvalue) 197 { 198 int val; 199 200 if (defopen(PWADMIN) != 0) 201 val = defvalue; 202 else 203 val = def_getuint(name, defvalue); 204 205 (void) defopen(NULL); 206 return (val); 207 } 208