1 /* vifm
2  * Copyright (C) 2001 Ken Steen.
3  * Copyright (C) 2011 xaizek.
4  *
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License as published by
7  * the Free Software Foundation; either version 2 of the License, or
8  * (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program; if not, write to the Free Software
17  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
18  */
19 
20 #ifndef VIFM__UTILS__FS_H__
21 #define VIFM__UTILS__FS_H__
22 
23 #include <sys/types.h> /* mode_t */
24 
25 #include <stddef.h> /* size_t */
26 #include <stdint.h> /* uint32_t uint64_t */
27 
28 /* Functions to deal with file system objects */
29 
30 /* Named boolean values of "deref" parameter for better readability. */
31 enum
32 {
33 	NODEREF, /* Do not dereference symbolic links in checks. */
34 	DEREF,   /* Dereference symbolic links in checks. */
35 };
36 
37 /* Link types for get_symlink_type() function. */
38 typedef enum
39 {
40 	SLT_UNKNOWN, /* It's either a file or the link is broken. */
41 	SLT_DIR,     /* It's a valid link to a directory. */
42 	SLT_SLOW,    /* Target of the link is at slow file system, won't access it. */
43 }
44 SymLinkType;
45 
46 /* Per-entry callback type for enum_dir_content().  Should return zero on
47  * success or non-zero to indicate failure which will lead to stopping of
48  * directory content enumeration. */
49 typedef int (*dir_content_client_func)(const char name[], const void *data,
50 		void *param);
51 
52 /* Checks if path is an existing directory.  Automatically dereferences symbolic
53  * links. */
54 int is_dir(const char path[]);
55 
56 /* Checks whether directory is empty.  Returns non-zero if it is, in case of
57  * error or when directory is empty non-zero is returned. */
58 int is_dir_empty(const char path[]);
59 
60 /* Checks if path could be a directory (e.g. it can be UNC root on Windows). */
61 int is_valid_dir(const char *path);
62 
63 /* Checks whether file at path exists.  The path should be an absolute path.
64  * Relative paths are checked relatively to the working directory, which might
65  * produce incorrect results. */
66 int path_exists(const char path[], int deref);
67 
68 /* Checks whether path/file exists. */
69 int path_exists_at(const char path[], const char filename[], int deref);
70 
71 /* Checks if two paths refer to the same file-system object.  Returns non-zero
72  * if so, otherwise zero is returned. */
73 int paths_are_same(const char s[], const char t[]);
74 
75 /* Checks whether given path points to a symbolic link.  Returns non-zero if
76  * it's so, otherwise zero is returned. */
77 int is_symlink(const char path[]);
78 
79 /* Checks whether given path points to a shortcut file (link implemented as a
80  * regular file).  Returns non-zero if it's so, otherwise zero is returned. */
81 int is_shortcut(const char path[]);
82 
83 /* Gets approximate symbolic link type: directory, won't check, anything else.
84  * Returns one of SymLinkType values. */
85 SymLinkType get_symlink_type(const char path[]);
86 
87 /* Fills the buf of size buf_len with the absolute path to a file pointed to by
88  * the link symbolic link.  Uses the cwd parameter to make absolute path from
89  * relative symbolic links.  The link and buf can point to the same piece of
90  * memory.  Returns non-zero on error. */
91 int get_link_target_abs(const char link[], const char cwd[], char buf[],
92 		size_t buf_len);
93 
94 /* Fills the buf of size buf_len with the path symbolic link specified by link
95  * parameter points to.  Returns zero on success, otherwise non-zero is
96  * returned. */
97 int get_link_target(const char link[], char buf[], size_t buf_len);
98 
99 /* Creates directory and all intermediate directories if needed using specified
100  * access mode.  If target directory already exists, no error will be raised.
101  * Returns zero on success, otherwise non-zero is returned. */
102 int make_path(const char dir_name[], mode_t mode);
103 
104 /* Same as make_path(), but fails if target path already exists and is a
105  * directory. */
106 int create_path(const char dir_name[], mode_t mode);
107 
108 /* Whether symbolic links can be used.  Returns non-zero if so, otherwise zero
109  * is returned. */
110 int symlinks_available(void);
111 
112 /* Whether file rename-with-replace (deletion of file at destination) is
113  * supported and atomic.  Returns non-zero if so, otherwise zero is returned. */
114 int has_atomic_file_replace(void);
115 
116 /* Checks if one can change current directory to the path.  Returns non-zero if
117  * so, otherwise zero is returned. */
118 int directory_accessible(const char path[]);
119 
120 /* Checks if one can write in directory specified by the path, which should be
121  * absolute (in order for this function to work correctly). */
122 int is_dir_writable(const char path[]);
123 
124 /* Gets correct file size independently of platform.  Returns zero for both
125  * empty files and on error. */
126 uint64_t get_file_size(const char path[]);
127 
128 /* Appends all regular files inside the path directory.  Reallocates array of
129  * strings if necessary to fit all elements.  Returns pointer to reallocated
130  * array or source list (on error). */
131 char ** list_regular_files(const char path[], char *list[], int *len);
132 
133 /* Enumerates content of the path.  Returns list of names of lengths *len, which
134  * can be NULL on empty list, error is indicated by negative *len. */
135 char ** list_all_files(const char path[], int *len);
136 
137 /* Enumerates content of the path in sorted order.  Returns list of names of
138  * length *len, which can be NULL on empty list, error is indicated by negative
139  * *len. */
140 char ** list_sorted_files(const char path[], int *len);
141 
142 /* Returns non-zero if file (or symbolic link target) path points to is a
143  * regular file. */
144 int is_regular_file(const char path[]);
145 
146 /* Checks whether file path points to a regular file (not a symbolic link or
147  * anything else).  Returns non-zero if so, otherwise zero is returned. */
148 int is_regular_file_noderef(const char path[]);
149 
150 /* Renames file specified by the src argument to the path specified by the dst
151  * argument.  Overwrites destination file if it exists.  Returns non-zero on
152  * error, otherwise zero is returned. */
153 int rename_file(const char src[], const char dst[]);
154 
155 /* Removes directory content, but not the directory itself. */
156 void remove_dir_content(const char path[]);
157 
158 struct dirent;
159 
160 /* Uses dentry or full path to check whether target is symbolic link.  Returns
161  * non-zero if so, otherwise zero is returned. */
162 int entry_is_link(const char path[], const struct dirent *dentry);
163 
164 /* Uses dentry or full path to check file type.  Returns non-zero for
165  * directories, otherwise zero is returned.  Symbolic links are _not_
166  * dereferenced. */
167 int entry_is_dir(const char full_path[], const struct dirent* dentry);
168 
169 /* Uses dentry or path to check file type.  Assumes that file is located in
170  * current working directory.  Returns non-zero for directories, otherwise zero
171  * is returned.  Symbolic links are dereferenced. */
172 int is_dirent_targets_dir(const char full_path[], const struct dirent *d);
173 
174 /* Checks that entity pointed to by the path is located under the root
175  * directory.  Non-zero include_root parameter makes root being considered to be
176  * part of the subtree that it defines.  Returns non-zero if so, otherwise zero
177  * is returned. */
178 int is_in_subtree(const char path[], const char root[], int include_root);
179 
180 /* Checks whether to paths belong to the same file system.  Returns non-zero if
181  * so, otherwise zero is returned. */
182 int are_on_the_same_fs(const char s[], const char t[]);
183 
184 /* Checks whether file moving from src to dst corresponds to file rename that
185  * just changes case of file name on case insensitive file system.  Returns
186  * non-zero if so, otherwise zero is returned. */
187 int is_case_change(const char src[], const char dst[]);
188 
189 /* Checks whether paths are case sensitive at specified location.  Returns
190  * non-zero if so, otherwise zero is returned. */
191 int case_sensitive_paths(const char at[]);
192 
193 /* Calls the client callback for each entry of the directory.  Returns zero on
194  * success, otherwise non-zero is returned. */
195 int enum_dir_content(const char path[], dir_content_client_func client,
196 		void *param);
197 
198 /* Counts number of files in the directory excluding . and .. entries.  Returns
199  * the count. */
200 int count_dir_items(const char path[]);
201 
202 /* getcwd() wrapper that always uses forward slashes.  Returns buf on success or
203  * NULL on error. */
204 char * get_cwd(char buf[], size_t size);
205 
206 /* Remembers current working directory.  If path can't be obtained, does
207  * nothing.  Result should be passed to restore_cwd(), no checks are needed (but
208  * NULL indicates that we failed to get CWD). */
209 char * save_cwd(void);
210 
211 /* Restores previously remembered working directory via save_cwd().  If nothing
212  * was remembered, does nothing. */
213 void restore_cwd(char saved_cwd[]);
214 
215 #ifdef _WIN32
216 
217 int S_ISLNK(mode_t mode);
218 
219 int readlink(const char *path, char *buf, size_t len);
220 
221 int is_on_fat_volume(const char *path);
222 
223 /* Checks specified drive for existence.  Returns non-zero if it exists,
224  * otherwise zero is returned. */
225 int drive_exists(char letter);
226 
227 int is_win_symlink(uint32_t attr, uint32_t tag);
228 
229 #endif
230 
231 #endif /* VIFM__UTILS__FS_H__ */
232 
233 /* vim: set tabstop=2 softtabstop=2 shiftwidth=2 noexpandtab cinoptions-=(0 : */
234 /* vim: set cinoptions+=t0 filetype=c : */
235