--- gnuser-1.2.1.c 2009-11-05 21:54:43.000000000 +0100 +++ gnuser-1.3.0.c 2009-11-08 12:22:31.000000000 +0100 @@ -1,10 +1,8 @@ /* * Project: gnuser (Gnu User Manager) * File: gnuser.c - * Version: 1.2.1 - * Copyright (c) 2009-2010 - * Author: Jonathan Salwan - * Mail: jonathan.salwan [!] gnuser.org + * Version: 1.3.0 + * Copyright (c) 2009 - Jonathan Salwan * * All rights reserved. * @@ -21,14 +19,14 @@ * * French: * La redistribution et l'utilisation sous forme source et binaire, - * avec ou sans modification, sont autoris?es ? condition que les + * avec ou sans modification, sont autorisées à condition que les * conditions suivantes soient remplies: * 1. Les redistributions du code source doivent contenir la notice * de copyright ci-dessus, cette liste de conditions et la clause - * de non responsabilit?. + * de non responsabilité. * 2. Les redistributions sous forme binaire doivent reproduire la * notice de copyright ci-dessus, cette liste de conditions et la - * clause de non responsabilit? dans la documentation et / ou d'autres + * clause de non responsabilité dans la documentation et/ou d'autres * documents fournis avec la distribution. * */ @@ -42,87 +40,141 @@ #include #include +/* Files Patach Values */ #define patch_passwd "/etc/passwd" #define patch_shadow "/etc/shadow" #define patch_group "/etc/group" +/* Exit Status Values */ +#define EXIT_SUCCESS 0 /* success */ +#define EXIT_USAGE 1 /* invalid command syntax */ +#define EXIT_ROOT 2 /* Not root */ +#define EXIT_UID 3 /* UID exist */ +#define EXIT_GID 4 /* GID exist */ +#define EXIT_LOGIN 5 /* Login name exist */ +#define EXIT_GROUP 6 /* Group name exist */ +#define EXIT_LOGIN_NOT_EXIST 7 /* Login name not exist */ +#define EXIT_GROUP_NOT_EXIST 8 /* Group name not exist */ + +/* local function prototypes */ +static void root(void); + +static void usage(void); +static void usage_add_user(void); +static void usage_del_user(void); +static void usage_show(void); +static void usage_group_info(void); +static void usage_add_group(void); +static void usage_dell_group(void); + +static int del_passwd(int); +static int del_shadow(int); +static int del_group(int); +static int verif_uid(int); +static int verif_name(char *); +static int verif_gid(int); +static int verif_grname(char *); + static void root(void) { if(getuid() != 0) { fprintf(stderr,"Error: You need privileges root\n"); - exit(1); + exit(EXIT_ROOT); } } - -static void option(void) +static void usage(void) { fprintf(stderr, "gnuser: invalid option\n" "Usage: gnuser [option] \n\n" "Options:\n" - "-add Add a new user\n" - "-del Delete user\n" - "-show Show user informations\n" - "-gi Group informations\n" + "-a Add a new user\n" + "-A Delete user\n" + "-s Show user informations\n" + "-i Group informations\n" + "-g Add a new group\n" + "-G Delete group\n" "-v Version informations\n"); -exit(1); +exit(EXIT_USAGE); } -static void option_add(void) +static void usage_add_user(void) { fprintf(stderr, "gnuser: invalid option for add user\n" - "Usage: gnuser -add \n\n" + "Usage: gnuser -a \n\n" - "Exemple: gnuser -add jonathan 1001 1001 /home/jonathan\n\n"); + "Exemple: gnuser -a jonathan 1001 1001 /home/jonathan\n\n"); -exit(1); +exit(EXIT_USAGE); } -static void option_del(void) +static void usage_del_user(void) { fprintf(stderr, "gnuser: invalid option for del user\n" - "Usage: gnuser -del \n\n" + "Usage: gnuser -A \n\n" - "Exemple: gnuser -del jonathan\n\n"); + "Exemple: gnuser -A jonathan\n\n"); -exit(1); +exit(EXIT_USAGE); } -static void option_show(void) +static void usage_show(void) { fprintf(stderr, "gnuser: invalid option for show user\n" - "Usage: gnuser -show \n\n" + "Usage: gnuser -s \n\n" + + "Exemple: gnuser -s jonathan\n\n"); + +exit(EXIT_USAGE); +} + +static void usage_group_info(void) +{ + fprintf(stderr, + "gnuser: invalid option for informations group\n" + "Usage: gnuser -i \n\n" - "Exemple: gnuser -show jonathan\n\n"); + "Exemple: gnuser -i daemon\n\n"); -exit(1); +exit(EXIT_USAGE); } -static void option_gi(void) +static void usage_add_group(void) { fprintf(stderr, - "gnuser: invalid option for information group\n" - "Usage: gnuser -gi \n\n" + "gnuser: invalid option for add a new group\n" + "Usage: gnuser -g \n\n" - "Exemple: gnuser -gi daemon\n\n"); + "Exemple: gnuser -g newgroup 501\n\n"); -exit(1); +exit(EXIT_USAGE); +} + +static void usage_del_group(void) +{ + fprintf(stderr, + "gnuser: invalid option for delete group\n" + "Usage: gnuser -G \n\n" + + "Exemple: gnuser -G newgroup\n\n"); + +exit(EXIT_USAGE); } static void version(void) { fprintf(stdout, - "gnuser (Gnu User Manager) - v1.2.1\n" + "gnuser (Gnu User Manager) - v1.3.0\n" "GPL Licence\n"); -exit(0); +exit(EXIT_SUCCESS); } static int del_passwd(int login_line) @@ -164,6 +216,7 @@ return 0; } + static int del_shadow(int login_line) { FILE *fp1, *fp2; @@ -205,7 +258,48 @@ return 0; } -int verif_uid(int idlogin) +static int del_group(int group_line) +{ + FILE *fp1, *fp2; + char *line = NULL; + size_t len = 0; + ssize_t read; + + fp1 = fopen(patch_group, "r"); + fp2 = fopen("/etc/group2", "w"); + + + int cpt = 0; + int line_rease = group_line; + + /* On recopie le fichier /etc/group dans /etc/group2 sans la ligne du login à effacer */ + while ((read = getline(&line, &len, fp1)) != -1) { + cpt++; + if(cpt != line_rease) + fprintf(fp2,"%s", line); + } + fclose(fp1); + fclose(fp2); + + + /* On remplace /etc/group2 par /etc/group puis on supprimer /etc/group2 */ + unlink(patch_group); + + fp1 = fopen(patch_group, "w"); + fp2 = fopen("/etc/group2", "r"); + +while ((read = getline(&line, &len, fp2)) != -1) { + fprintf(fp1,"%s", line); + } + fclose(fp1); + fclose(fp2); + + unlink("/etc/group2"); + +return 0; +} + +static int verif_uid(int idlogin) { FILE *fileread; @@ -218,41 +312,109 @@ if (pswd_struct->pw_uid == idlogin){ break; } } - /* test if uid exist */ + /* test if entry exist */ + if (pswd_struct == NULL) + {return 0;} + else + {return 1;} +} + +static int verif_name(char *namelogin) +{ + + FILE *fileread; + + fileread = fopen(patch_passwd, "r"); + struct passwd *pswd_struct; /* Structur passwd file entry */ + + while ((pswd_struct = fgetpwent(fileread)) != NULL) + { + if (strcmp(pswd_struct->pw_name, namelogin) == 0){ break; } + } + + /* test if entry exist */ if (pswd_struct == NULL) {return 0;} else {return 1;} } -int main(int argc, char *argv[]) +static int verif_gid(int gidname) +{ + + FILE *fileread; + + fileread = fopen(patch_group, "r"); + struct group *group_struct; /* Structur group file entry */ + + while ((group_struct = fgetgrent(fileread)) != NULL) + { + if (group_struct->gr_gid == gidname){ break; } + } + + /* test if uid exist */ + if (group_struct == NULL) + {return 0;} + else + {return 1;} +} + +static int verif_grname(char *grname) +{ + + FILE *fileread; + + fileread = fopen(patch_group, "r"); + struct group *group_struct; /* Structur group file entry */ + + while ((group_struct = fgetgrent(fileread)) != NULL) + { + if (strcmp(group_struct->gr_name, grname) == 0){ break; } + } + + /* test if entry exist */ + if (group_struct == NULL) + {return 0;} + else + {return 1;} +} + +int main(int argc, char **argv) { /* Are you root ? */ root(); if(argc < 2) - option(); + usage(); - if(strcmp(argv[1], "-add") && - strcmp(argv[1], "-del") && - strcmp(argv[1], "-show")&& - strcmp(argv[1], "-gi")&& + if(strcmp(argv[1], "-a") && + strcmp(argv[1], "-A") && + strcmp(argv[1], "-s")&& + strcmp(argv[1], "-g")&& + strcmp(argv[1], "-G")&& + strcmp(argv[1], "-i")&& strcmp(argv[1], "-v")) - option(); + usage(); /* Option add user */ - if(!strcmp(argv[1], "-add")) + if(!strcmp(argv[1], "-a")) { if(argc < 5) - option_add(); + usage_add_user(); - /* Verification if uid exist in /etc/passwd */ + /* Checking if uid exist in /etc/passwd */ if(verif_uid(atoi(argv[3])) == 1){ - fprintf(stderr,"Error: Uid exist, please change uid.\n"); - exit(1); + fprintf(stderr,"Error: Uid exist, please change it.\n"); + exit(EXIT_UID); + } + + /* Checking if login name exist in /etc/passwd */ + if(verif_name(argv[2]) == 1){ + fprintf(stderr,"Error: Login name exist, please change it.\n"); + exit(EXIT_LOGIN); } FILE *fichier; @@ -295,14 +457,14 @@ gid = atoi(argv[4]); chown(argv[5], uid, gid); - } // [option -add] + } // [option -a] - if(!strcmp(argv[1], "-del")) + if(!strcmp(argv[1], "-A")) { if(argc < 3) - option_del(); + usage_del_user(); int login_line = 0; /* pour connaitre la ligne où ce situe le login*/ @@ -339,7 +501,7 @@ /* test if login exist */ if (pswd_struct == NULL){ fprintf(stderr,"Error: /etc/passwd - login not exist\n"); - exit(1); + exit(EXIT_LOGIN_NOT_EXIST); } if (pswd_struct != NULL){ @@ -361,20 +523,20 @@ /* test if login exist */ if (shad_struct == NULL){ fprintf(stderr,"Error: /etc/shadow - login not exist\n"); - exit(1); + exit(EXIT_LOGIN_NOT_EXIST); } if (shad_struct != NULL){ del_shadow(login_line); } - } // [option -del] + } // [option -A] - if(!strcmp(argv[1], "-show")) + if(!strcmp(argv[1], "-s")) { if(argc < 3) - option_show(); + usage_show(); struct passwd *pswd_struct; /* Structur passwd file entry */ struct spwd *shad_struct; /* Structur shadow file entry */ @@ -433,17 +595,17 @@ /* test if login exist */ if (getpwnam(argv[2]) == NULL){ fprintf(stderr,"Error: login not exist\n"); - exit(1); + exit(EXIT_LOGIN_NOT_EXIST); } } // [option -show] - if(!strcmp(argv[1], "-gi")) + if(!strcmp(argv[1], "-i")) { if(argc < 3) - option_gi(); + usage_group_info(); struct group *grou_struct; /* Structur group file entry */ @@ -466,9 +628,9 @@ while ((grou_struct = fgetgrent(fichier)) != NULL) if (strcmp(grou_struct->gr_name, argv[2]) == 0){ - fprintf(stdout, "\nGroup Informations\n================\n\n" + fprintf(stdout, "\nGroup Informations\n==================\n\n" "Group: %s\n" - "Gid: %d\n" + "Gid: %d\n\n" ,grou_struct->gr_name ,grou_struct->gr_gid); } @@ -477,15 +639,71 @@ /* test if group exist */ if (getgrnam(argv[2]) == NULL){ fprintf(stderr,"Error: group not exist\n"); - exit(1); + exit(EXIT_GROUP_NOT_EXIST); } - } // [option -ig] + } // [option -i] + + if(!strcmp(argv[1], "-g")) + { + if(argc < 4) + usage_add_group(); + + /* Checking if gid exist in /etc/group */ + if(verif_gid(atoi(argv[3])) == 1){ + fprintf(stderr,"Error: Gid exist, please change it.\n"); + exit(EXIT_GID); + } + + /* Checking if group name exist in /etc/group */ + if(verif_grname(argv[2]) == 1){ + fprintf(stderr,"Error: Group name exist, please change it.\n"); + exit(EXIT_GROUP); + } + + /* open file /etc/group */ + FILE *fichier; + fichier = fopen(patch_group,"a"); + + fprintf(fichier,"%s:x:%d:\n", argv[2], atoi(argv[3])); + fclose(fichier); + + } // option [-g] + + if(!strcmp(argv[1], "-G")) + { + if(argc < 3) + usage_del_group(); + + int group_line = 0; /* pour connaitre la ligne où ce situe le groupe*/ + FILE *fileread; + + fileread = fopen(patch_group, "r"); + struct group *group_struct; /* Structur group file entry */ + + while ((group_struct = fgetgrent(fileread)) != NULL) + { + group_line++; + if (strcmp(group_struct->gr_name, argv[2]) == 0){ break; } + } + + + /* test if login exist */ + if (group_struct == NULL){ + fprintf(stderr,"Error: /etc/group - Group name not exist\n"); + exit(EXIT_GROUP_NOT_EXIST); + } + + if (group_struct != NULL){ + del_group(group_line); + } + + } // option [-G] /* Version informations*/ if(!strcmp(argv[1], "-v")) version(); -return 0; +exit(EXIT_SUCCESS); }