-
Notifications
You must be signed in to change notification settings - Fork 20
Try to preserve current working directory #48
Changes from 4 commits
a39fb3f
93c9ff2
6f58c38
42c7bad
912a5a0
0e690b3
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,21 @@ | ||
summary: Regression check for https://bugs.launchpad.net/snap-confine/+bug/1595444 | ||
# This is blacklisted on debian because we first have to get the dpkg-vendor patches | ||
systems: [-debian-8] | ||
execute: | | ||
echo "Having installed the snapd-hacker-toolbelt snap" | ||
snap list | grep -q snapd-hacker-toolbelt || snap install snapd-hacker-toolbelt | ||
|
||
echo "We can go to a location that is available in all snaps (/tmp)" | ||
echo "We can run the 'cwd' tool from busybox and it reports /tmp" | ||
[ "$(cd /tmp && /snap/bin/snapd-hacker-toolbelt.busybox pwd)" = "/tmp" ] | ||
|
||
echo "But if we go to a location that is not available to snaps (e.g. $HOME/.cache)" | ||
echo "Then the same 'cwd' tool refuses to run the snap" | ||
mkdir -p "$HOME/.cache/" | ||
cd "$HOME/.cache" || exit 1 | ||
# pwd doesn't run | ||
[ "$(/snap/bin/snapd-hacker-toolbelt.busybox pwd)" = "" ] | ||
# there's an accurate error message | ||
[ "$(/snap/bin/snapd-hacker-toolbelt.busybox pwd 2>&1)" = "cannot remain in $HOME/.cache, please run this snap from another location" ] | ||
# snap-confine returns an error code on exit | ||
! /snap/bin/snapd-hacker-toolbelt.busybox pwd |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -86,6 +86,13 @@ int main(int argc, char **argv) | |
// this launcher | ||
setup_slave_mount_namespace(); | ||
|
||
// Get the current working directory before we start fiddling with | ||
// mounts and possibly pivot_root. At the end of the whole process, we | ||
// will try to re-locate to the same directory (if possible). | ||
char vanilla_cwd[512]; | ||
if (getcwd(vanilla_cwd, sizeof vanilla_cwd) == NULL) { | ||
die("cannot get the current working directory"); | ||
} | ||
// do the mounting if run on a non-native snappy system | ||
if (is_running_on_classic_distribution()) { | ||
setup_snappy_os_mounts(); | ||
|
@@ -104,6 +111,15 @@ int main(int argc, char **argv) | |
snappy_udev_cleanup(&udev_s); | ||
#endif // ifdef STRICT_CONFINEMENT | ||
|
||
// Try to re-locate back to vanilla working directory. This can fail | ||
// because that directory is no longer present. | ||
if (chdir(vanilla_cwd) != 0) { | ||
// NOTE: Use exit rather than die as this produces a more refined error message | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Hm, I wonder if the perror() from die() might be interessting here for the user. E.g. to see that its a permsision denied error vs a not-exit error and the like. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Hmm, I can switch back to die, given that we run as root the only cause for this to fail might be apparmor. In any case, I'll switch to die and we'll see. |
||
fprintf(stderr, | ||
"cannot remain in %s, please run this snap from another location\n", | ||
vanilla_cwd); | ||
exit(1); | ||
} | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Since we are die()ing, LGTM with the get_current_dir_name() change. |
||
// the rest does not so temporarily drop privs back to calling | ||
// user (we'll permanently drop after loading seccomp) | ||
if (setegid(real_gid) != 0) | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I suggest using get_current_dir_name() instead of getcwd(), like we do in mount-support.c. This has the advantage of not having to pick an arbitrary size for vanilla_cwd but does mean you need to free() the result.