1 /* TODO merge/factor in debugfs.c here */
14 static const char * const sysfs__fs_known_mountpoints
[] = {
19 static const char * const procfs__known_mountpoints
[] = {
26 const char * const *mounts
;
27 char path
[PATH_MAX
+ 1];
37 static struct fs fs__entries
[] = {
40 .mounts
= sysfs__fs_known_mountpoints
,
45 .mounts
= procfs__known_mountpoints
,
46 .magic
= PROC_SUPER_MAGIC
,
50 static bool fs__read_mounts(struct fs
*fs
)
56 fp
= fopen("/proc/mounts", "r");
61 fscanf(fp
, "%*s %" STR(PATH_MAX
) "s %99s %*s %*d %*d\n",
62 fs
->path
, type
) == 2) {
64 if (strcmp(type
, fs
->name
) == 0)
69 return fs
->found
= found
;
72 static int fs__valid_mount(const char *fs
, long magic
)
76 if (statfs(fs
, &st_fs
) < 0)
78 else if (st_fs
.f_type
!= magic
)
84 static bool fs__check_mounts(struct fs
*fs
)
86 const char * const *ptr
;
90 if (fs__valid_mount(*ptr
, fs
->magic
) == 0) {
92 strcpy(fs
->path
, *ptr
);
101 static void mem_toupper(char *f
, size_t len
)
111 * Check for "NAME_PATH" environment variable to override fs location (for
112 * testing). This matches the recommendation in Documentation/sysfs-rules.txt
115 static bool fs__env_override(struct fs
*fs
)
118 size_t name_len
= strlen(fs
->name
);
119 /* name + "_PATH" + '\0' */
120 char upper_name
[name_len
+ 5 + 1];
121 memcpy(upper_name
, fs
->name
, name_len
);
122 mem_toupper(upper_name
, name_len
);
123 strcpy(&upper_name
[name_len
], "_PATH");
125 override_path
= getenv(upper_name
);
130 strncpy(fs
->path
, override_path
, sizeof(fs
->path
));
134 static const char *fs__get_mountpoint(struct fs
*fs
)
136 if (fs__env_override(fs
))
139 if (fs__check_mounts(fs
))
142 if (fs__read_mounts(fs
))
148 static const char *fs__mountpoint(int idx
)
150 struct fs
*fs
= &fs__entries
[idx
];
153 return (const char *)fs
->path
;
155 return fs__get_mountpoint(fs
);
158 #define FS__MOUNTPOINT(name, idx) \
159 const char *name##__mountpoint(void) \
161 return fs__mountpoint(idx); \
164 FS__MOUNTPOINT(sysfs
, FS__SYSFS
);
165 FS__MOUNTPOINT(procfs
, FS__PROCFS
);