summaryrefslogtreecommitdiff
path: root/libtecla-1.4.1/pathutil.c
diff options
context:
space:
mode:
Diffstat (limited to 'libtecla-1.4.1/pathutil.c')
-rw-r--r--libtecla-1.4.1/pathutil.c532
1 files changed, 0 insertions, 532 deletions
diff --git a/libtecla-1.4.1/pathutil.c b/libtecla-1.4.1/pathutil.c
deleted file mode 100644
index 015504b..0000000
--- a/libtecla-1.4.1/pathutil.c
+++ /dev/null
@@ -1,532 +0,0 @@
-/*
- * Copyright (c) 2000, 2001 by Martin C. Shepherd.
- *
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, and/or sell copies of the Software, and to permit persons
- * to whom the Software is furnished to do so, provided that the above
- * copyright notice(s) and this permission notice appear in all copies of
- * the Software and that both the above copyright notice(s) and this
- * permission notice appear in supporting documentation.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
- * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT
- * OF THIRD PARTY RIGHTS. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
- * HOLDERS INCLUDED IN THIS NOTICE BE LIABLE FOR ANY CLAIM, OR ANY SPECIAL
- * INDIRECT OR CONSEQUENTIAL DAMAGES, OR ANY DAMAGES WHATSOEVER RESULTING
- * FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
- * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
- * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
- *
- * Except as contained in this notice, the name of a copyright holder
- * shall not be used in advertising or otherwise to promote the sale, use
- * or other dealings in this Software without prior written authorization
- * of the copyright holder.
- */
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <errno.h>
-#include <string.h>
-#include <ctype.h>
-
-#include <unistd.h>
-#include <sys/types.h>
-#include <sys/stat.h>
-
-#include "pathutil.h"
-
-/*.......................................................................
- * Create a new PathName object.
- *
- * Output:
- * return PathName * The new object, or NULL on error.
- */
-PathName *_new_PathName(void)
-{
- PathName *path; /* The object to be returned */
-/*
- * Allocate the container.
- */
- path = (PathName *)malloc(sizeof(PathName));
- if(!path) {
- fprintf(stderr, "_new_PathName: Insufficient memory.\n");
- return NULL;
- };
-/*
- * Before attempting any operation that might fail, initialize the
- * container at least up to the point at which it can safely be passed
- * to _del_PathName().
- */
- path->name = NULL;
- path->dim = 0;
-/*
- * Figure out the maximum length of an expanded pathname.
- */
- path->dim = _pu_pathname_dim();
- if(path->dim == 0)
- return _del_PathName(path);
-/*
- * Allocate the pathname buffer.
- */
- path->name = (char *)malloc(path->dim * sizeof(char));
- if(!path->name) {
- fprintf(stderr,
- "_new_PathName: Insufficient memory to allocate pathname buffer.\n");
- return _del_PathName(path);
- };
- return path;
-}
-
-/*.......................................................................
- * Delete a PathName object.
- *
- * Input:
- * path PathName * The object to be deleted.
- * Output:
- * return PathName * The deleted object (always NULL).
- */
-PathName *_del_PathName(PathName *path)
-{
- if(path) {
- if(path->name)
- free(path->name);
- free(path);
- };
- return NULL;
-}
-
-/*.......................................................................
- * Return the pathname to a zero-length string.
- *
- * Input:
- * path PathName * The pathname container.
- * Output:
- * return char * The cleared pathname buffer, or NULL on error.
- */
-char *_pn_clear_path(PathName *path)
-{
-/*
- * Check the arguments.
- */
- if(!path) {
- fprintf(stderr, "_pn_clear_path: NULL argument.\n");
- return NULL;
- };
- path->name[0] = '\0';
- return path->name;
-}
-
-/*.......................................................................
- * Append a string to a pathname, increasing the size of the pathname
- * buffer if needed.
- *
- * Input:
- * path PathName * The pathname container.
- * string const char * The string to be appended to the pathname.
- * Note that regardless of the slen argument,
- * this should be a '\0' terminated string.
- * slen int The maximum number of characters to append
- * from string[], or -1 to append the whole
- * string.
- * remove_escapes int If true, remove the backslashes that escape
- * spaces, tabs, backslashes etc..
- * Output:
- * return char * The pathname string path->name[], which may
- * have been reallocated, or NULL if there was
- * insufficient memory to extend the pathname.
- */
-char *_pn_append_to_path(PathName *path, const char *string, int slen,
- int remove_escapes)
-{
- int pathlen; /* The length of the pathname */
- int i;
-/*
- * Check the arguments.
- */
- if(!path || !string) {
- fprintf(stderr, "_pn_append_to_path: NULL argument(s).\n");
- return NULL;
- };
-/*
- * Get the current length of the pathname.
- */
- pathlen = strlen(path->name);
-/*
- * How many characters should be appended?
- */
- if(slen < 0 || slen > strlen(string))
- slen = strlen(string);
-/*
- * Resize the pathname if needed.
- */
- if(!_pn_resize_path(path, pathlen + slen))
- return NULL;
-/*
- * Append the string to the output pathname, removing any escape
- * characters found therein.
- */
- if(remove_escapes) {
- int is_escape = 0;
- for(i=0; i<slen; i++) {
- is_escape = !is_escape && string[i] == '\\';
- if(!is_escape)
- path->name[pathlen++] = string[i];
- };
-/*
- * Terminate the string.
- */
- path->name[pathlen] = '\0';
- } else {
-/*
- * Append the string directly to the pathname.
- */
- memcpy(path->name + pathlen, string, slen);
- path->name[pathlen + slen] = '\0';
- };
- return path->name;
-}
-
-/*.......................................................................
- * Prepend a string to a pathname, increasing the size of the pathname
- * buffer if needed.
- *
- * Input:
- * path PathName * The pathname container.
- * string const char * The string to be prepended to the pathname.
- * Note that regardless of the slen argument,
- * this should be a '\0' terminated string.
- * slen int The maximum number of characters to prepend
- * from string[], or -1 to append the whole
- * string.
- * remove_escapes int If true, remove the backslashes that escape
- * spaces, tabs, backslashes etc..
- * Output:
- * return char * The pathname string path->name[], which may
- * have been reallocated, or NULL if there was
- * insufficient memory to extend the pathname.
- */
-char *_pn_prepend_to_path(PathName *path, const char *string, int slen,
- int remove_escapes)
-{
- int pathlen; /* The length of the pathname */
- int shift; /* The number of characters to shift the suffix by */
- int i,j;
-/*
- * Check the arguments.
- */
- if(!path || !string) {
- fprintf(stderr, "_pn_prepend_to_path: NULL argument(s).\n");
- return NULL;
- };
-/*
- * Get the current length of the pathname.
- */
- pathlen = strlen(path->name);
-/*
- * How many characters should be appended?
- */
- if(slen < 0 || slen > strlen(string))
- slen = strlen(string);
-/*
- * Work out how far we need to shift the original path string to make
- * way for the new prefix. When removing escape characters, we need
- * final length of the new prefix, after unescaped backslashes have
- * been removed.
- */
- if(remove_escapes) {
- int is_escape = 0;
- for(shift=0,i=0; i<slen; i++) {
- is_escape = !is_escape && string[i] == '\\';
- if(!is_escape)
- shift++;
- };
- } else {
- shift = slen;
- };
-/*
- * Resize the pathname if needed.
- */
- if(!_pn_resize_path(path, pathlen + shift))
- return NULL;
-/*
- * Make room for the prefix at the beginning of the string.
- */
- memmove(path->name + shift, path->name, pathlen+1);
-/*
- * Copy the new prefix into the vacated space at the beginning of the
- * output pathname, removing any escape characters if needed.
- */
- if(remove_escapes) {
- int is_escape = 0;
- for(i=j=0; i<slen; i++) {
- is_escape = !is_escape && string[i] == '\\';
- if(!is_escape)
- path->name[j++] = string[i];
- };
- } else {
- memcpy(path->name, string, slen);
- };
- return path->name;
-}
-
-/*.......................................................................
- * If needed reallocate a given pathname buffer to allow a string of
- * a given length to be stored in it.
- *
- * Input:
- * path PathName * The pathname container object.
- * length size_t The required length of the pathname buffer,
- * not including the terminating '\0'.
- * Output:
- * return char * The pathname buffer, or NULL if there was
- * insufficient memory (this isn't reported
- * to stderr).
- */
-char *_pn_resize_path(PathName *path, size_t length)
-{
-/*
- * Check the arguments.
- */
- if(!path) {
- fprintf(stderr, "_pn_resize_path: NULL argument(s).\n");
- return NULL;
- };
-/*
- * If the pathname buffer isn't large enough to accomodate a string
- * of the specified length, attempt to reallocate it with the new
- * size, plus space for a terminating '\0'. Also add a bit of
- * head room to prevent too many reallocations if the initial length
- * turned out to be very optimistic.
- */
- if(length + 1 > path->dim) {
- size_t dim = length + 1 + PN_PATHNAME_INC;
- char *name = (char *) realloc(path->name, dim);
- if(!name)
- return NULL;
- path->name = name;
- path->dim = dim;
- };
- return path->name;
-}
-
-/*.......................................................................
- * Estimate the largest amount of space needed to store a pathname.
- *
- * Output:
- * return size_t The number of bytes needed, including space for the
- * terminating '\0'.
- */
-size_t _pu_pathname_dim(void)
-{
- int maxlen; /* The return value excluding space for the '\0' */
-/*
- * If the POSIX PATH_MAX macro is defined in limits.h, use it.
- */
-#ifdef PATH_MAX
- maxlen = PATH_MAX;
-/*
- * If we have pathconf, use it.
- */
-#elif defined(_PC_PATH_MAX)
- errno = 0;
- maxlen = pathconf(FS_ROOT_DIR, _PC_PATH_MAX);
- if(maxlen <= 0 || errno)
- maxlen = MAX_PATHLEN_FALLBACK;
-/*
- * None of the above approaches worked, so substitute our fallback
- * guess.
- */
-#else
- maxlen = MAX_PATHLEN_FALLBACK;
-#endif
-/*
- * Return the amount of space needed to accomodate a pathname plus
- * a terminating '\0'.
- */
- return maxlen + 1;
-}
-
-/*.......................................................................
- * Return non-zero if the specified path name refers to a directory.
- *
- * Input:
- * pathname const char * The path to test.
- * Output:
- * return int 0 - Not a directory.
- * 1 - pathname[] refers to a directory.
- */
-int _pu_path_is_dir(const char *pathname)
-{
- struct stat statbuf; /* The file-statistics return buffer */
-/*
- * Look up the file attributes.
- */
- if(stat(pathname, &statbuf) < 0)
- return 0;
-/*
- * Is the file a directory?
- */
- return S_ISDIR(statbuf.st_mode) != 0;
-}
-
-/*.......................................................................
- * Return non-zero if the specified path name refers to a regular file.
- *
- * Input:
- * pathname const char * The path to test.
- * Output:
- * return int 0 - Not a regular file.
- * 1 - pathname[] refers to a regular file.
- */
-int _pu_path_is_file(const char *pathname)
-{
- struct stat statbuf; /* The file-statistics return buffer */
-/*
- * Look up the file attributes.
- */
- if(stat(pathname, &statbuf) < 0)
- return 0;
-/*
- * Is the file a regular file?
- */
- return S_ISREG(statbuf.st_mode) != 0;
-}
-
-/*.......................................................................
- * Return non-zero if the specified path name refers to an executable.
- *
- * Input:
- * pathname const char * The path to test.
- * Output:
- * return int 0 - Not an executable file.
- * 1 - pathname[] refers to an executable file.
- */
-int _pu_path_is_exe(const char *pathname)
-{
- struct stat statbuf; /* The file-statistics return buffer */
-/*
- * Look up the file attributes.
- */
- if(stat(pathname, &statbuf) < 0)
- return 0;
-/*
- * Is the file a regular file which is executable by the current user.
- */
- return S_ISREG(statbuf.st_mode) != 0 &&
- (statbuf.st_mode & (S_IXOTH | S_IXGRP | S_IXUSR)) &&
- access(pathname, X_OK) == 0;
-}
-
-/*.......................................................................
- * Search backwards for the potential start of a filename. This
- * looks backwards from the specified index in a given string,
- * stopping at the first unescaped space or the start of the line.
- *
- * Input:
- * string const char * The string to search backwards in.
- * back_from int The index of the first character in string[]
- * that follows the pathname.
- * Output:
- * return char * The pointer to the first character of
- * the potential pathname, or NULL on error.
- */
-char *_pu_start_of_path(const char *string, int back_from)
-{
- int i, j;
-/*
- * Check the arguments.
- */
- if(!string || back_from < 0) {
- fprintf(stderr, "_pu_start_path: Invalid argument(s).\n");
- return NULL;
- };
-/*
- * Search backwards from the specified index.
- */
- for(i=back_from-1; i>=0; i--) {
- int c = string[i];
-/*
- * Stop on unescaped spaces.
- */
- if(isspace((int)(unsigned char)c)) {
-/*
- * The space can't be escaped if we are at the start of the line.
- */
- if(i==0)
- break;
-/*
- * Find the extent of the escape characters which precedes the space.
- */
- for(j=i-1; j>=0 && string[j]=='\\'; j--)
- ;
-/*
- * If there isn't an odd number of escape characters before the space,
- * then the space isn't escaped.
- */
- if((i - 1 - j) % 2 == 0)
- break;
- };
- };
- return (char *)string + i + 1;
-}
-
-/*.......................................................................
- * Find the length of a potential filename starting from a given
- * point. This looks forwards from the specified index in a given string,
- * stopping at the first unescaped space or the end of the line.
- *
- * Input:
- * string const char * The string to search backwards in.
- * start_from int The index of the first character of the pathname
- * in string[].
- * Output:
- * return char * The pointer to the character that follows
- * the potential pathname, or NULL on error.
- */
-char *_pu_end_of_path(const char *string, int start_from)
-{
- int c; /* The character being examined */
- int escaped = 0; /* True when the next character is escaped */
- int i;
-/*
- * Check the arguments.
- */
- if(!string || start_from < 0) {
- fprintf(stderr, "_pu_end_path: Invalid argument(s).\n");
- return NULL;
- };
-/*
- * Search forwards from the specified index.
- */
- for(i=start_from; (c=string[i]) != '\0'; i++) {
- if(escaped) {
- escaped = 0;
- } else if(isspace(c)) {
- break;
- } else if(c == '\\') {
- escaped = 1;
- };
- };
- return (char *)string + i;
-}
-
-/*.......................................................................
- * Return non-zero if the specified path name refers to an existing file.
- *
- * Input:
- * pathname const char * The path to test.
- * Output:
- * return int 0 - The file doesn't exist.
- * 1 - The file does exist.
- */
-int _pu_file_exists(const char *pathname)
-{
- struct stat statbuf;
- return stat(pathname, &statbuf) == 0;
-}