FlatImage
A configurable Linux containerization system
Loading...
Searching...
No Matches
fuse.hpp
Go to the documentation of this file.
1
8
9#pragma once
10
11#include <cstring>
12#include <filesystem>
13#include <expected>
14#include <sys/vfs.h>
15#include <sys/mount.h>
16#include <thread>
17
18#include "subprocess.hpp"
19#include "env.hpp"
20#include "../std/expected.hpp"
21
22// Other codes available here:
23// https://man7.org/linux/man-pages/man2/statfs.2.html
24#define FUSE_SUPER_MAGIC 0x65735546
25
34namespace ns_fuse
35{
36
37namespace
38{
39
40namespace fs = std::filesystem;
41
42} // namespace
43
50inline Value<bool> is_fuse(fs::path const& path_dir_mount)
51{
52 struct statfs buf;
53
54 if ( statfs(path_dir_mount.c_str(), &buf) < 0 )
55 {
56 return Error("E::{}", strerror(errno));
57 }
58
59 return buf.f_type == FUSE_SUPER_MAGIC;
60}
61
68inline void wait_fuse(fs::path const& path_dir_filesystem)
69{
70 using namespace std::chrono_literals;
71 auto time_beg = std::chrono::system_clock::now();
72 while ( true )
73 {
74 auto expected_is_fuse = ns_fuse::is_fuse(path_dir_filesystem);
75 break_if(not expected_is_fuse, "E::Could not check if filesystem is fuse");
76 break_if(*expected_is_fuse, "D::Filesystem '{}' is fuse", path_dir_filesystem.string());
77 auto time_cur = std::chrono::system_clock::now();
78 auto elapsed = std::chrono::duration_cast<std::chrono::seconds>(time_cur - time_beg);
79 break_if(elapsed.count() > 60, "E::Reached timeout to wait for fuse filesystems");
80 } // while
81} // function: wait_fuse
82
83
90inline Value<int> unmount(fs::path const& path_dir_mount)
91{
92 using namespace std::chrono_literals;
93
94 // Find fusermount
95 auto path_file_fusermount = Pop(ns_env::search_path("fusermount"));
96
97 // Un-mount filesystem
98 using enum ns_subprocess::Stream;
99 auto child = ns_subprocess::Subprocess(path_file_fusermount)
100 .with_args("-zu", path_dir_mount)
101 .spawn();
102
103 // Check if process was started
104 return_if(not child, Error("E::Could not spawn fusermount"));
105
106 // Retrieve return code
107 int code = Pop(child->wait());
108
109 // Check for successful un-mount
110 if(code == 0)
111 {
112 logger("D::Un-mounted filesystem '{}'", path_dir_mount.string());
113 }
114 else
115 {
116 logger("D::Failed to un-mount filesystem '{}'", path_dir_mount.string());
117 }
118
119 // Filesystem could be busy for a bit after un-mount
120 while(Pop(ns_fuse::is_fuse(path_dir_mount)))
121 {
122 std::this_thread::sleep_for(100ms);
123 }
124
125 return code;
126} // function: unmount
127
128} // namespace ns_fuse
129
130/* vim: set expandtab fdm=marker ts=2 sw=2 tw=100 et :*/
std::unique_ptr< Child > spawn()
Spawns (forks) the child process and begins execution.
Subprocess & with_args(Args &&... args)
Arguments forwarded as the process' arguments.
Enhanced error handling framework built on std::expected.
A library for manipulating environment variables.
#define logger(fmt,...)
Compile-time log level dispatch macro with automatic location capture.
Definition log.hpp:682
Value< fs::path > search_path(std::string const &query)
Search the directories in the PATH variable for the given input file name.
Definition env.hpp:150
FUSE filesystem operation utilities.
Value< int > unmount(fs::path const &path_dir_mount)
Un-mounts the given fuse mount point.
Definition fuse.hpp:90
void wait_fuse(fs::path const &path_dir_filesystem)
Waits for the given directory to not be fuse.
Definition fuse.hpp:68
Value< bool > is_fuse(fs::path const &path_dir_mount)
Checks if a directory is a fuse filesystem mount point.
Definition fuse.hpp:50
Stream
Stream redirection modes for child process stdio.
Enhanced expected type with integrated logging capabilities.
Definition expected.hpp:44
A library to spawn sub-processes in linux.