xref: /openbsd/lib/libcurses/tinfo/access.c (revision 17df1aa7)
1 /* $OpenBSD: access.c,v 1.5 2010/01/12 23:22:06 nicm Exp $ */
2 
3 /****************************************************************************
4  * Copyright (c) 1998-2006,2007 Free Software Foundation, Inc.              *
5  *                                                                          *
6  * Permission is hereby granted, free of charge, to any person obtaining a  *
7  * copy of this software and associated documentation files (the            *
8  * "Software"), to deal in the Software without restriction, including      *
9  * without limitation the rights to use, copy, modify, merge, publish,      *
10  * distribute, distribute with modifications, sublicense, and/or sell       *
11  * copies of the Software, and to permit persons to whom the Software is    *
12  * furnished to do so, subject to the following conditions:                 *
13  *                                                                          *
14  * The above copyright notice and this permission notice shall be included  *
15  * in all copies or substantial portions of the Software.                   *
16  *                                                                          *
17  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS  *
18  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF               *
19  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.   *
20  * IN NO EVENT SHALL THE ABOVE COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,   *
21  * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR    *
22  * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR    *
23  * THE USE OR OTHER DEALINGS IN THE SOFTWARE.                               *
24  *                                                                          *
25  * Except as contained in this notice, the name(s) of the above copyright   *
26  * holders shall not be used in advertising or otherwise to promote the     *
27  * sale, use or other dealings in this Software without prior written       *
28  * authorization.                                                           *
29  ****************************************************************************/
30 
31 /****************************************************************************
32  *  Author: Thomas E. Dickey                                                *
33  ****************************************************************************/
34 
35 #include <curses.priv.h>
36 
37 #include <ctype.h>
38 #include <sys/stat.h>
39 
40 #include <tic.h>
41 #include <nc_alloc.h>
42 
43 MODULE_ID("$Id: access.c,v 1.5 2010/01/12 23:22:06 nicm Exp $")
44 
45 #define LOWERCASE(c) ((isalpha(UChar(c)) && isupper(UChar(c))) ? tolower(UChar(c)) : (c))
46 
47 NCURSES_EXPORT(char *)
48 _nc_rootname(char *path)
49 {
50     char *result = _nc_basename(path);
51 #if !MIXEDCASE_FILENAMES || defined(PROG_EXT)
52     static char *temp;
53     char *s;
54 
55     temp = strdup(result);
56     result = temp;
57 #if !MIXEDCASE_FILENAMES
58     for (s = result; *s != '\0'; ++s) {
59 	*s = LOWERCASE(*s);
60     }
61 #endif
62 #if defined(PROG_EXT)
63     if ((s = strrchr(result, '.')) != 0) {
64 	if (!strcmp(s, PROG_EXT))
65 	    *s = '\0';
66     }
67 #endif
68 #endif
69     return result;
70 }
71 
72 /*
73  * Check if a string appears to be an absolute pathname.
74  */
75 NCURSES_EXPORT(bool)
76 _nc_is_abs_path(const char *path)
77 {
78 #if defined(__EMX__) || defined(__DJGPP__)
79 #define is_pathname(s) ((((s) != 0) && ((s)[0] == '/')) \
80 		  || (((s)[0] != 0) && ((s)[1] == ':')))
81 #else
82 #define is_pathname(s) ((s) != 0 && (s)[0] == '/')
83 #endif
84     return is_pathname(path);
85 }
86 
87 /*
88  * Return index of the basename
89  */
90 NCURSES_EXPORT(unsigned)
91 _nc_pathlast(const char *path)
92 {
93     const char *test = strrchr(path, '/');
94 #ifdef __EMX__
95     if (test == 0)
96 	test = strrchr(path, '\\');
97 #endif
98     if (test == 0)
99 	test = path;
100     else
101 	test++;
102     return (test - path);
103 }
104 
105 NCURSES_EXPORT(char *)
106 _nc_basename(char *path)
107 {
108     return path + _nc_pathlast(path);
109 }
110 
111 NCURSES_EXPORT(int)
112 _nc_access(const char *path, int mode)
113 {
114     if (access(path, mode) < 0) {
115 	if ((mode & W_OK) != 0
116 	    && errno == ENOENT
117 	    && strlen(path) < PATH_MAX) {
118 	    char *leaf, head[PATH_MAX];
119 
120             strlcpy(head, path, sizeof(head));
121             if ((leaf = _nc_basename(head)) == 0)
122 		    leaf = head;
123             *leaf = '\0';
124 	    if (head == leaf)
125 		(void) strlcpy(head, ".", sizeof(head));
126 
127 	    return access(head, R_OK | W_OK | X_OK);
128 	}
129 	return -1;
130     }
131     return 0;
132 }
133 
134 NCURSES_EXPORT(bool)
135 _nc_is_dir_path(const char *path)
136 {
137     bool result = FALSE;
138     struct stat sb;
139 
140     if (stat(path, &sb) == 0
141 	&& (sb.st_mode & S_IFMT) == S_IFDIR) {
142 	result = TRUE;
143     }
144     return result;
145 }
146 
147 NCURSES_EXPORT(bool)
148 _nc_is_file_path(const char *path)
149 {
150     bool result = FALSE;
151     struct stat sb;
152 
153     if (stat(path, &sb) == 0
154 	&& (sb.st_mode & S_IFMT) == S_IFREG) {
155 	result = TRUE;
156     }
157     return result;
158 }
159 
160 #ifndef USE_ROOT_ENVIRON
161 /*
162  * Returns true if we allow application to use environment variables that are
163  * used for searching lists of directories, etc.
164  */
165 NCURSES_EXPORT(int)
166 _nc_env_access(void)
167 {
168 #if HAVE_ISSETUGID
169     if (issetugid())
170 	return FALSE;
171 #elif HAVE_GETEUID && HAVE_GETEGID
172     if (getuid() != geteuid()
173 	|| getgid() != getegid())
174 	return FALSE;
175 #endif
176     return getuid() != 0 && geteuid() != 0;	/* ...finally, disallow root */
177 }
178 #endif
179