From 0c3ec12ca530d73203590da784ecc484c5f02036 Mon Sep 17 00:00:00 2001 From: Your Name Date: Mon, 6 Nov 2023 18:32:22 +0300 Subject: [PATCH] chgrp --- TODO | 2 - coreutils/chgrp.c | 113 +++++++++++++++++++++++++++++++++++++++++ coreutils/chmod.c | 5 +- coreutils/tee.c | 6 +++ coreutils/truncate.c | 5 ++ miscutils/getloadavg.c | 13 ----- 6 files changed, 128 insertions(+), 16 deletions(-) create mode 100644 coreutils/chgrp.c create mode 100644 coreutils/tee.c delete mode 100644 miscutils/getloadavg.c diff --git a/TODO b/TODO index 82c586b..f703c37 100644 --- a/TODO +++ b/TODO @@ -11,7 +11,6 @@ renice nohup split date -tee tr cut shuf @@ -23,7 +22,6 @@ stat sort test tar -chgrp Other: kill diff --git a/coreutils/chgrp.c b/coreutils/chgrp.c new file mode 100644 index 0000000..35ea83b --- /dev/null +++ b/coreutils/chgrp.c @@ -0,0 +1,113 @@ +#include +#include +#include +#include +#include +#include +#include +#include "make_path.h" +#include "get_stat.h" + +int (*get_stat)(const char *prog_name, const char *path, struct stat *stat_path); +unsigned int r_flag; +unsigned int s_flag; +struct group *grp; + +int change(const char *file) { + struct stat stat_path; + if (mu_get_stat("chgrp", file, &stat_path)) + return 1; + + if (lchown(file, stat_path.st_uid, grp->gr_gid)) { + if (!s_flag) + fprintf(stderr, "chgrp: %s: %s\n", file, strerror(errno)); + + return 1; + } + + return 0; +} + +int chtree(const char *dst) { + int ret = change(dst); + + struct stat stat_path; + if (get_stat("chgrp", dst, &stat_path)) + return 1; + + if (!S_ISDIR(stat_path.st_mode) || !r_flag) + return ret; + + DIR *dir = opendir(dst); + if (dir == NULL) { + if (!s_flag) + fprintf(stderr, "chgrp: %s: Can`t open directory\n", dst); + + return 1; + } + + struct dirent *ep; + while ((ep = readdir(dir)) != NULL) { + if (!strcmp(ep->d_name, ".") || !strcmp(ep->d_name, "..")) + continue; + + char *full_path = mu_make_path("chgrp", dst, ep->d_name); + if (full_path == NULL) + continue; + + if (chtree(full_path)) + ret = 1; + + free(full_path); + } + + closedir(dir); + return ret; +} + +int main(int argc, char **argv) { + int i; + + get_stat = mu_get_lstat; + for (i = 1; i < argc; i++) { + if (argv[i][0] != '-') + break; + + else if (!strcmp(argv[i], "-r")) + r_flag = 1; + + else if (!strcmp(argv[i], "-s") || !strcmp(argv[i], "-f")) + s_flag = 1; + + else if (!strcmp(argv[i], "-H")) + get_stat = mu_get_stat; + + else if (!strcmp(argv[i], "--help")) { + printf("chgrp [-H if a command line argument is a symbolic link] [-r recursive] [-s silent] [group] [file1 file2...]\n"); + return 0; + } + } + + if (argc - i < 2) { + fprintf(stderr, "chgrp: missing operand\n"); + return 1; + } + + grp = getgrnam(argv[i]); + if (!grp) { + fprintf(stderr, "chgrp: unknow group\n"); + return 1; + } + + argv++; + argc--; + + int ret = 0; + for (; i < argc; i++) + if (chtree(argv[i])) + ret = 1; + + return ret; +} + + diff --git a/coreutils/chmod.c b/coreutils/chmod.c index d45f3da..ed4cc50 100644 --- a/coreutils/chmod.c +++ b/coreutils/chmod.c @@ -19,7 +19,9 @@ int change(const char *file, const char *mode_arg) { mode_t mode = mu_parse_mode(mode_arg, old_file.st_mode); if (chmod(file, mode) != 0) { - fprintf(stderr, "chmod: unable to chown %s: %s\n", file, strerror(errno)); + if (!s_flag) + fprintf(stderr, "chmod: unable to chown %s: %s\n", file, strerror(errno)); + return 1; } @@ -40,6 +42,7 @@ int chtree(const char *dst, const char *mode_arg) { if (dir == NULL) { if (!s_flag) fprintf(stderr, "chown: %s: Can`t open directory\n", dst); + return 1; } diff --git a/coreutils/tee.c b/coreutils/tee.c new file mode 100644 index 0000000..fb11188 --- /dev/null +++ b/coreutils/tee.c @@ -0,0 +1,6 @@ +#include + +int main(const int argc, const char **argv) { + + return 0; +} diff --git a/coreutils/truncate.c b/coreutils/truncate.c index 3eee63a..f17172f 100644 --- a/coreutils/truncate.c +++ b/coreutils/truncate.c @@ -26,6 +26,11 @@ int main(const int argc, const char **argv) { } } + if (argc - i == 0) { + fprintf(stderr, "truncate: missing operand\n"); + return 1; + } + int flags = O_WRONLY | O_NONBLOCK; if (!c_flag) flags |= O_CREAT; diff --git a/miscutils/getloadavg.c b/miscutils/getloadavg.c deleted file mode 100644 index 0569f5f..0000000 --- a/miscutils/getloadavg.c +++ /dev/null @@ -1,13 +0,0 @@ -#include -#include - -int main(void) { - double avg[3] = {0, 0, 0}; - - if (getloadavg(avg, sizeof(avg) / sizeof(avg[0])) < 0) { - fprintf(stderr, "getloadavg: getloadavg() failed\n"); - return 1; - } - - printf("%.2f %.2f %.2f\n", avg[0], avg[1], avg[2]); -}