我正在尝试寻找一种标准的 POSIX 方法来将一个文件的权限复制到另一个文件。在 GNU 系统上,这很容易:
[alexmchale@bullfrog ~]$ ls -l hardcopy.*
-rw-r--r-- 1 alexmchale users 2972 Jul 8 20:40 hardcopy.1
---------- 1 alexmchale users 2824 May 14 13:45 hardcopy.4
[alexmchale@bullfrog ~]$ chmod --reference=hardcopy.1 hardcopy.4
[alexmchale@bullfrog ~]$ ls -l hardcopy.*
-rw-r--r-- 1 alexmchale users 2972 Jul 8 20:40 hardcopy.1
-rw-r--r-- 1 alexmchale users 2824 May 14 13:45 hardcopy.4
不幸的是,chmod 的 --reference 标志是非标准选项。因此,这不符合我的目的。我希望它是一行代码,但这不是必需的。最终,它确实需要采用 POSIX sh 语法。
答案1
一个诱惑就是解析ls
。避免这种诱惑。
下面的似乎有效,但它充满了 Kluge。它依赖于cp
保留目标文件的权限。对于此演示,文件“模板”必须不存在。
- 将文件复制到所需的权限新的文件
- 将要更改的文件复制到上一步创建的文件中
- 删除要更改的原始文件
- 将中间文件重命名为要更改的文件的名称
演示:
$ echo "contents of has">has
$ echo "contents of wants">wants
$ chmod ug+x has # just so it's different - represents the desired permissions
$ cp has template
$ cat has
contents of has
$ cat wants
contents of wants
$ cat template
contents of has
$ ls -l has wants template
-rwxr-xr-- 1 user user 16 2010-07-31 09:22 has
-rwxr-xr-- 1 user user 16 2010-07-31 09:23 template
-rw-r--r-- 1 user user 18 2010-07-31 09:22 wants
$ cp wants template
$ ls -l has wants template
-rwxr-xr-- 1 user user 16 2010-07-31 09:22 has
-rwxr-xr-- 1 user user 18 2010-07-31 09:24 template
-rw-r--r-- 1 user user 18 2010-07-31 09:22 wants
$ cat template
contents of wants
$ rm wants
$ mv template wants
$ ls -l has wants
-rwxr-xr-- 1 user user 16 2010-07-31 09:22 has
-rwxr-xr-- 1 user user 18 2010-07-31 09:24 wants
$ cat has
contents of has
$ cat wants
contents of wants
答案2
您可以使用以下stat
命令获取文件权限:
Mac OS X(BSD)语法:
chmod `stat -f %A fileWithPerm` fileToSetPerm
Linux 语法(不确定):
chmod `stat -c %a fileWithPerm` fileToSetPerm
这`符号是反引号。
答案3
ACL 实用程序获取函数和设置可用于此目的,但我不知道它是否足够符合 POSIX 标准。至少在 FreeBSD 8.0 和 Linux 中可以工作,但另一方面,可能必须安装 ACL 实用程序。
来自手册页:
getfacl file1 | setfacl -b -n -M - file2
Copy ACL entries from file1 to file2.
我认为 getfacl 和 setfacl 除了可以操作 ACL 之外,还可以操作标准文件权限。
答案4
一种可移植的、直接的方法不是标准实用程序 - 您需要在模板文件上调用 stat(),然后在目标文件上调用 chmod()。这意味着使用 C 之类的语言或另一种广泛使用的语言(如 perl)。
文件访问权限在 struct stat st_mode 成员中由 0007777 位指定。Dennis 的解决方案是正确的,如果 I/O 有点重,那么对于非常大的文件,它可能会失败:
cp has template
考虑这个尚未准备好生产的示例:
#include <sys/types.h>
#include <sys/stat.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <errno.h>
mode_t
getperm(const char *template_file)
{
struct stat st;
if(stat(template_file, &st)==-1)
{
perror("Cannot stat file");
exit(1);
}
return st.st_mode;
}
int main(int argc, char **argv)
{
mode_t mode=getperm(argv[1]);
int i=0;
for(i=2; argv[i]!=NULL; i++)
{
if(chmod(argv[i], mode)==-1)
fprintf(stderr, "Permissions failed on %s:\n\t%s\n",
argv[i], strerror(errno));
}
return 0;
}