-
Notifications
You must be signed in to change notification settings - Fork 69
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Notification of when the mount is ready #49
Comments
Here is an example of how I try to detect the mount #define FUSE_SUPER_MAGIC 0x65735546
static bool is_squashfuse_mount(const std::string& dir) {
// Check if the filesystem backing 'dir' is of type 'fuse'.
struct statfs fs;
if (0 != statfs(dir.c_str(), &fs)) {
std::cerr << "statfs:" << strerror(errno) << std::endl;
return false;
}
if (fs.f_type != FUSE_SUPER_MAGIC)
return false;
// Check if 'dir' is really a mountpoint
FILE *fd = setmntent("/proc/mounts", "re");
if (!fd) {
std::cerr << "setmntent:" << strerror(errno) << std::endl;
return false;
}
struct mntent me;
char buf[1024];
while (getmntent_r(fd, &me, (char*)&buf, sizeof(buf)) != NULL) {
// Check that squashfuse asked for the mount entry to be created,
// I've seen the names 'squashfuse' or 'lt-squashfuse' so far
if (me.mnt_dir == dir && strstr(me.mnt_fsname, "squashfuse") != NULL) {
endmntent(fd);
return true;
}
}
endmntent(fd);
return false;
}
|
For xarexec (our main use for squasfuse_ll), we use polling to find a file expected inside the filesystem. and and finally This works well for us in practice. Directly using/linking squashfuse might work but we've found the above to be robust (plus the mount persists after your process exits which, for us, combined with idle timeout, is ideal). |
Yeah, the FUSE API is a bit grotty, I wouldn't rely on calling functions in the FUSE layer and having them do what you want. (Calling lower-level squashfuse functions is fine.) If you were going to invoke squashfuse and receive some sort of notification, what side-channel would you want? |
A message on a pipe could work
To play with it, I've written out some toy code (with no error handling):
parent.c: #include <stdlib.h>
#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>
#include <string.h>
int main() {
int fildes[2];
pipe(fildes);
pid_t pid = fork();
if (pid == 0) {
char file_to_close[5];
snprintf(file_to_close, 5, "%d", fildes[1]);
execlp("fake-squashfuse", "squashfuse", "--pipe-notify", file_to_close, "-f", NULL);
perror("exec: ");
exit(1);
}
char buf[10];
read(fildes[0], buf, 10);
perror("parent read: ");
if (strncmp("mounted", buf, strlen("mounted")) == 0) {
printf("parent: mount message recieved!\n");
// do stuff with squashfuse mount!
exit(0);
}
return 1;
} fake-squashfuse.c: #include <stdlib.h>
#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>
#include <string.h>
int main(int argc, char* argv[]) {
if (argc < 3)
// usage: fake-squashfuse --pipe-notify pipe_to_close
exit(1);
int fd = atoi(argv[2]);
// do_the_mounting();
// Notify parent process that the mount is ready
char* msg = "mounted";
write(fd, msg, strlen(msg));
perror("child write: ");
close(fd);
return 0;
} I think a shell scripting user could use it too if we could provide a named pipe from Does this approach seem ok? |
Cute, I don't mind that! Can I see the WIP? |
This would sure be nice... |
Hopefully squashfuse will grow a proper notification of when a mountpoint is ready (vasi/squashfuse#49) but until then let's watch /proc/self/mountinfo while we wait. Signed-off-by: Serge Hallyn <[email protected]>
Apptainer could use this too. It is also polling currently. |
puzzlefs has this implemented |
Apptainer polls every 25 milliseconds looking for the mountpoint to show up in |
If the solution were available for squashfuse_ll, at least our user which mounts overlays of squashfuse (atomfs, and stacker, through atomfs) would use it. |
Add the notify_pipe option which allows the user to specify the path to a named pipe. When the mountpoint is ready, a message will be written to this pipe: 's' for success and 'f' for failure. To avoid blocking the fuse process until the pipe is read, a new process is spawned which performs a blocking operation on the pipe. In case of failure, the main process blocks until the pipe is read. Fixes vasi#49
Add the notify_pipe option which allows the user to specify the path to a named pipe. When the mountpoint is ready, a message will be written to this pipe: 's' for success and 'f' for failure. To avoid blocking the fuse process until the pipe is read, a new process is spawned which performs a blocking operation on the pipe. In case of failure, the main process blocks until the pipe is read. An example of operation is provided below: ``` set -x FIFO=$(mktemp -u) mkfifo "$FIFO" ./squashfuse_ll -o notify_pipe="$FIFO" -f /path/to/squashfs/archive /tmp/squash& STATUS=$(head -c1 "$FIFO") if [ "$STATUS" = "s" ]; then echo "Mountpoint contains:" ls /tmp/squash else echo "Mounting squashfuse on /tmp/squash failed" fi ``` Fixes vasi#49
Add the notify_pipe option which allows the user to specify the path to a named pipe. When the mountpoint is ready, a message will be written to this pipe: 's' for success and 'f' for failure. To avoid blocking the fuse process until the pipe is read, a new process is spawned which performs a blocking operation on the pipe. In case of mount failure, no additional process is created and the main process blocks until the pipe is read. An example of operation is provided below: ``` set -x FIFO=$(mktemp -u) mkfifo "$FIFO" ./squashfuse_ll -o notify_pipe="$FIFO" -f /path/to/squashfs/archive /tmp/squash& STATUS=$(head -c1 "$FIFO") if [ "$STATUS" = "s" ]; then echo "Mountpoint contains:" ls /tmp/squash else echo "Mounting squashfuse on /tmp/squash failed" fi ``` Fixes vasi#49
Add the notify_pipe option which allows the user to specify the path to a named pipe. When the mountpoint is ready, a message will be written to this pipe: 's' for success and 'f' for failure. To avoid blocking the fuse process until the pipe is read, a new process is spawned which performs a blocking operation on the pipe. In case of mount failure, no additional process is created and the main process blocks until the pipe is read. An example of operation is provided below: ``` set -x FIFO=$(mktemp -u) mkfifo "$FIFO" ./squashfuse_ll -o notify_pipe="$FIFO" -f /path/to/squashfs/archive /tmp/squash& STATUS=$(head -c1 "$FIFO") if [ "$STATUS" = "s" ]; then echo "Mountpoint contains:" ls /tmp/squash else echo "Mounting squashfuse on /tmp/squash failed" fi ``` Fixes vasi#49
Add the notify_pipe option which allows the user to specify the path to a named pipe. When the mountpoint is ready, a message will be written to this pipe: 's' for success and 'f' for failure. To avoid blocking the fuse process until the pipe is read, a new process is spawned which performs a blocking operation on the pipe. In case of mount failure, no additional process is created and the main process blocks until the pipe is read. An example of operation is provided below: ``` set -x FIFO=$(mktemp -u) mkfifo "$FIFO" ./squashfuse_ll -o notify_pipe="$FIFO" -f /path/to/squashfs/archive /tmp/squash& STATUS=$(head -c1 "$FIFO") if [ "$STATUS" = "s" ]; then echo "Mountpoint contains:" ls /tmp/squash else echo "Mounting squashfuse on /tmp/squash failed" fi ``` Fixes vasi#49
Add the notify_pipe option which allows the user to specify the path to a named pipe. When the mountpoint is ready, a message will be written to this pipe: 's' for success and 'f' for failure. To avoid blocking the fuse process until the pipe is read, a new process is spawned which performs a blocking operation on the pipe. In case of mount failure, no additional process is created and the main process blocks until the pipe is read. An example of operation is provided below: ``` set -x FIFO=$(mktemp -u) mkfifo "$FIFO" ./squashfuse_ll -o notify_pipe="$FIFO" -f /path/to/squashfs/archive /tmp/squash& STATUS=$(head -c1 "$FIFO") if [ "$STATUS" = "s" ]; then echo "Mountpoint contains:" ls /tmp/squash else echo "Mounting squashfuse on /tmp/squash failed" fi ``` Fixes vasi#49
When using squasfuse, check whether it supports -o notifypipe. If it does, use it instead our manual checking of the mountpoint inode. The notification mechanism is a better alternative to the existing polling approach. If it's not available, then use the old mechanism. This feature is supported starting from squasfuse version 0.5.0, see [1] for details. [1] vasi/squashfuse#49 Co-Developed-by: Serge Hallyn <[email protected]> Signed-off-by: Ariel Miculas <[email protected]>
When using squasfuse, check whether it supports -o notifypipe. If it does, use it instead our manual checking of the mountpoint inode. The notification mechanism is a better alternative to the existing polling approach. If it's not available, then use the old mechanism. This feature is supported starting from squasfuse version 0.5.0, see [1] for details. [1] vasi/squashfuse#49 Co-Developed-by: Serge Hallyn <[email protected]> Signed-off-by: Ariel Miculas <[email protected]>
When using squasfuse, check whether it supports -o notifypipe. If it does, use it instead our manual checking of the mountpoint inode. The notification mechanism is a better alternative to the existing polling approach. If it's not available, then use the old mechanism. This feature is supported starting from squasfuse version 0.5.0, see [1] for details. [1] vasi/squashfuse#49 Co-Developed-by: Serge Hallyn <[email protected]> Signed-off-by: Ariel Miculas <[email protected]>
When using squasfuse, check whether it supports -o notifypipe. If it does, use it instead our manual checking of the mountpoint inode. The notification mechanism is a better alternative to the existing polling approach. If it's not available, then use the old mechanism. This feature is supported starting from squasfuse version 0.5.0, see [1] for details. [1] vasi/squashfuse#49 Co-Developed-by: Serge Hallyn <[email protected]> Signed-off-by: Ariel Miculas <[email protected]>
Hi,
Is there a recommended way to know if the mount is ready once squashfuse starts?
In an application, I'm
fork()
ing out to squashfuse (with the-f
option) then trying to use calls likestatfs
/getmntent
in a polling loop to check if the mount point is ready to use, so that I don't race ahead and find an empty mountpoint.Should I skip forking out to squashfuse and just call functions like
sqfs_ll_mount
directly?Thanks
Matthew
The text was updated successfully, but these errors were encountered: