Index: Makefile =================================================================== RCS file: /home/ncvs/src/usr.bin/xinstall/Makefile,v retrieving revision 1.18 diff -u -r1.18 Makefile --- Makefile 12 Dec 2001 08:49:51 -0000 1.18 +++ Makefile 1 Feb 2002 15:45:39 -0000 @@ -10,6 +10,10 @@ .PATH: ${.CURDIR}/../../lib/libc/gen SRCS+= strtofflags.c NO_WERROR= yes +.else +.PATH: ${.CURDIR}/../../bin/setfacl +CFLAGS+= -DWANT_ACL -I${.CURDIR}/../../bin/setfacl +SRCS+= merge.c .endif .include Index: install.1 =================================================================== RCS file: /home/ncvs/src/usr.bin/xinstall/install.1,v retrieving revision 1.23 diff -u -r1.23 install.1 --- install.1 23 Oct 2001 00:47:27 -0000 1.23 +++ install.1 1 Feb 2002 15:45:39 -0000 @@ -42,6 +42,7 @@ .Nm .Op Fl bCcMpSsv .Op Fl B Ar suffix +.Op Fl a Ar access acl .Op Fl f Ar flags .Op Fl g Ar group .Op Fl m Ar mode @@ -50,6 +51,7 @@ .Nm .Op Fl bCcMpSsv .Op Fl B Ar suffix +.Op Fl a Ar access acl .Op Fl f Ar flags .Op Fl g Ar group .Op Fl m Ar mode @@ -58,6 +60,8 @@ .Nm .Fl d .Op Fl v +.Op Fl A Ar default acl +.Op Fl a Ar access acl .Op Fl g Ar group .Op Fl m Ar mode .Op Fl o Ar owner @@ -84,6 +88,19 @@ .Pp The options are as follows: .Bl -tag -width indent +.It Fl A +Specify the default ACL to be applied. Currently only directories +support default ACLs and the +.Ar default acl +must be complete and valid. +.It Fl a +Specify the access ACL to be merged. +.It Fl B Ar suffix +Use +.Ar suffix +as the backup suffix if +.Fl b +is given. .It Fl b Back up any existing files before overwriting them by renaming them to @@ -91,12 +108,6 @@ See .Fl B for specifying a different backup suffix. -.It Fl B Ar suffix -Use -.Ar suffix -as the backup suffix if -.Fl b -is given. .It Fl C Copy the file. If the target file already exists and the files are the same, Index: xinstall.c =================================================================== RCS file: /home/ncvs/src/usr.bin/xinstall/xinstall.c,v retrieving revision 1.47 diff -u -r1.47 xinstall.c --- xinstall.c 19 Dec 2001 06:05:42 -0000 1.47 +++ xinstall.c 1 Feb 2002 15:45:39 -0000 @@ -48,6 +48,9 @@ #endif #include +#ifdef WANT_ACL +#include +#endif #include #include #include @@ -68,6 +71,9 @@ #include #include "pathnames.h" +#ifdef WANT_ACL +#include "setfacl.h" +#endif /* Bootstrap aid - this doesn't exist in most older releases */ #ifndef MAP_FAILED @@ -86,6 +92,9 @@ int dobackup, docompare, dodir, dopreserve, dostrip, nommap, safecopy, verbose; mode_t mode = S_IRWXU | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH; const char *suffix = BACKUP_SUFFIX; +#ifdef WANT_ACL +acl_t acc_acl, def_acl; +#endif void copy __P((int, const char *, int, const char *, off_t)); int compare __P((int, const char *, size_t, int, const char *, size_t)); @@ -110,11 +119,30 @@ u_int iflags; char *flags; const char *group, *owner, *to_name; +#ifdef WANT_ACL + char *acc_acl_txt, *def_acl_txt; + acc_acl = def_acl = NULL; + acc_acl_txt = def_acl_txt = NULL; +#endif iflags = 0; group = owner = NULL; - while ((ch = getopt(argc, argv, "B:bCcdf:g:Mm:o:pSsv")) != -1) + while ((ch = getopt(argc, argv, "A:a:B:bCcdf:g:Mm:o:pSsv")) != -1) switch((char)ch) { + case 'A': +#ifdef WANT_ACL + def_acl_txt = optarg; +#else + warnx("ACL support has not been compiled in"); +#endif + break; + case 'a': +#ifdef WANT_ACL + acc_acl_txt = optarg; +#else + warnx("ACL support has not been compiled in"); +#endif + break; case 'B': suffix = optarg; /* FALLTHROUGH */ @@ -190,6 +218,26 @@ if (docompare && dostrip) safecopy = 1; +#ifdef WANT_ACL + /* default ACLs can only be applied to directories */ + if (def_acl_txt != NULL && dodir != 1) + usage(); + + /* convert ACLs from text */ + if (def_acl_txt != NULL) { + def_acl = acl_from_text(def_acl_txt); + if (def_acl == NULL) + err(1, "invalid default ACL"); + if (acl_valid(def_acl) == -1) + errx(1, "invalid default ACL"); + } + if (acc_acl_txt != NULL) { + acc_acl = acl_from_text(acc_acl_txt); + if (acc_acl == NULL) + err(1, "invalid access ACL"); + } +#endif + /* get group and owner id's */ if (group != NULL) { if ((gp = getgrnam(group)) != NULL) @@ -273,12 +321,16 @@ u_long fset; u_int flags; { +#ifdef WANT_ACL + acl_t acl[2]; +#endif struct stat from_sb, temp_sb, to_sb; struct utimbuf utb; int devnull, files_match, from_fd, serrno, target; int tempcopy, temp_fd, to_fd; char backup[MAXPATHLEN], *p, pathbuf[MAXPATHLEN], tempfile[MAXPATHLEN]; + from_fd = to_fd = -1; files_match = 0; /* If try to install NULL file to a directory, fails. */ @@ -506,6 +558,25 @@ } } } +#ifdef WANT_ACL + if (acc_acl != NULL) { + acl[ACCESS_ACL] = acl_get_file(from_name, ACL_TYPE_ACCESS); + if (acl[ACCESS_ACL] == NULL) { + if (errno != EOPNOTSUPP) + err(1, "failed to retrieve access ACL from %s", + from_name); + } else { + acl_type = ACL_TYPE_ACCESS; + if (merge_acl(acc_acl, acl) != 0) + err(1, "failed to merge access ACLs"); + if (acl_calc_mask(&acl[ACCESS_ACL]) == -1) + err(1, "failed to calculate access ACL mask"); + if (acl_set_fd(to_fd, acl[ACCESS_ACL]) == -1) + warn("failed to set access ACL on %s", to_name); + acl_free(acl[ACCESS_ACL]); + } + } +#endif (void)close(to_fd); if (!devnull) @@ -730,6 +801,9 @@ install_dir(path) char *path; { +#ifdef WANT_ACL + acl_t acl[2]; +#endif register char *p; struct stat sb; int ch; @@ -755,6 +829,31 @@ warn("chown %u:%u %s", uid, gid, path); if (chmod(path, mode)) warn("chmod %o %s", mode, path); +#ifdef WANT_ACL + if (def_acl != NULL) { + if (acl_set_file(path, ACL_TYPE_DEFAULT, def_acl) == -1) + warn("failed to set default ACL on %s", path); + } + + if (acc_acl != NULL) { + acl[ACCESS_ACL] = acl_get_file(path, ACL_TYPE_ACCESS); + if (acl[ACCESS_ACL] == NULL) { + if (errno != EOPNOTSUPP) + err(1, "failed to retrieve access ACL from %s", + path); + } else { + acl_type = ACL_TYPE_ACCESS; + if (merge_acl(acc_acl, acl) != 0) + err(1, "failed to merge access ACLs"); + if (acl_calc_mask(&acl[ACCESS_ACL]) == -1) + err(1, "failed to calculate access ACL mask"); + if (acl_set_file(path, ACL_TYPE_ACCESS, acl[ACCESS_ACL]) + == -1) + warn("failed to set access ACL on %s", path); + acl_free(acl[ACCESS_ACL]); + } + } +#endif } /* @@ -765,11 +864,12 @@ usage() { (void)fprintf(stderr, "\ -usage: install [-bCcpSsv] [-B suffix] [-f flags] [-g group] [-m mode]\n\ - [-o owner] file1 file2\n\ - install [-bCcpSsv] [-B suffix] [-f flags] [-g group] [-m mode]\n\ - [-o owner] file1 ... fileN directory\n\ - install -d [-v] [-g group] [-m mode] [-o owner] directory ...\n"); +usage: install [-bCcpSsv] [-a access acl] [-B suffix] [-f flags] [-g group]\n\ + [-m mode] [-o owner] file1 file2\n\ + install [-bCcpSsv] [-a access acl] [-B suffix] [-f flags] [-g group]\n\ + [-m mode] [-o owner] file1 ... fileN directory\n\ + install -d [-v] [-A default acl] [-a access acl] [-g group] [-m mode]\n\ + [-o owner] directory ...\n"); exit(EX_USAGE); /* NOTREACHED */ }