📄 crontab.c
字号:
#include <errno.h>#include <fcntl.h>#include <signal.h>#include <sys/file.h>#include <sys/stat.h>#include <sys/ipc.h>#include <sys/sem.h>#include <unistd.h>#include <time.h>#include <utime.h>#include <stdio.h>#include <pwd.h>#include <unistd.h>#include <string.h>#include <dirent.h>#include <errno.h>#include <sys/types.h>#include <sys/wait.h>#include "crontab.h"static struct passwd *pw;static char *User;static char *RealUser;static char ProgramName[] = "my_crontab";static enum opt_t Option;static char Filename[MAX_FNAME];static char Directory[MAX_FNAME];static FILE *NewCrontab = NULL;static pid_t Pid;static char *getoptarg = "u:ler";static char tn[MAX_FNAME];static void usage(char *msg){ fprintf(stderr, "%s: usage error: %s\n", ProgramName, msg); fprintf(stderr, "usage:\t%s [-u user] file\n", ProgramName); fprintf(stderr, "\t%s [-u user] { -e | -l | -r }\n", ProgramName); fprintf(stderr, "\t\t(default operation is replace, per 1003.2)\n"); fprintf(stderr, "\t-e\t(edit user's crontab)\n"); fprintf(stderr, "\t-l\t(list user's crontab)\n"); fprintf(stderr, "\t-r\t(delete user's crontab)\n"); exit(0);}static void parse_args(int argc,char **argv){ int argch; struct stat statbuf; /* get the user id */ if (!(pw = getpwuid(getuid()))) { fprintf(stderr, "%s: your UID isn't in the passwd file.\n", ProgramName); fprintf(stderr, "bailing out.\n"); exit(1); } /* dup the user id*/ if (((User=strdup(pw->pw_name)) == NULL)) { fprintf(stderr, "Memory allocation error\n"); exit(1); } Filename[0] = '\0'; Option = opt_unknown; while ((argch = getopt(argc, argv, getoptarg)) != EOF) { switch (argch) { case 'u': /*return a pointer to a structure containing the broken field of a line from etc/passwd for the entry that match the user name*/ if (!(pw = getpwnam(optarg)))/*check if the user is efficiency*/ { fprintf(stderr, "%s: user `%s' unknown\n", ProgramName, optarg); exit(1); } /*if the user is root and the user is not the name after -u*/ if ((getuid() != ROOT_UID) && (getuid() != pw->pw_uid)) { fprintf(stderr, "Your are not root or the user that own this crontab\n"); exit(1); } free(User); if ((User=strdup(pw->pw_name)) == NULL) { fprintf(stderr, "Memory allocation error\n"); exit(1); } break; case 'l': if (Option != opt_unknown) usage("only one operation permitted"); Option = opt_list; break; case 'r': if (Option != opt_unknown) usage("only one operation permitted"); Option = opt_delete; break; case 'e': if (Option != opt_unknown) usage("only one operation permitted"); Option = opt_edit; break; default: usage("unrecognized option"); } } endpwent(); if (Option != opt_unknown) { if (argv[optind] != NULL) { usage("no arguments permitted after this option"); } } else { if (argv[optind] != NULL) { Option = opt_replace; (void) strncpy (Filename, argv[optind], (sizeof Filename)-1); Filename[(sizeof Filename)-1] = '\0'; } else { usage("file name must be specified for replace"); } } if (Option == opt_replace) { if (!(NewCrontab = fopen(Filename, "r"))) { perror(Filename); exit(1); } /* Make sure we opened a normal file. */ if (fstat(fileno(NewCrontab), &statbuf) < 0) { perror("fstat"); exit(1); } if (!S_ISREG(statbuf.st_mode)) { fprintf(stderr, "%s: Not a regular file.\n", Filename); exit(1); } }}/******************************* cmd here *******************************/static void list_cmd(){ FILE *f; int ch; char n[MAX_FNAME]; (void) snprintf(n, MAX_FNAME, CRON_TAB(User)); if (!(f = fopen(n, "r"))) { /*no such file or dir*/ if (errno == ENOENT) fprintf(stderr, "no crontab for %s\n", User); else perror(n); exit(1); } while (EOF != (ch = getc(f))) putchar(ch); fclose(f);}static void delete_cmd(){ char n[MAX_FNAME]; (void) snprintf(n, MAX_FNAME, CRON_TAB(User)); if (unlink(n)) { if (errno == ENOENT) fprintf(stderr, "no crontab for %s\n", User); else perror(n); exit(1); } //poke_daemon();}static int get_next_token(char *buffer,char *line,int *pt){ int i = 0; while (line[*pt] == ' ' || line[*pt] == '\t') { (*pt)++; } if (line[*pt] == ',') { (*pt)++; return 4; } else if (isdigit(line[*pt])) { buffer[i++] = line[*pt]; (*pt)++; while (isdigit(line[*pt])) { buffer[i++] = line[*pt]; (*pt)++; } if (line[*pt] == ',') { buffer[i] = '\0'; (*pt)++; return 3; } else if (line[*pt] == ' ' || line[*pt] == '\t') { buffer[i] = '\0'; while(line[*pt] == ' ' || line[*pt] == '\t') (*pt)++; if(line[*pt] == ',') { (*pt)++; return 3; } else return 1; } else { return 5; } } else if (line[*pt] == '*') { (*pt)++; return 2; } else { return 5; }}static int check_number(char *buffer,int i){ int num; int value[5][2] = {{0,59},{0,23},{1,31},{1,12},{0,6}}; num = atoi(buffer); if(num >= value[i][0] && num <= value[i][1]) return 1; else return 0;}static int check_error(){ char line[MAX_LINE]; char buffer[MAX_FNAME]; char * f; int pt = 0; int i = 0; int flag = 0; int can_gets = 0; int finish = 0; while((f = fgets(line,MAX_LINE,NewCrontab)) != NULL) { can_gets = 1; pt = 0; /****** to see if the line is an empty line or a comment line **/ while(line[pt] == ' ' || line[pt] == '\t') pt++; if(line[pt] == '#' || line[pt] == '\n') continue; /*************** divide the date in to five part *****************/ for(; i < 5; i++) { finish = 0; while(1) { flag = get_next_token(buffer,line,&pt); switch(flag) { case 1: if(!check_number(buffer,i)) { fprintf(stderr,"%s\n",line); fprintf(stderr,"Some of the number of your crontab is excess the legal range.\n"); fprintf(stderr,"1) Minute: 0 ~ 59.\n"); fprintf(stderr,"2) Hour: 0 ~ 23.\n"); fprintf(stderr,"3) Day of month: 1 ~ 31.\n"); fprintf(stderr,"4) Month of year: 1 ~ 12.\n"); fprintf(stderr,"5) Day of week: 0 ~ 6.\n"); return 0; } finish = 1; break; case 2: finish = 1; break; case 3: finish = 0; if(!check_number(buffer,i)) { fprintf(stderr,"%s\n",line); fprintf(stderr,"Some of the number of your crontab is excess the legal range!\n"); return 0; } break; case 4: fprintf(stderr,"%s\n",line); fprintf(stderr,"Empty term is not allow!\n"); return 0; break; case 5: fprintf(stderr,"%s\n",line); fprintf(stderr,"Unexpected word here!\n"); return 0; break; default: return 0; break; } if(finish) break; } } i = 0; } return 1;}static int replace_cmd(){ char n[MAX_FNAME], envstr[MAX_ENVSTR]; FILE *tmp; int ch, eof, fd; int markfd;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -