[Toybox] How do I tell cyanogenmod they're wrong?

Rob Landley rob at landley.net
Tue May 31 15:36:59 PDT 2016


On 05/31/2016 12:03 PM, Tom Marshall wrote:
> In your example below, the permission denied message and subsequent
> failure exit code are the result of EACCES on open(2).  The issue we had
> was when file copying succeeded but the subsequent chown(2) fails.

$ sudo /bin/bash
[sudo] password for landley:
# ./mount vfat.img vfat
# cp -a todo vfat/todo2
cp: failed to preserve ownership for ‘vfat/todo2/attachment.bin.4’:
Operation not permitted
cp: failed to preserve ownership for ‘vfat/todo2/attachment-0002.bin’:
Operation not permitted
cp: failed to preserve ownership for ‘vfat/todo2/netstat.patch’:
Operation not permitted
cp: failed to preserve ownership for ‘vfat/todo2/githash.patch’:
Operation not permitted
cp: failed to preserve ownership for ‘vfat/todo2/expr.patch’: Operation
not permitted
...

Just tried again, it's saying "failed to preserve ownership". There is a
vfat/todo2 directory full of files after I do that...

> This can be demonstrated on stock Ubuntu 14.04 as follows:
> 
> $ sudo touch foo
> $ cp -a foo bar

Ah, I see: cp -a doesn't attempt to preserve ownership for non-root
users (because it can't). So that's an _expected_ failure.

Blah, I knew that and didn't implement it (because the man page doesn't
mention it and I was going by the man page).

> $ echo $?
> 0
> $ ls -l foo bar
> -rw-r--r-- 1 tdm  tdm  0 May 31 18:59 bar
> -rw-r--r-- 1 root root 0 May 31 18:59 foo
> 
> I can't say that this is correct or even necessarily desirable, but it
> is indeed what coreutils does.

It's correct not to complain if a normal user can't preserve ownership.
It's wrong not to complain if ROOT can't preserve ownership.

> Also note that in your example below, you are using VFAT.  The bug in
> question regards the OnePlus One.  It does not use VFAT (no sdcard), it
> uses ext4 (or possibly f2fs, but mostly ext4).

The test I did was creating an environment where root could not preserve
ownership. I used vfat precisely because it doesn't track ownership, and
thus all files are owned by whoever mounted the filesystem. (I.E.
creating the "this fails when it was expected to work" case.)

The next question is, should it _attempt_ to chown if geteuid() isn't 0?
Let's try cp -a /etc/init.d blah as a normal user, and it looks like...

lstat("/etc/init.d/pulseaudio", {st_mode=S_IFREG|0755, st_size=2182,
...}) = 0
open("/etc/init.d/pulseaudio", O_RDONLY|O_NOFOLLOW) = 3
fstat(3, {st_mode=S_IFREG|0755, st_size=2182, ...}) = 0
open("blah/pulseaudio", O_WRONLY|O_CREAT|O_EXCL, 0700) = 4
fstat(4, {st_mode=S_IFREG|0700, st_size=0, ...}) = 0
fadvise64(3, 0, 0, POSIX_FADV_SEQUENTIAL) = 0
read(3, "#!/bin/sh -e\n### BEGIN INIT INFO"..., 65536) = 2182
write(4, "#!/bin/sh -e\n### BEGIN INIT INFO"..., 2182) = 2182
read(3, "", 65536)                      = 0
utimensat(4, NULL, {{1396597239, 0}, {1396597239, 0}}, 0) = 0
fchown(4, 0, 0)                         = -1 EPERM (Operation not permitted)
fchown(4, 4294967295, 0)                = -1 EPERM (Operation not permitted)
flistxattr(3, NULL, 0)                  = 0
flistxattr(3, "", 0)                    = 0
fgetxattr(3, "system.posix_acl_access", 0x7ffcf2bb1ff0, 132) = -1
ENODATA (No data available)
fstat(3, {st_mode=S_IFREG|0755, st_size=2182, ...}) = 0
fsetxattr(4, "system.posix_acl_access",
"\x02\x00\x00\x00\x01\x00\x07\x00\xff\xff\xff\xff\x04\x00\x05\x00\xff\xff\xff\xff
\x00\x05\x00\xff\xff\xff\xff", 28, 0) = 0
close(4)                                = 0
close(3)                                = 0

Yup, it still tries it, it just silently fails for non-root. (Why on
EARTH it tries to change it to -1 the second time, I couldn't tell you.)

Hmmm, adding a test for this is one of those things requiring root
access (so I can _create_ a file with different ownership, then have the
chown fail and see it doesn't emit an error message). Note added to the
pile...

Thanks,

Rob




More information about the Toybox mailing list