Commit | Line | Data |
---|---|---|
252b5132 | 1 | /* filemode.c -- make a string describing file modes |
82704155 | 2 | Copyright (C) 1985-2019 Free Software Foundation, Inc. |
252b5132 RH |
3 | |
4 | This program is free software; you can redistribute it and/or modify | |
5 | it under the terms of the GNU General Public License as published by | |
32866df7 | 6 | the Free Software Foundation; either version 3, or (at your option) |
252b5132 RH |
7 | any later version. |
8 | ||
9 | This program is distributed in the hope that it will be useful, | |
10 | but WITHOUT ANY WARRANTY; without even the implied warranty of | |
11 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
12 | GNU General Public License for more details. | |
13 | ||
14 | You should have received a copy of the GNU General Public License | |
15 | along with this program; if not, write to the Free Software | |
b43b5d5f NC |
16 | Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA |
17 | 02110-1301, USA. */ | |
252b5132 | 18 | \f |
3db64b00 | 19 | #include "sysdep.h" |
252b5132 RH |
20 | #include "bfd.h" |
21 | #include "bucomm.h" | |
22 | ||
2da42df6 AJ |
23 | static char ftypelet (unsigned long); |
24 | static void setst (unsigned long, char *); | |
252b5132 RH |
25 | |
26 | /* filemodestring - fill in string STR with an ls-style ASCII | |
27 | representation of the st_mode field of file stats block STATP. | |
28 | 10 characters are stored in STR; no terminating null is added. | |
29 | The characters stored in STR are: | |
30 | ||
31 | 0 File type. 'd' for directory, 'c' for character | |
32 | special, 'b' for block special, 'm' for multiplex, | |
33 | 'l' for symbolic link, 's' for socket, 'p' for fifo, | |
34 | '-' for any other file type | |
35 | ||
36 | 1 'r' if the owner may read, '-' otherwise. | |
37 | ||
38 | 2 'w' if the owner may write, '-' otherwise. | |
39 | ||
40 | 3 'x' if the owner may execute, 's' if the file is | |
41 | set-user-id, '-' otherwise. | |
42 | 'S' if the file is set-user-id, but the execute | |
43 | bit isn't set. | |
44 | ||
45 | 4 'r' if group members may read, '-' otherwise. | |
46 | ||
47 | 5 'w' if group members may write, '-' otherwise. | |
48 | ||
49 | 6 'x' if group members may execute, 's' if the file is | |
50 | set-group-id, '-' otherwise. | |
51 | 'S' if it is set-group-id but not executable. | |
52 | ||
53 | 7 'r' if any user may read, '-' otherwise. | |
54 | ||
55 | 8 'w' if any user may write, '-' otherwise. | |
56 | ||
57 | 9 'x' if any user may execute, 't' if the file is "sticky" | |
58 | (will be retained in swap space after execution), '-' | |
59 | otherwise. | |
0af11b59 | 60 | 'T' if the file is sticky but not executable. */ |
252b5132 | 61 | |
252b5132 RH |
62 | /* Get definitions for the file permission bits. */ |
63 | ||
64 | #ifndef S_IRWXU | |
65 | #define S_IRWXU 0700 | |
66 | #endif | |
67 | #ifndef S_IRUSR | |
68 | #define S_IRUSR 0400 | |
69 | #endif | |
70 | #ifndef S_IWUSR | |
71 | #define S_IWUSR 0200 | |
72 | #endif | |
73 | #ifndef S_IXUSR | |
74 | #define S_IXUSR 0100 | |
75 | #endif | |
76 | ||
77 | #ifndef S_IRWXG | |
78 | #define S_IRWXG 0070 | |
79 | #endif | |
80 | #ifndef S_IRGRP | |
81 | #define S_IRGRP 0040 | |
82 | #endif | |
83 | #ifndef S_IWGRP | |
84 | #define S_IWGRP 0020 | |
85 | #endif | |
86 | #ifndef S_IXGRP | |
87 | #define S_IXGRP 0010 | |
88 | #endif | |
89 | ||
90 | #ifndef S_IRWXO | |
91 | #define S_IRWXO 0007 | |
92 | #endif | |
93 | #ifndef S_IROTH | |
94 | #define S_IROTH 0004 | |
95 | #endif | |
96 | #ifndef S_IWOTH | |
97 | #define S_IWOTH 0002 | |
98 | #endif | |
99 | #ifndef S_IXOTH | |
100 | #define S_IXOTH 0001 | |
101 | #endif | |
102 | ||
103 | /* Like filemodestring, but only the relevant part of the `struct stat' | |
0af11b59 | 104 | is given as an argument. */ |
252b5132 RH |
105 | |
106 | void | |
2da42df6 | 107 | mode_string (unsigned long mode, char *str) |
252b5132 RH |
108 | { |
109 | str[0] = ftypelet ((unsigned long) mode); | |
110 | str[1] = (mode & S_IRUSR) != 0 ? 'r' : '-'; | |
111 | str[2] = (mode & S_IWUSR) != 0 ? 'w' : '-'; | |
112 | str[3] = (mode & S_IXUSR) != 0 ? 'x' : '-'; | |
113 | str[4] = (mode & S_IRGRP) != 0 ? 'r' : '-'; | |
114 | str[5] = (mode & S_IWGRP) != 0 ? 'w' : '-'; | |
115 | str[6] = (mode & S_IXGRP) != 0 ? 'x' : '-'; | |
116 | str[7] = (mode & S_IROTH) != 0 ? 'r' : '-'; | |
117 | str[8] = (mode & S_IWOTH) != 0 ? 'w' : '-'; | |
118 | str[9] = (mode & S_IXOTH) != 0 ? 'x' : '-'; | |
119 | setst ((unsigned long) mode, str); | |
120 | } | |
121 | ||
122 | /* Return a character indicating the type of file described by | |
123 | file mode BITS: | |
124 | 'd' for directories | |
125 | 'b' for block special files | |
126 | 'c' for character special files | |
aaad4cf3 | 127 | 'm' for multiplexer files |
252b5132 RH |
128 | 'l' for symbolic links |
129 | 's' for sockets | |
130 | 'p' for fifos | |
0af11b59 | 131 | '-' for any other file type. */ |
252b5132 RH |
132 | |
133 | #ifndef S_ISDIR | |
134 | #ifdef S_IFDIR | |
135 | #define S_ISDIR(i) (((i) & S_IFMT) == S_IFDIR) | |
136 | #else /* ! defined (S_IFDIR) */ | |
137 | #define S_ISDIR(i) (((i) & 0170000) == 040000) | |
138 | #endif /* ! defined (S_IFDIR) */ | |
139 | #endif /* ! defined (S_ISDIR) */ | |
140 | ||
141 | #ifndef S_ISBLK | |
142 | #ifdef S_IFBLK | |
143 | #define S_ISBLK(i) (((i) & S_IFMT) == S_IFBLK) | |
144 | #else /* ! defined (S_IFBLK) */ | |
145 | #define S_ISBLK(i) 0 | |
146 | #endif /* ! defined (S_IFBLK) */ | |
147 | #endif /* ! defined (S_ISBLK) */ | |
148 | ||
149 | #ifndef S_ISCHR | |
150 | #ifdef S_IFCHR | |
151 | #define S_ISCHR(i) (((i) & S_IFMT) == S_IFCHR) | |
152 | #else /* ! defined (S_IFCHR) */ | |
153 | #define S_ISCHR(i) 0 | |
154 | #endif /* ! defined (S_IFCHR) */ | |
155 | #endif /* ! defined (S_ISCHR) */ | |
156 | ||
157 | #ifndef S_ISFIFO | |
158 | #ifdef S_IFIFO | |
159 | #define S_ISFIFO(i) (((i) & S_IFMT) == S_IFIFO) | |
160 | #else /* ! defined (S_IFIFO) */ | |
161 | #define S_ISFIFO(i) 0 | |
162 | #endif /* ! defined (S_IFIFO) */ | |
163 | #endif /* ! defined (S_ISFIFO) */ | |
164 | ||
165 | #ifndef S_ISSOCK | |
166 | #ifdef S_IFSOCK | |
167 | #define S_ISSOCK(i) (((i) & S_IFMT) == S_IFSOCK) | |
168 | #else /* ! defined (S_IFSOCK) */ | |
169 | #define S_ISSOCK(i) 0 | |
170 | #endif /* ! defined (S_IFSOCK) */ | |
171 | #endif /* ! defined (S_ISSOCK) */ | |
172 | ||
173 | #ifndef S_ISLNK | |
174 | #ifdef S_IFLNK | |
175 | #define S_ISLNK(i) (((i) & S_IFMT) == S_IFLNK) | |
176 | #else /* ! defined (S_IFLNK) */ | |
177 | #define S_ISLNK(i) 0 | |
178 | #endif /* ! defined (S_IFLNK) */ | |
179 | #endif /* ! defined (S_ISLNK) */ | |
180 | ||
181 | static char | |
2da42df6 | 182 | ftypelet (unsigned long bits) |
252b5132 RH |
183 | { |
184 | if (S_ISDIR (bits)) | |
185 | return 'd'; | |
186 | if (S_ISLNK (bits)) | |
187 | return 'l'; | |
188 | if (S_ISBLK (bits)) | |
189 | return 'b'; | |
190 | if (S_ISCHR (bits)) | |
191 | return 'c'; | |
192 | if (S_ISSOCK (bits)) | |
193 | return 's'; | |
194 | if (S_ISFIFO (bits)) | |
195 | return 'p'; | |
196 | ||
197 | #ifdef S_IFMT | |
198 | #ifdef S_IFMPC | |
199 | if ((bits & S_IFMT) == S_IFMPC | |
200 | || (bits & S_IFMT) == S_IFMPB) | |
201 | return 'm'; | |
202 | #endif | |
203 | #ifdef S_IFNWK | |
204 | if ((bits & S_IFMT) == S_IFNWK) | |
205 | return 'n'; | |
206 | #endif | |
207 | #endif | |
208 | ||
209 | return '-'; | |
210 | } | |
211 | ||
212 | /* Set the 's' and 't' flags in file attributes string CHARS, | |
0af11b59 | 213 | according to the file mode BITS. */ |
252b5132 RH |
214 | |
215 | static void | |
2da42df6 | 216 | setst (unsigned long bits ATTRIBUTE_UNUSED, char *chars ATTRIBUTE_UNUSED) |
252b5132 RH |
217 | { |
218 | #ifdef S_ISUID | |
219 | if (bits & S_ISUID) | |
220 | { | |
221 | if (chars[3] != 'x') | |
0af11b59 | 222 | /* Set-uid, but not executable by owner. */ |
252b5132 RH |
223 | chars[3] = 'S'; |
224 | else | |
225 | chars[3] = 's'; | |
226 | } | |
227 | #endif | |
228 | #ifdef S_ISGID | |
229 | if (bits & S_ISGID) | |
230 | { | |
231 | if (chars[6] != 'x') | |
0af11b59 | 232 | /* Set-gid, but not executable by group. */ |
252b5132 RH |
233 | chars[6] = 'S'; |
234 | else | |
235 | chars[6] = 's'; | |
236 | } | |
237 | #endif | |
238 | #ifdef S_ISVTX | |
239 | if (bits & S_ISVTX) | |
240 | { | |
241 | if (chars[9] != 'x') | |
0af11b59 | 242 | /* Sticky, but not executable by others. */ |
252b5132 RH |
243 | chars[9] = 'T'; |
244 | else | |
245 | chars[9] = 't'; | |
246 | } | |
247 | #endif | |
248 | } |