From 3ca1029905dff5273da1e8ad2be4eaf4bd039db1 Mon Sep 17 00:00:00 2001 From: Sami Kerola Date: Wed, 23 Nov 2011 22:57:31 +0100 Subject: chfn: fix coding style Signed-off-by: Sami Kerola --- login-utils/chfn.c | 695 ++++++++++++++++++++++++++++------------------------- 1 file changed, 367 insertions(+), 328 deletions(-) (limited to 'login-utils/chfn.c') diff --git a/login-utils/chfn.c b/login-utils/chfn.c index f3fdfa78f..21c6466bd 100644 --- a/login-utils/chfn.c +++ b/login-utils/chfn.c @@ -18,181 +18,184 @@ * * 1999-02-22 Arkadiusz Mi¶kiewicz * - added Native Language Support - * */ -#include -#include -#include -#include -#include -#include -#include #include +#include #include +#include #include +#include +#include +#include +#include +#include -#include "pamfail.h" +#include "c.h" +#include "env.h" #include "islocal.h" +#include "nls.h" +#include "pamfail.h" #include "setpwnam.h" #include "strutils.h" -#include "nls.h" -#include "env.h" #include "xalloc.h" -#include "c.h" #ifdef HAVE_LIBSELINUX -#include -#include -#include "selinux_utils.h" +# include +# include +# include "selinux_utils.h" #endif static char buf[1024]; struct finfo { - struct passwd *pw; - char *username; - char *full_name; - char *office; - char *office_phone; - char *home_phone; - char *other; + struct passwd *pw; + char *username; + char *full_name; + char *office; + char *office_phone; + char *home_phone; + char *other; }; -static int parse_argv (int argc, char *argv[], struct finfo *pinfo); -static void parse_passwd (struct passwd *pw, struct finfo *pinfo); -static void ask_info (struct finfo *oldfp, struct finfo *newfp); -static char *prompt (char *question, char *def_val); -static int check_gecos_string (char *msg, char *gecos); -static int set_changed_data (struct finfo *oldfp, struct finfo *newfp); -static int save_new_data (struct finfo *pinfo); +static int parse_argv(int argc, char *argv[], struct finfo *pinfo); +static void parse_passwd(struct passwd *pw, struct finfo *pinfo); +static void ask_info(struct finfo *oldfp, struct finfo *newfp); +static char *prompt(char *question, char *def_val); +static int check_gecos_string(char *msg, char *gecos); +static int set_changed_data(struct finfo *oldfp, struct finfo *newfp); +static int save_new_data(struct finfo *pinfo); /* we do not accept gecos field sizes longer than MAX_FIELD_SIZE */ #define MAX_FIELD_SIZE 256 static void __attribute__((__noreturn__)) usage(FILE *fp) { - fputs(USAGE_HEADER, fp); - fprintf(fp, _(" %s [options] [username]\n"), program_invocation_short_name); - fputs(USAGE_OPTIONS, fp); - fputs(_(" -f, --full-name real name\n"), fp); - fputs(_(" -o, --office office number\n"), fp); - fputs(_(" -p, --office-phone office phone number\n"), fp); - fputs(_(" -h, --home-phone home phone number\n"), fp); - fputs(USAGE_SEPARATOR, fp); - fputs(_(" -u, --help display this help and exit\n"), fp); - fputs(_(" -v, --version output version information and exit\n"), fp); - fprintf(fp, USAGE_MAN_TAIL("chfn(1)")); - exit(fp == stderr ? EXIT_FAILURE : EXIT_SUCCESS); + fputs(USAGE_HEADER, fp); + fprintf(fp, _(" %s [options] [username]\n"), program_invocation_short_name); + fputs(USAGE_OPTIONS, fp); + fputs(_(" -f, --full-name real name\n"), fp); + fputs(_(" -o, --office office number\n"), fp); + fputs(_(" -p, --office-phone office phone number\n"), fp); + fputs(_(" -h, --home-phone home phone number\n"), fp); + fputs(USAGE_SEPARATOR, fp); + fputs(_(" -u, --help display this help and exit\n"), fp); + fputs(_(" -v, --version output version information and exit\n"), fp); + fprintf(fp, USAGE_MAN_TAIL("chfn(1)")); + exit(fp == stderr ? EXIT_FAILURE : EXIT_SUCCESS); } -int main (int argc, char **argv) { - uid_t uid; - struct finfo oldf, newf; - int interactive; - int status; - - sanitize_env(); - setlocale(LC_ALL, ""); /* both for messages and for iscntrl() below */ - bindtextdomain(PACKAGE, LOCALEDIR); - textdomain(PACKAGE); - - /* - * "oldf" contains the users original finger information. - * "newf" contains the changed finger information, and contains NULL - * in fields that haven't been changed. - * in the end, "newf" is folded into "oldf". - * the reason the new finger information is not put _immediately_ into - * "oldf" is that on the command line, new finger information can - * be specified before we know what user the information is being - * specified for. - */ - uid = getuid (); - memset(&oldf, 0, sizeof(oldf)); - memset(&newf, 0, sizeof (newf)); - - interactive = parse_argv (argc, argv, &newf); - if (! newf.username) { - parse_passwd (getpwuid (uid), &oldf); - if (! oldf.username) - errx(EXIT_FAILURE, _("you (user %d) don't exist."), uid); - } - else { - parse_passwd (getpwnam (newf.username), &oldf); - if (! oldf.username) - errx(EXIT_FAILURE, _("user \"%s\" does not exist."), - newf.username); - } - - if (!(is_local(oldf.username))) - errx(EXIT_FAILURE, _("can only change local entries")); +int main(int argc, char **argv) +{ + uid_t uid; + struct finfo oldf, newf; + int interactive; + int status; + + sanitize_env(); + setlocale(LC_ALL, ""); /* both for messages and for iscntrl() below */ + bindtextdomain(PACKAGE, LOCALEDIR); + textdomain(PACKAGE); + + /* + * "oldf" contains the users original finger information. + * "newf" contains the changed finger information, and contains NULL + * in fields that haven't been changed. + * in the end, "newf" is folded into "oldf". + * + * the reason the new finger information is not put _immediately_ + * into "oldf" is that on the command line, new finger information + * can be specified before we know what user the information is + * being specified for. + */ + uid = getuid(); + memset(&oldf, 0, sizeof(oldf)); + memset(&newf, 0, sizeof(newf)); + + interactive = parse_argv(argc, argv, &newf); + if (!newf.username) { + parse_passwd(getpwuid(uid), &oldf); + if (!oldf.username) + errx(EXIT_FAILURE, _("you (user %d) don't exist."), + uid); + } else { + parse_passwd(getpwnam(newf.username), &oldf); + if (!oldf.username) + errx(EXIT_FAILURE, _("user \"%s\" does not exist."), + newf.username); + } + + if (!(is_local(oldf.username))) + errx(EXIT_FAILURE, _("can only change local entries")); #ifdef HAVE_LIBSELINUX - if (is_selinux_enabled() > 0) { - if(uid == 0) { - if (checkAccess(oldf.username,PASSWD__CHFN)!=0) { - security_context_t user_context; - if (getprevcon(&user_context) < 0) - user_context = NULL; - - errx(EXIT_FAILURE, _("%s is not authorized to change " - "the finger info of %s"), - user_context ? : _("Unknown user context"), - oldf.username); + if (is_selinux_enabled() > 0) { + if (uid == 0) { + if (checkAccess(oldf.username, PASSWD__CHFN) != 0) { + security_context_t user_context; + if (getprevcon(&user_context) < 0) + user_context = NULL; + errx(EXIT_FAILURE, + _("%s is not authorized to change " + "the finger info of %s"), + user_context ? : _("Unknown user context"), + oldf.username); + } + } + if (setupDefaultContext("/etc/passwd")) + errx(EXIT_FAILURE, + _("can't set default context for /etc/passwd")); } - } - if (setupDefaultContext("/etc/passwd")) - errx(EXIT_FAILURE, _("can't set default context for /etc/passwd")); - } #endif - /* Reality check */ - if (uid != 0 && uid != oldf.pw->pw_uid) { - errno = EACCES; - err(EXIT_FAILURE, NULL); - } + /* Reality check */ + if (uid != 0 && uid != oldf.pw->pw_uid) { + errno = EACCES; + err(EXIT_FAILURE, NULL); + } - printf (_("Changing finger information for %s.\n"), oldf.username); + printf(_("Changing finger information for %s.\n"), oldf.username); #ifdef REQUIRE_PASSWORD - if(uid != 0) { - pam_handle_t *pamh = NULL; - struct pam_conv conv = { misc_conv, NULL }; - int retcode; - - retcode = pam_start("chfn", oldf.username, &conv, &pamh); - if (pam_fail_check(pamh, retcode)) - exit(EXIT_FAILURE); - - retcode = pam_authenticate(pamh, 0); - if (pam_fail_check(pamh, retcode)) - exit(EXIT_FAILURE); - - retcode = pam_acct_mgmt(pamh, 0); - if (retcode == PAM_NEW_AUTHTOK_REQD) - retcode = pam_chauthtok(pamh, PAM_CHANGE_EXPIRED_AUTHTOK); - if (pam_fail_check(pamh, retcode)) - exit(EXIT_FAILURE); - - retcode = pam_setcred(pamh, 0); - if (pam_fail_check(pamh, retcode)) - exit(EXIT_FAILURE); - - pam_end(pamh, 0); - /* no need to establish a session; this isn't a session-oriented - * activity... */ - } -#endif /* REQUIRE_PASSWORD */ - - - if (interactive) ask_info (&oldf, &newf); - - if (! set_changed_data (&oldf, &newf)) { - printf (_("Finger information not changed.\n")); - return EXIT_SUCCESS; - } - status = save_new_data (&oldf); - return status; + if (uid != 0) { + pam_handle_t *pamh = NULL; + struct pam_conv conv = { misc_conv, NULL }; + int retcode; + + retcode = pam_start("chfn", oldf.username, &conv, &pamh); + if (pam_fail_check(pamh, retcode)) + exit(EXIT_FAILURE); + + retcode = pam_authenticate(pamh, 0); + if (pam_fail_check(pamh, retcode)) + exit(EXIT_FAILURE); + + retcode = pam_acct_mgmt(pamh, 0); + if (retcode == PAM_NEW_AUTHTOK_REQD) + retcode = + pam_chauthtok(pamh, PAM_CHANGE_EXPIRED_AUTHTOK); + if (pam_fail_check(pamh, retcode)) + exit(EXIT_FAILURE); + + retcode = pam_setcred(pamh, 0); + if (pam_fail_check(pamh, retcode)) + exit(EXIT_FAILURE); + + pam_end(pamh, 0); + /* no need to establish a session; this isn't a + * session-oriented activity... */ + } +#endif /* REQUIRE_PASSWORD */ + + if (interactive) + ask_info(&oldf, &newf); + + if (!set_changed_data(&oldf, &newf)) { + printf(_("Finger information not changed.\n")); + return EXIT_SUCCESS; + } + status = save_new_data(&oldf); + return status; } /* @@ -202,102 +205,116 @@ int main (int argc, char **argv) { */ static int parse_argv(int argc, char *argv[], struct finfo *pinfo) { - int index, c, status; - int info_given; - - static struct option long_options[] = { - { "full-name", required_argument, 0, 'f' }, - { "office", required_argument, 0, 'o' }, - { "office-phone", required_argument, 0, 'p' }, - { "home-phone", required_argument, 0, 'h' }, - { "help", no_argument, 0, 'u' }, - { "version", no_argument, 0, 'v' }, - { NULL, no_argument, 0, '0' }, - }; - - optind = 0; - info_given = false; - while (true) { - c = getopt_long (argc, argv, "f:r:p:h:o:uv", long_options, &index); - if (c == -1) break; - /* version? output version and exit. */ - if (c == 'v') { - printf (UTIL_LINUX_VERSION); - exit (EXIT_SUCCESS); + int index, c, status; + int info_given; + + static struct option long_options[] = { + {"full-name", required_argument, 0, 'f'}, + {"office", required_argument, 0, 'o'}, + {"office-phone", required_argument, 0, 'p'}, + {"home-phone", required_argument, 0, 'h'}, + {"help", no_argument, 0, 'u'}, + {"version", no_argument, 0, 'v'}, + {NULL, no_argument, 0, '0'}, + }; + + optind = 0; + info_given = false; + while (true) { + c = getopt_long(argc, argv, "f:r:p:h:o:uv", long_options, + &index); + if (c == -1) + break; + /* version? output version and exit. */ + if (c == 'v') { + printf(UTIL_LINUX_VERSION); + exit(EXIT_SUCCESS); + } + if (c == 'u') + usage(stdout); + /* all other options must have an argument. */ + if (!optarg) + usage(stderr); + /* ok, we were given an argument */ + info_given = true; + status = 0; + + /* now store the argument */ + switch (c) { + case 'f': + pinfo->full_name = optarg; + status = check_gecos_string(_("Name"), optarg); + break; + case 'o': + pinfo->office = optarg; + status = check_gecos_string(_("Office"), optarg); + break; + case 'p': + pinfo->office_phone = optarg; + status = check_gecos_string(_("Office Phone"), optarg); + break; + case 'h': + pinfo->home_phone = optarg; + status = check_gecos_string(_("Home Phone"), optarg); + break; + default: + usage(stderr); + } + if (status < 0) + exit(status); } - if (c == 'u') - usage (stdout); - /* all other options must have an argument. */ - if (! optarg) - usage (stderr); - /* ok, we were given an argument */ - info_given = true; - status = 0; - - /* now store the argument */ - switch (c) { - case 'f': - pinfo->full_name = optarg; - status = check_gecos_string (_("Name"), optarg); - break; - case 'o': - pinfo->office = optarg; - status = check_gecos_string (_("Office"), optarg); - break; - case 'p': - pinfo->office_phone = optarg; - status = check_gecos_string (_("Office Phone"), optarg); - break; - case 'h': - pinfo->home_phone = optarg; - status = check_gecos_string (_("Home Phone"), optarg); - break; - default: - usage (stderr); + /* done parsing arguments. check for a username. */ + if (optind < argc) { + if (optind + 1 < argc) + usage(stderr); + pinfo->username = argv[optind]; } - if (status < 0) exit (status); - } - /* done parsing arguments. check for a username. */ - if (optind < argc) { - if (optind + 1 < argc) - usage (stderr); - pinfo->username = argv[optind]; - } - return (! info_given); + return (!info_given); } /* * parse_passwd () -- - * take a struct password and fill in the fields of the - * struct finfo. + * take a struct password and fill in the fields of the struct finfo. */ static void parse_passwd(struct passwd *pw, struct finfo *pinfo) { - char *gecos; - char *cp; - - if (pw) { - pinfo->pw = pw; - pinfo->username = pw->pw_name; - /* use pw_gecos - we take a copy since PAM destroys the original */ - gecos = xstrdup(pw->pw_gecos); - cp = (gecos ? gecos : ""); - pinfo->full_name = cp; - cp = strchr (cp, ','); - if (cp) { *cp = 0, cp++; } else return; - pinfo->office = cp; - cp = strchr (cp, ','); - if (cp) { *cp = 0, cp++; } else return; - pinfo->office_phone = cp; - cp = strchr (cp, ','); - if (cp) { *cp = 0, cp++; } else return; - pinfo->home_phone = cp; - /* extra fields contain site-specific information, and - * can not be changed by this version of chfn. */ - cp = strchr (cp, ','); - if (cp) { *cp = 0, cp++; } else return; - pinfo->other = cp; - } + char *gecos; + char *cp; + + if (pw) { + pinfo->pw = pw; + pinfo->username = pw->pw_name; + /* use pw_gecos - we take a copy since PAM destroys the original */ + gecos = xstrdup(pw->pw_gecos); + cp = (gecos ? gecos : ""); + pinfo->full_name = cp; + cp = strchr(cp, ','); + if (cp) { + *cp = 0, cp++; + } else + return; + pinfo->office = cp; + cp = strchr(cp, ','); + if (cp) { + *cp = 0, cp++; + } else + return; + pinfo->office_phone = cp; + cp = strchr(cp, ','); + if (cp) { + *cp = 0, cp++; + } else + return; + pinfo->home_phone = cp; + /* extra fields contain site-specific information, and can + * not be changed by this version of chfn. */ + cp = strchr(cp, ','); + if (cp) { + *cp = 0, cp++; + } else + return; + pinfo->other = cp; + } } /* @@ -306,11 +323,11 @@ static void parse_passwd(struct passwd *pw, struct finfo *pinfo) */ static void ask_info(struct finfo *oldfp, struct finfo *newfp) { - newfp->full_name = prompt (_("Name"), oldfp->full_name); - newfp->office = prompt (_("Office"), oldfp->office); - newfp->office_phone = prompt (_("Office Phone"), oldfp->office_phone); - newfp->home_phone = prompt (_("Home Phone"), oldfp->home_phone); - printf ("\n"); + newfp->full_name = prompt(_("Name"), oldfp->full_name); + newfp->office = prompt(_("Office"), oldfp->office); + newfp->office_phone = prompt(_("Office Phone"), oldfp->office_phone); + newfp->home_phone = prompt(_("Home Phone"), oldfp->home_phone); + printf("\n"); } /* @@ -319,67 +336,74 @@ static void ask_info(struct finfo *oldfp, struct finfo *newfp) */ static char *prompt(char *question, char *def_val) { - static char *blank = "none"; - int len; - char *ans, *cp; - - while (true) { - if (! def_val) def_val = ""; - printf("%s [%s]: ", question, def_val); - *buf = 0; - if (fgets (buf, sizeof (buf), stdin) == NULL) - errx (EXIT_FAILURE, _("Aborted.")); - /* remove the newline at the end of buf. */ - ans = buf; - while (isspace (*ans)) ans++; - len = strlen (ans); - while (len > 0 && isspace (ans[len-1])) len--; - if (len <= 0) return NULL; - ans[len] = 0; - if (! strcasecmp (ans, blank)) return ""; - if (check_gecos_string (NULL, ans) >= 0) break; - } - cp = (char *) xmalloc (len + 1); - strcpy (cp, ans); - return cp; + static char *blank = "none"; + int len; + char *ans, *cp; + + while (true) { + if (!def_val) + def_val = ""; + printf("%s [%s]: ", question, def_val); + *buf = 0; + if (fgets(buf, sizeof(buf), stdin) == NULL) + errx(EXIT_FAILURE, _("Aborted.")); + /* remove the newline at the end of buf. */ + ans = buf; + while (isspace(*ans)) + ans++; + len = strlen(ans); + while (len > 0 && isspace(ans[len - 1])) + len--; + if (len <= 0) + return NULL; + ans[len] = 0; + if (!strcasecmp(ans, blank)) + return ""; + if (check_gecos_string(NULL, ans) >= 0) + break; + } + cp = (char *)xmalloc(len + 1); + strcpy(cp, ans); + return cp; } /* * check_gecos_string () -- * check that the given gecos string is legal. if it's not legal, - * output "msg" followed by a description of the problem, and - * return (-1). + * output "msg" followed by a description of the problem, and return (-1). */ static int check_gecos_string(char *msg, char *gecos) { - unsigned int i, c; - - if (strlen(gecos) > MAX_FIELD_SIZE) { - if (msg) - warnx (_("field %s is too long"), msg); - else - warnx (_("field is too long")); - return -1; - } - - for (i = 0; i < strlen (gecos); i++) { - c = gecos[i]; - if (c == ',' || c == ':' || c == '=' || c == '"' || c == '\n') { - if (msg) - warnx (_("%s: '%c' is not allowed"), msg, c); - else - warnx (_("'%c' is not allowed"), c); - return -1; + unsigned int i, c; + + if (strlen(gecos) > MAX_FIELD_SIZE) { + if (msg) + warnx(_("field %s is too long"), msg); + else + warnx(_("field is too long")); + return -1; } - if (iscntrl (c)) { - if (msg) - warnx (_("%s: control characters are not allowed"), msg); - else - warnx (_("control characters are not allowed")); - return -1; + + for (i = 0; i < strlen(gecos); i++) { + c = gecos[i]; + if (c == ',' || c == ':' || c == '=' || c == '"' || c == '\n') { + if (msg) + warnx(_("%s: '%c' is not allowed"), msg, c); + else + warnx(_("'%c' is not allowed"), c); + return -1; + } + if (iscntrl(c)) { + if (msg) + warnx(_ + ("%s: control characters are not allowed"), + msg); + else + warnx(_("control characters are not allowed")); + return -1; + } } - } - return 0; + return 0; } /* @@ -388,18 +412,26 @@ static int check_gecos_string(char *msg, char *gecos) */ static int set_changed_data(struct finfo *oldfp, struct finfo *newfp) { - int changed = false; - - if (newfp->full_name) { - oldfp->full_name = newfp->full_name; changed = true; } - if (newfp->office) { - oldfp->office = newfp->office; changed = true; } - if (newfp->office_phone) { - oldfp->office_phone = newfp->office_phone; changed = true; } - if (newfp->home_phone) { - oldfp->home_phone = newfp->home_phone; changed = true; } - - return changed; + int changed = false; + + if (newfp->full_name) { + oldfp->full_name = newfp->full_name; + changed = true; + } + if (newfp->office) { + oldfp->office = newfp->office; + changed = true; + } + if (newfp->office_phone) { + oldfp->office_phone = newfp->office_phone; + changed = true; + } + if (newfp->home_phone) { + oldfp->home_phone = newfp->home_phone; + changed = true; + } + + return changed; } /* @@ -409,37 +441,44 @@ static int set_changed_data(struct finfo *oldfp, struct finfo *newfp) */ static int save_new_data(struct finfo *pinfo) { - char *gecos; - int len; - - /* null fields will confuse printf(). */ - if (! pinfo->full_name) pinfo->full_name = ""; - if (! pinfo->office) pinfo->office = ""; - if (! pinfo->office_phone) pinfo->office_phone = ""; - if (! pinfo->home_phone) pinfo->home_phone = ""; - if (! pinfo->other) pinfo->other = ""; - - /* create the new gecos string */ - len = (strlen (pinfo->full_name) + strlen (pinfo->office) + - strlen (pinfo->office_phone) + strlen (pinfo->home_phone) + - strlen (pinfo->other) + 4); - gecos = (char *) xmalloc (len + 1); - sprintf (gecos, "%s,%s,%s,%s,%s", pinfo->full_name, pinfo->office, - pinfo->office_phone, pinfo->home_phone, pinfo->other); - - /* remove trailing empty fields (but not subfields of pinfo->other) */ - if (! pinfo->other[0] ) { - while (len > 0 && gecos[len-1] == ',') len--; - gecos[len] = 0; - } - - /* write the new struct passwd to the passwd file. */ - pinfo->pw->pw_gecos = gecos; - if (setpwnam (pinfo->pw) < 0) { - warn ("setpwnam"); - printf( _("Finger information *NOT* changed. Try again later.\n" )); - return -1; - } - printf (_("Finger information changed.\n")); - return 0; + char *gecos; + int len; + + /* null fields will confuse printf(). */ + if (!pinfo->full_name) + pinfo->full_name = ""; + if (!pinfo->office) + pinfo->office = ""; + if (!pinfo->office_phone) + pinfo->office_phone = ""; + if (!pinfo->home_phone) + pinfo->home_phone = ""; + if (!pinfo->other) + pinfo->other = ""; + + /* create the new gecos string */ + len = (strlen(pinfo->full_name) + strlen(pinfo->office) + + strlen(pinfo->office_phone) + strlen(pinfo->home_phone) + + strlen(pinfo->other) + 4); + gecos = (char *)xmalloc(len + 1); + sprintf(gecos, "%s,%s,%s,%s,%s", pinfo->full_name, pinfo->office, + pinfo->office_phone, pinfo->home_phone, pinfo->other); + + /* remove trailing empty fields (but not subfields of pinfo->other) */ + if (!pinfo->other[0]) { + while (len > 0 && gecos[len - 1] == ',') + len--; + gecos[len] = 0; + } + + /* write the new struct passwd to the passwd file. */ + pinfo->pw->pw_gecos = gecos; + if (setpwnam(pinfo->pw) < 0) { + warn("setpwnam"); + printf(_ + ("Finger information *NOT* changed. Try again later.\n")); + return -1; + } + printf(_("Finger information changed.\n")); + return 0; } -- cgit v1.2.3-55-g7522