summaryrefslogtreecommitdiff
path: root/doc/files_and_dirs.rst
diff options
context:
space:
mode:
Diffstat (limited to 'doc/files_and_dirs.rst')
-rw-r--r--doc/files_and_dirs.rst190
1 files changed, 190 insertions, 0 deletions
diff --git a/doc/files_and_dirs.rst b/doc/files_and_dirs.rst
new file mode 100644
index 0000000..a4fdc59
--- /dev/null
+++ b/doc/files_and_dirs.rst
@@ -0,0 +1,190 @@
+===========================
+File and directory handling
+===========================
+
+
+Directory traversal
+===================
+
+libHX provides a minimal readdir-style wrapper for cross-platform directory
+traversal. This is needed because the Win32 platforms does not have readdir,
+and there is some housekeeping to do on Unixish platforms, since the dirent
+structure needs allocation of a path-specific size.
+
+.. code-block:: c
+
+ #include <libHX/io.h>
+
+ struct HXdir *HXdir_open(const char *directory);
+ const char *HXdir_read(struct HXdir *handle);
+ void HXdir_close(struct HXdir *handle);
+
+``HXdir_open`` returns a pointer to its private data area, or ``NULL`` upon
+failure, in which case ``errno`` is preserved from the underlying system calls.
+``HXdir_read`` causes the next entry from the directory to be fetched. The
+pointer returned by ``HXdir_read`` must not be freed, and the data is
+overwritten in subsequent calls to the same handle. If you want to keep it
+around, you will have to duplicate it yourself. ``HXdir_close`` will close the
+directory and free the private data it held.
+
+
+Example
+-------
+
+.. code-block:: c
+
+ #include <errno.h>
+ #include <stdio.h>
+ #include <libHX/io.h>
+
+ struct HXdir *dh;
+ if ((dh = HXdir_open(".")) == NULL) {
+ fprintf(stderr, "Could not open directory: %s\n", strerror(errno));
+ return;
+ }
+ while ((dentry = HXdir_read(dh)) != NULL)
+ printf("%s\n", dentry);
+ HXdir_close(dh);
+
+This sample will open the current directory, and print out all entries as it
+iterates over them.
+
+
+Operation on directory entries
+==============================
+
+.. code-block:: c
+
+ #include <libHX/io.h>
+
+ int HX_readlink(hxmc_t **buf, const char *path);
+ int HX_realpath(hxmc_t **buf, const char *path, unsigned int flags);
+
+``HX_readlink`` calls through to readlink to read the target of a symbolic
+link, and stores the result in the memory container referenced by ``*buf``
+(similar to ``HX_getl`` semantics). If ``*buf`` is ``NULL``, a new container
+will be allocated and a pointer to it stored in ``*buf``. The container's
+content is naturally zero-terminated automatically. The return value of the
+function will be the length of the link target, or negative to indicate the
+system error value.
+
+``HX_realpath`` will normalize the given path by transforming various path
+components into alternate descriptions. The flags parameter controls its
+actions:
+
+``HX_REALPATH_DEFAULT``
+ A mnemonic for a set of standard flags: ``HX_REALPATH_SELF |
+ HX_REALPATH_PARENT``. Note that ``HX_REALPATH_ABSOLUTE``, which would
+ also be required to get libc's ``realpath``(3) behavior, is not
+ included in the set.
+
+``HX_REALPATH_ABSOLUTE``
+ Requests that the output path shall be absolute. In the absence of this
+ flag, an absolute output path will only be produced if the input path
+ is also absolute.
+
+``HX_REALPATH_SELF``
+ Request resolution of `.` path components.
+
+``HX_REALPATH_PARENT`
+ Request resolution of `..` path components.
+
+The result is stored in a memory container whose pointer is returned through
+``*buf``. The return value of the function will be negative to indicate a
+possible system error, or be positive non-zero for success.
+
+
+Operations on directories
+=========================
+
+.. code-block:: c
+
+ #include <libHX/io.h>
+
+ int HX_mkdir(const char *path, unsigned int mode);
+ int HX_rrmdir(const char *path);
+
+``HX_mkdir`` will create the directory given by path and all its parents that
+do not exist yet using the given mode. It is equivalent to the ``mkdir -p``
+shell command. It will return >0 for success, or ``-errno`` on error.
+
+``HX_rrmdir`` also maps to an operation commonly done on the shell, ``rm -Rf``,
+deleting the directory given by path, including all files within it and its
+subdirectories. Errors during deletion are ignored, but if there was any, the
+errno value of the first one is returned negated.
+
+
+Operations on files
+===================
+
+.. code-block:: c
+
+ #include <libHX/io.h>
+
+ #define HXF_KEEP ...
+ #define HXF_UID ...
+ #define HXF_GID ...
+
+ int HX_copy_file(const char *src, const char *dest, unsigned int flags, ...);
+ int HX_copy_dir(const char *src, const char *dest, unsigned int flags, ...);
+ char *HX_slurp_fd(int fd, size_t *outsize);
+ char *HX_slurp_file(const char *file, size_t *outsize);
+
+``HX_copy_file``
+ Copies one named file to a new location. Possible ``flags`` are
+ ``HXF_KEEP``, ``HXF_UID`` and ``HXF_GID``. Error checking by
+ ``HX_copy_file`` is flakey. ``HX_copy_file`` will return >0 on success,
+ or ``-errno`` on failure. Errors can arise from the use of the syscalls
+ ``open``, ``read`` and ``write``. The return value of ``fchmod``, which
+ is used to set the UID and GID, is actually ignored, which means
+ verifying that the owner has been set cannot be detected with
+ ``HX_copy_file`` alone (historic negligience?).
+
+``HXF_KEEP``
+ Do not overwrite existing files.
+
+``HXF_UID``
+ Change the new file's owner to the UID given in the varargs section
+ (...). ``HXF_UID`` is processed before ``HXF_GID``.
+
+``HXF_GID``
+ Change the new file's group owner to the GID given in the varargs
+ section. This is processed after ``HXF_UID``.
+
+``HX_copy_dir``
+ Copies one named directory to a new location, recursively.
+ (Uses ``HX_copy_file`` and ``HX_copy_dir``.) Error checking by
+ ``HX_copy_dir`` is flakey.
+
+``HX_slurp_fd``
+ Reads all remaining bytes from the given filedescriptor ``fd`` and
+ returns a pointer to a newly-allocated content buffer. If ``outsize``
+ is not ``NULL``, the size of the buffer will be written to it. The
+ buffer is always terminated by a gratuitious NUL (not counted in
+ ``outsize``). Once no longer needed, the buffer should be released with
+ ``free``.
+
+``HX_slurp_file``
+ Reads all bytes from the given filename and returns a pointer to the
+ content buffer. Inherits all the characteristics from ``HX_slurp_fd``.
+
+
+Filedescriptor helpers
+======================
+
+.. code-block:: c
+
+ #include <libHX/io.h>
+
+ ssize_t HXio_fullread(int fd, void *buf, size_t size, unsigned int flags);
+ ssize_t HXio_fullwrite(int fd, const void *buf, size_t size, unsigned int flags);
+ ssize_t HX_sendfile(int dst, int src, size_t count);
+
+Since plain ``read``(2) and ``write``(2) may process only part of the buffer —
+even more likely so with sockets —, libHX provides two functions that calls
+these in a loop to retry said operations until the full amount has been
+processed. Since read and write can also be used with socket file descriptors,
+so can these.
+
+``HX_sendfile`` wraps ``sendfile``(2) for the same reason; in addition, it
+falls back to a read-write loop on platforms which do not offer sendfile.