]>
Commit | Line | Data |
---|---|---|
1 | /* | |
2 | * Copyright (C) the libgit2 contributors. All rights reserved. | |
3 | * | |
4 | * This file is part of libgit2, distributed under the GNU GPL v2 with | |
5 | * a Linking Exception. For full terms see the included COPYING file. | |
6 | */ | |
7 | #ifndef INCLUDE_path_h__ | |
8 | #define INCLUDE_path_h__ | |
9 | ||
10 | #include "common.h" | |
11 | #include "posix.h" | |
12 | #include "buffer.h" | |
13 | #include "vector.h" | |
14 | ||
15 | /** | |
16 | * Path manipulation utils | |
17 | * | |
18 | * These are path utilities that munge paths without actually | |
19 | * looking at the real filesystem. | |
20 | */ | |
21 | ||
22 | /* | |
23 | * The dirname() function shall take a pointer to a character string | |
24 | * that contains a pathname, and return a pointer to a string that is a | |
25 | * pathname of the parent directory of that file. Trailing '/' characters | |
26 | * in the path are not counted as part of the path. | |
27 | * | |
28 | * If path does not contain a '/', then dirname() shall return a pointer to | |
29 | * the string ".". If path is a null pointer or points to an empty string, | |
30 | * dirname() shall return a pointer to the string "." . | |
31 | * | |
32 | * The `git_path_dirname` implementation is thread safe. The returned | |
33 | * string must be manually free'd. | |
34 | * | |
35 | * The `git_path_dirname_r` implementation writes the dirname to a `git_buf` | |
36 | * if the buffer pointer is not NULL. | |
37 | * It returns an error code < 0 if there is an allocation error, otherwise | |
38 | * the length of the dirname (which will be > 0). | |
39 | */ | |
40 | extern char *git_path_dirname(const char *path); | |
41 | extern int git_path_dirname_r(git_buf *buffer, const char *path); | |
42 | ||
43 | /* | |
44 | * This function returns the basename of the file, which is the last | |
45 | * part of its full name given by fname, with the drive letter and | |
46 | * leading directories stripped off. For example, the basename of | |
47 | * c:/foo/bar/file.ext is file.ext, and the basename of a:foo is foo. | |
48 | * | |
49 | * Trailing slashes and backslashes are significant: the basename of | |
50 | * c:/foo/bar/ is an empty string after the rightmost slash. | |
51 | * | |
52 | * The `git_path_basename` implementation is thread safe. The returned | |
53 | * string must be manually free'd. | |
54 | * | |
55 | * The `git_path_basename_r` implementation writes the basename to a `git_buf`. | |
56 | * It returns an error code < 0 if there is an allocation error, otherwise | |
57 | * the length of the basename (which will be >= 0). | |
58 | */ | |
59 | extern char *git_path_basename(const char *path); | |
60 | extern int git_path_basename_r(git_buf *buffer, const char *path); | |
61 | ||
62 | /* Return the offset of the start of the basename. Unlike the other | |
63 | * basename functions, this returns 0 if the path is empty. | |
64 | */ | |
65 | extern size_t git_path_basename_offset(git_buf *buffer); | |
66 | ||
67 | extern const char *git_path_topdir(const char *path); | |
68 | ||
69 | /** | |
70 | * Find offset to root of path if path has one. | |
71 | * | |
72 | * This will return a number >= 0 which is the offset to the start of the | |
73 | * path, if the path is rooted (i.e. "/rooted/path" returns 0 and | |
74 | * "c:/windows/rooted/path" returns 2). If the path is not rooted, this | |
75 | * returns < 0. | |
76 | */ | |
77 | extern int git_path_root(const char *path); | |
78 | ||
79 | /** | |
80 | * Ensure path has a trailing '/'. | |
81 | */ | |
82 | extern int git_path_to_dir(git_buf *path); | |
83 | ||
84 | /** | |
85 | * Ensure string has a trailing '/' if there is space for it. | |
86 | */ | |
87 | extern void git_path_string_to_dir(char* path, size_t size); | |
88 | ||
89 | /** | |
90 | * Taken from git.git; returns nonzero if the given path is "." or "..". | |
91 | */ | |
92 | GIT_INLINE(int) git_path_is_dot_or_dotdot(const char *name) | |
93 | { | |
94 | return (name[0] == '.' && | |
95 | (name[1] == '\0' || | |
96 | (name[1] == '.' && name[2] == '\0'))); | |
97 | } | |
98 | ||
99 | #ifdef GIT_WIN32 | |
100 | GIT_INLINE(int) git_path_is_dot_or_dotdotW(const wchar_t *name) | |
101 | { | |
102 | return (name[0] == L'.' && | |
103 | (name[1] == L'\0' || | |
104 | (name[1] == L'.' && name[2] == L'\0'))); | |
105 | } | |
106 | ||
107 | /** | |
108 | * Convert backslashes in path to forward slashes. | |
109 | */ | |
110 | GIT_INLINE(void) git_path_mkposix(char *path) | |
111 | { | |
112 | while (*path) { | |
113 | if (*path == '\\') | |
114 | *path = '/'; | |
115 | ||
116 | path++; | |
117 | } | |
118 | } | |
119 | #else | |
120 | # define git_path_mkposix(p) /* blank */ | |
121 | #endif | |
122 | ||
123 | /** | |
124 | * Check if string is a relative path (i.e. starts with "./" or "../") | |
125 | */ | |
126 | GIT_INLINE(int) git_path_is_relative(const char *p) | |
127 | { | |
128 | return (p[0] == '.' && (p[1] == '/' || (p[1] == '.' && p[2] == '/'))); | |
129 | } | |
130 | ||
131 | /** | |
132 | * Check if string is at end of path segment (i.e. looking at '/' or '\0') | |
133 | */ | |
134 | GIT_INLINE(int) git_path_at_end_of_segment(const char *p) | |
135 | { | |
136 | return !*p || *p == '/'; | |
137 | } | |
138 | ||
139 | extern int git__percent_decode(git_buf *decoded_out, const char *input); | |
140 | ||
141 | /** | |
142 | * Extract path from file:// URL. | |
143 | */ | |
144 | extern int git_path_fromurl(git_buf *local_path_out, const char *file_url); | |
145 | ||
146 | ||
147 | /** | |
148 | * Path filesystem utils | |
149 | * | |
150 | * These are path utilities that actually access the filesystem. | |
151 | */ | |
152 | ||
153 | /** | |
154 | * Check if a file exists and can be accessed. | |
155 | * @return true or false | |
156 | */ | |
157 | extern bool git_path_exists(const char *path); | |
158 | ||
159 | /** | |
160 | * Check if the given path points to a directory. | |
161 | * @return true or false | |
162 | */ | |
163 | extern bool git_path_isdir(const char *path); | |
164 | ||
165 | /** | |
166 | * Check if the given path points to a regular file. | |
167 | * @return true or false | |
168 | */ | |
169 | extern bool git_path_isfile(const char *path); | |
170 | ||
171 | /** | |
172 | * Check if the given path is a directory, and is empty. | |
173 | */ | |
174 | extern bool git_path_is_empty_dir(const char *path); | |
175 | ||
176 | /** | |
177 | * Stat a file and/or link and set error if needed. | |
178 | */ | |
179 | extern int git_path_lstat(const char *path, struct stat *st); | |
180 | ||
181 | /** | |
182 | * Check if the parent directory contains the item. | |
183 | * | |
184 | * @param dir Directory to check. | |
185 | * @param item Item that might be in the directory. | |
186 | * @return 0 if item exists in directory, <0 otherwise. | |
187 | */ | |
188 | extern bool git_path_contains(git_buf *dir, const char *item); | |
189 | ||
190 | /** | |
191 | * Check if the given path contains the given subdirectory. | |
192 | * | |
193 | * @param parent Directory path that might contain subdir | |
194 | * @param subdir Subdirectory name to look for in parent | |
195 | * @return true if subdirectory exists, false otherwise. | |
196 | */ | |
197 | extern bool git_path_contains_dir(git_buf *parent, const char *subdir); | |
198 | ||
199 | /** | |
200 | * Make the path relative to the given parent path. | |
201 | * | |
202 | * @param path The path to make relative | |
203 | * @param parent The parent path to make path relative to | |
204 | * @return 0 if path was made relative, GIT_ENOTFOUND | |
205 | * if there was not common root between the paths, | |
206 | * or <0. | |
207 | */ | |
208 | extern int git_path_make_relative(git_buf *path, const char *parent); | |
209 | ||
210 | /** | |
211 | * Check if the given path contains the given file. | |
212 | * | |
213 | * @param dir Directory path that might contain file | |
214 | * @param file File name to look for in parent | |
215 | * @return true if file exists, false otherwise. | |
216 | */ | |
217 | extern bool git_path_contains_file(git_buf *dir, const char *file); | |
218 | ||
219 | /** | |
220 | * Prepend base to unrooted path or just copy path over. | |
221 | * | |
222 | * This will optionally return the index into the path where the "root" | |
223 | * is, either the end of the base directory prefix or the path root. | |
224 | */ | |
225 | extern int git_path_join_unrooted( | |
226 | git_buf *path_out, const char *path, const char *base, ssize_t *root_at); | |
227 | ||
228 | /** | |
229 | * Clean up path, prepending base if it is not already rooted. | |
230 | */ | |
231 | extern int git_path_prettify(git_buf *path_out, const char *path, const char *base); | |
232 | ||
233 | /** | |
234 | * Clean up path, prepending base if it is not already rooted and | |
235 | * appending a slash. | |
236 | */ | |
237 | extern int git_path_prettify_dir(git_buf *path_out, const char *path, const char *base); | |
238 | ||
239 | /** | |
240 | * Get a directory from a path. | |
241 | * | |
242 | * If path is a directory, this acts like `git_path_prettify_dir` | |
243 | * (cleaning up path and appending a '/'). If path is a normal file, | |
244 | * this prettifies it, then removed the filename a la dirname and | |
245 | * appends the trailing '/'. If the path does not exist, it is | |
246 | * treated like a regular filename. | |
247 | */ | |
248 | extern int git_path_find_dir(git_buf *dir, const char *path, const char *base); | |
249 | ||
250 | /** | |
251 | * Resolve relative references within a path. | |
252 | * | |
253 | * This eliminates "./" and "../" relative references inside a path, | |
254 | * as well as condensing multiple slashes into single ones. It will | |
255 | * not touch the path before the "ceiling" length. | |
256 | * | |
257 | * Additionally, this will recognize an "c:/" drive prefix or a "xyz://" URL | |
258 | * prefix and not touch that part of the path. | |
259 | */ | |
260 | extern int git_path_resolve_relative(git_buf *path, size_t ceiling); | |
261 | ||
262 | /** | |
263 | * Apply a relative path to base path. | |
264 | * | |
265 | * Note that the base path could be a filename or a URL and this | |
266 | * should still work. The relative path is walked segment by segment | |
267 | * with three rules: series of slashes will be condensed to a single | |
268 | * slash, "." will be eaten with no change, and ".." will remove a | |
269 | * segment from the base path. | |
270 | */ | |
271 | extern int git_path_apply_relative(git_buf *target, const char *relpath); | |
272 | ||
273 | enum { | |
274 | GIT_PATH_DIR_IGNORE_CASE = (1u << 0), | |
275 | GIT_PATH_DIR_PRECOMPOSE_UNICODE = (1u << 1), | |
276 | GIT_PATH_DIR_INCLUDE_DOT_AND_DOTDOT = (1u << 2), | |
277 | }; | |
278 | ||
279 | /** | |
280 | * Walk each directory entry, except '.' and '..', calling fn(state). | |
281 | * | |
282 | * @param pathbuf Buffer the function reads the initial directory | |
283 | * path from, and updates with each successive entry's name. | |
284 | * @param flags Combination of GIT_PATH_DIR flags. | |
285 | * @param callback Callback for each entry. Passed the `payload` and each | |
286 | * successive path inside the directory as a full path. This may | |
287 | * safely append text to the pathbuf if needed. Return non-zero to | |
288 | * cancel iteration (and return value will be propagated back). | |
289 | * @param payload Passed to callback as first argument. | |
290 | * @return 0 on success or error code from OS error or from callback | |
291 | */ | |
292 | extern int git_path_direach( | |
293 | git_buf *pathbuf, | |
294 | uint32_t flags, | |
295 | int (*callback)(void *payload, git_buf *path), | |
296 | void *payload); | |
297 | ||
298 | /** | |
299 | * Sort function to order two paths | |
300 | */ | |
301 | extern int git_path_cmp( | |
302 | const char *name1, size_t len1, int isdir1, | |
303 | const char *name2, size_t len2, int isdir2, | |
304 | int (*compare)(const char *, const char *, size_t)); | |
305 | ||
306 | /** | |
307 | * Invoke callback up path directory by directory until the ceiling is | |
308 | * reached (inclusive of a final call at the root_path). | |
309 | * | |
310 | * Returning anything other than 0 from the callback function | |
311 | * will stop the iteration and propagate the error to the caller. | |
312 | * | |
313 | * @param pathbuf Buffer the function reads the directory from and | |
314 | * and updates with each successive name. | |
315 | * @param ceiling Prefix of path at which to stop walking up. If NULL, | |
316 | * this will walk all the way up to the root. If not a prefix of | |
317 | * pathbuf, the callback will be invoked a single time on the | |
318 | * original input path. | |
319 | * @param callback Function to invoke on each path. Passed the `payload` | |
320 | * and the buffer containing the current path. The path should not | |
321 | * be modified in any way. Return non-zero to stop iteration. | |
322 | * @param state Passed to fn as the first ath. | |
323 | */ | |
324 | extern int git_path_walk_up( | |
325 | git_buf *pathbuf, | |
326 | const char *ceiling, | |
327 | int (*callback)(void *payload, const char *path), | |
328 | void *payload); | |
329 | ||
330 | ||
331 | enum { GIT_PATH_NOTEQUAL = 0, GIT_PATH_EQUAL = 1, GIT_PATH_PREFIX = 2 }; | |
332 | ||
333 | /* | |
334 | * Determines if a path is equal to or potentially a child of another. | |
335 | * @param parent The possible parent | |
336 | * @param child The possible child | |
337 | */ | |
338 | GIT_INLINE(int) git_path_equal_or_prefixed( | |
339 | const char *parent, | |
340 | const char *child, | |
341 | ssize_t *prefixlen) | |
342 | { | |
343 | const char *p = parent, *c = child; | |
344 | int lastslash = 0; | |
345 | ||
346 | while (*p && *c) { | |
347 | lastslash = (*p == '/'); | |
348 | ||
349 | if (*p++ != *c++) | |
350 | return GIT_PATH_NOTEQUAL; | |
351 | } | |
352 | ||
353 | if (*p != '\0') | |
354 | return GIT_PATH_NOTEQUAL; | |
355 | ||
356 | if (*c == '\0') { | |
357 | if (prefixlen) | |
358 | *prefixlen = p - parent; | |
359 | ||
360 | return GIT_PATH_EQUAL; | |
361 | } | |
362 | ||
363 | if (*c == '/' || lastslash) { | |
364 | if (prefixlen) | |
365 | *prefixlen = (p - parent) - lastslash; | |
366 | ||
367 | return GIT_PATH_PREFIX; | |
368 | } | |
369 | ||
370 | return GIT_PATH_NOTEQUAL; | |
371 | } | |
372 | ||
373 | /* translate errno to libgit2 error code and set error message */ | |
374 | extern int git_path_set_error( | |
375 | int errno_value, const char *path, const char *action); | |
376 | ||
377 | /* check if non-ascii characters are present in filename */ | |
378 | extern bool git_path_has_non_ascii(const char *path, size_t pathlen); | |
379 | ||
380 | #define GIT_PATH_REPO_ENCODING "UTF-8" | |
381 | ||
382 | #ifdef __APPLE__ | |
383 | #define GIT_PATH_NATIVE_ENCODING "UTF-8-MAC" | |
384 | #else | |
385 | #define GIT_PATH_NATIVE_ENCODING "UTF-8" | |
386 | #endif | |
387 | ||
388 | #ifdef GIT_USE_ICONV | |
389 | ||
390 | #include <iconv.h> | |
391 | ||
392 | typedef struct { | |
393 | iconv_t map; | |
394 | git_buf buf; | |
395 | } git_path_iconv_t; | |
396 | ||
397 | #define GIT_PATH_ICONV_INIT { (iconv_t)-1, GIT_BUF_INIT } | |
398 | ||
399 | /* Init iconv data for converting decomposed UTF-8 to precomposed */ | |
400 | extern int git_path_iconv_init_precompose(git_path_iconv_t *ic); | |
401 | ||
402 | /* Clear allocated iconv data */ | |
403 | extern void git_path_iconv_clear(git_path_iconv_t *ic); | |
404 | ||
405 | /* | |
406 | * Rewrite `in` buffer using iconv map if necessary, replacing `in` | |
407 | * pointer internal iconv buffer if rewrite happened. The `in` pointer | |
408 | * will be left unchanged if no rewrite was needed. | |
409 | */ | |
410 | extern int git_path_iconv(git_path_iconv_t *ic, const char **in, size_t *inlen); | |
411 | ||
412 | #endif /* GIT_USE_ICONV */ | |
413 | ||
414 | extern bool git_path_does_fs_decompose_unicode(const char *root); | |
415 | ||
416 | ||
417 | typedef struct git_path_diriter git_path_diriter; | |
418 | ||
419 | #if defined(GIT_WIN32) && !defined(__MINGW32__) | |
420 | ||
421 | struct git_path_diriter | |
422 | { | |
423 | git_win32_path path; | |
424 | size_t parent_len; | |
425 | ||
426 | git_buf path_utf8; | |
427 | size_t parent_utf8_len; | |
428 | ||
429 | HANDLE handle; | |
430 | ||
431 | unsigned int flags; | |
432 | ||
433 | WIN32_FIND_DATAW current; | |
434 | unsigned int needs_next; | |
435 | }; | |
436 | ||
437 | #define GIT_PATH_DIRITER_INIT { {0}, 0, GIT_BUF_INIT, 0, INVALID_HANDLE_VALUE } | |
438 | ||
439 | #else | |
440 | ||
441 | struct git_path_diriter | |
442 | { | |
443 | git_buf path; | |
444 | size_t parent_len; | |
445 | ||
446 | unsigned int flags; | |
447 | ||
448 | DIR *dir; | |
449 | ||
450 | #ifdef GIT_USE_ICONV | |
451 | git_path_iconv_t ic; | |
452 | #endif | |
453 | }; | |
454 | ||
455 | #define GIT_PATH_DIRITER_INIT { GIT_BUF_INIT } | |
456 | ||
457 | #endif | |
458 | ||
459 | /** | |
460 | * Initialize a directory iterator. | |
461 | * | |
462 | * @param diriter Pointer to a diriter structure that will be setup. | |
463 | * @param path The path that will be iterated over | |
464 | * @param flags Directory reader flags | |
465 | * @return 0 or an error code | |
466 | */ | |
467 | extern int git_path_diriter_init( | |
468 | git_path_diriter *diriter, | |
469 | const char *path, | |
470 | unsigned int flags); | |
471 | ||
472 | /** | |
473 | * Advance the directory iterator. Will return GIT_ITEROVER when | |
474 | * the iteration has completed successfully. | |
475 | * | |
476 | * @param diriter The directory iterator | |
477 | * @return 0, GIT_ITEROVER, or an error code | |
478 | */ | |
479 | extern int git_path_diriter_next(git_path_diriter *diriter); | |
480 | ||
481 | /** | |
482 | * Returns the file name of the current item in the iterator. | |
483 | * | |
484 | * @param out Pointer to store the path in | |
485 | * @param out_len Pointer to store the length of the path in | |
486 | * @param diriter The directory iterator | |
487 | * @return 0 or an error code | |
488 | */ | |
489 | extern int git_path_diriter_filename( | |
490 | const char **out, | |
491 | size_t *out_len, | |
492 | git_path_diriter *diriter); | |
493 | ||
494 | /** | |
495 | * Returns the full path of the current item in the iterator; that | |
496 | * is the current filename plus the path of the directory that the | |
497 | * iterator was constructed with. | |
498 | * | |
499 | * @param out Pointer to store the path in | |
500 | * @param out_len Pointer to store the length of the path in | |
501 | * @param diriter The directory iterator | |
502 | * @return 0 or an error code | |
503 | */ | |
504 | extern int git_path_diriter_fullpath( | |
505 | const char **out, | |
506 | size_t *out_len, | |
507 | git_path_diriter *diriter); | |
508 | ||
509 | /** | |
510 | * Performs an `lstat` on the current item in the iterator. | |
511 | * | |
512 | * @param out Pointer to store the stat data in | |
513 | * @param diriter The directory iterator | |
514 | * @return 0 or an error code | |
515 | */ | |
516 | extern int git_path_diriter_stat(struct stat *out, git_path_diriter *diriter); | |
517 | ||
518 | /** | |
519 | * Closes the directory iterator. | |
520 | * | |
521 | * @param diriter The directory iterator | |
522 | */ | |
523 | extern void git_path_diriter_free(git_path_diriter *diriter); | |
524 | ||
525 | /** | |
526 | * Load all directory entries (except '.' and '..') into a vector. | |
527 | * | |
528 | * For cases where `git_path_direach()` is not appropriate, this | |
529 | * allows you to load the filenames in a directory into a vector | |
530 | * of strings. That vector can then be sorted, iterated, or whatever. | |
531 | * Remember to free alloc of the allocated strings when you are done. | |
532 | * | |
533 | * @param contents Vector to fill with directory entry names. | |
534 | * @param path The directory to read from. | |
535 | * @param prefix_len When inserting entries, the trailing part of path | |
536 | * will be prefixed after this length. I.e. given path "/a/b" and | |
537 | * prefix_len 3, the entries will look like "b/e1", "b/e2", etc. | |
538 | * @param flags Combination of GIT_PATH_DIR flags. | |
539 | */ | |
540 | extern int git_path_dirload( | |
541 | git_vector *contents, | |
542 | const char *path, | |
543 | size_t prefix_len, | |
544 | uint32_t flags); | |
545 | ||
546 | ||
547 | /* Used for paths to repositories on the filesystem */ | |
548 | extern bool git_path_is_local_file_url(const char *file_url); | |
549 | extern int git_path_from_url_or_path(git_buf *local_path_out, const char *url_or_path); | |
550 | ||
551 | /* Flags to determine path validity in `git_path_isvalid` */ | |
552 | #define GIT_PATH_REJECT_TRAVERSAL (1 << 0) | |
553 | #define GIT_PATH_REJECT_DOT_GIT (1 << 1) | |
554 | #define GIT_PATH_REJECT_SLASH (1 << 2) | |
555 | #define GIT_PATH_REJECT_BACKSLASH (1 << 3) | |
556 | #define GIT_PATH_REJECT_TRAILING_DOT (1 << 4) | |
557 | #define GIT_PATH_REJECT_TRAILING_SPACE (1 << 5) | |
558 | #define GIT_PATH_REJECT_TRAILING_COLON (1 << 6) | |
559 | #define GIT_PATH_REJECT_DOS_PATHS (1 << 7) | |
560 | #define GIT_PATH_REJECT_NT_CHARS (1 << 8) | |
561 | #define GIT_PATH_REJECT_DOT_GIT_HFS (1 << 9) | |
562 | #define GIT_PATH_REJECT_DOT_GIT_NTFS (1 << 10) | |
563 | ||
564 | /* Default path safety for writing files to disk: since we use the | |
565 | * Win32 "File Namespace" APIs ("\\?\") we need to protect from | |
566 | * paths that the normal Win32 APIs would not write. | |
567 | */ | |
568 | #ifdef GIT_WIN32 | |
569 | # define GIT_PATH_REJECT_DEFAULTS \ | |
570 | GIT_PATH_REJECT_TRAVERSAL | \ | |
571 | GIT_PATH_REJECT_BACKSLASH | \ | |
572 | GIT_PATH_REJECT_TRAILING_DOT | \ | |
573 | GIT_PATH_REJECT_TRAILING_SPACE | \ | |
574 | GIT_PATH_REJECT_TRAILING_COLON | \ | |
575 | GIT_PATH_REJECT_DOS_PATHS | \ | |
576 | GIT_PATH_REJECT_NT_CHARS | |
577 | #else | |
578 | # define GIT_PATH_REJECT_DEFAULTS GIT_PATH_REJECT_TRAVERSAL | |
579 | #endif | |
580 | ||
581 | /* | |
582 | * Determine whether a path is a valid git path or not - this must not contain | |
583 | * a '.' or '..' component, or a component that is ".git" (in any case). | |
584 | * | |
585 | * `repo` is optional. If specified, it will be used to determine the short | |
586 | * path name to reject (if `GIT_PATH_REJECT_DOS_SHORTNAME` is specified), | |
587 | * in addition to the default of "git~1". | |
588 | */ | |
589 | extern bool git_path_isvalid( | |
590 | git_repository *repo, | |
591 | const char *path, | |
592 | unsigned int flags); | |
593 | ||
594 | #endif |