| @@ -1,337 +1,330 @@ | | | @@ -1,337 +1,330 @@ |
1 | /* $NetBSD: archive_pack_dev.c,v 1.9 2024/01/18 18:00:17 adam Exp $ */ | | 1 | /* $NetBSD: archive_pack_dev.c,v 1.10 2024/04/15 13:37:24 gutteridge Exp $ */ |
2 | | | 2 | |
3 | /*- | | 3 | /*- |
4 | * Copyright (c) 1998, 2001 The NetBSD Foundation, Inc. | | 4 | * Copyright (c) 1998, 2001 The NetBSD Foundation, Inc. |
5 | * All rights reserved. | | 5 | * All rights reserved. |
6 | * | | 6 | * |
7 | * This code is derived from software contributed to The NetBSD Foundation | | 7 | * This code is derived from software contributed to The NetBSD Foundation |
8 | * by Charles M. Hannum. | | 8 | * by Charles M. Hannum. |
9 | * | | 9 | * |
10 | * Redistribution and use in source and binary forms, with or without | | 10 | * Redistribution and use in source and binary forms, with or without |
11 | * modification, are permitted provided that the following conditions | | 11 | * modification, are permitted provided that the following conditions |
12 | * are met: | | 12 | * are met: |
13 | * 1. Redistributions of source code must retain the above copyright | | 13 | * 1. Redistributions of source code must retain the above copyright |
14 | * notice, this list of conditions and the following disclaimer. | | 14 | * notice, this list of conditions and the following disclaimer. |
15 | * 2. Redistributions in binary form must reproduce the above copyright | | 15 | * 2. Redistributions in binary form must reproduce the above copyright |
16 | * notice, this list of conditions and the following disclaimer in the | | 16 | * notice, this list of conditions and the following disclaimer in the |
17 | * documentation and/or other materials provided with the distribution. | | 17 | * documentation and/or other materials provided with the distribution. |
18 | * | | 18 | * |
19 | * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS | | 19 | * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS |
20 | * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED | | 20 | * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED |
21 | * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | | 21 | * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR |
22 | * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS | | 22 | * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS |
23 | * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR | | 23 | * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR |
24 | * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF | | 24 | * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF |
25 | * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS | | 25 | * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS |
26 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN | | 26 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN |
27 | * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | | 27 | * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) |
28 | * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE | | 28 | * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE |
29 | * POSSIBILITY OF SUCH DAMAGE. | | 29 | * POSSIBILITY OF SUCH DAMAGE. |
30 | */ | | 30 | */ |
31 | | | 31 | |
32 | /* Originally from NetBSD's mknod(8) source. */ | | 32 | /* Originally from NetBSD's mknod(8) source. */ |
33 | | | 33 | |
34 | #include "archive_platform.h" | | 34 | #include "archive_platform.h" |
35 | | | 35 | |
36 | #if HAVE_SYS_CDEFS_H | | | |
37 | #include <sys/cdefs.h> | | | |
38 | #endif | | | |
39 | #if !defined(lint) | | | |
40 | __RCSID("$NetBSD: archive_pack_dev.c,v 1.9 2024/01/18 18:00:17 adam Exp $"); | | | |
41 | #endif /* not lint */ | | | |
42 | | | | |
43 | #ifdef HAVE_LIMITS_H | | 36 | #ifdef HAVE_LIMITS_H |
44 | #include <limits.h> | | 37 | #include <limits.h> |
45 | #endif | | 38 | #endif |
46 | | | 39 | |
47 | #include <stdio.h> | | 40 | #include <stdio.h> |
48 | #ifdef HAVE_STDLIB_H | | 41 | #ifdef HAVE_STDLIB_H |
49 | #include <stdlib.h> | | 42 | #include <stdlib.h> |
50 | #endif | | 43 | #endif |
51 | #ifdef HAVE_STRING_H | | 44 | #ifdef HAVE_STRING_H |
52 | #include <string.h> | | 45 | #include <string.h> |
53 | #endif | | 46 | #endif |
54 | #ifdef HAVE_SYS_TYPES_H | | 47 | #ifdef HAVE_SYS_TYPES_H |
55 | #include <sys/types.h> | | 48 | #include <sys/types.h> |
56 | #endif | | 49 | #endif |
57 | #ifdef HAVE_SYS_STAT_H | | 50 | #ifdef HAVE_SYS_STAT_H |
58 | #include <sys/stat.h> | | 51 | #include <sys/stat.h> |
59 | #endif | | 52 | #endif |
60 | #if MAJOR_IN_MKDEV | | 53 | #if MAJOR_IN_MKDEV |
61 | #include <sys/mkdev.h> | | 54 | #include <sys/mkdev.h> |
62 | #define HAVE_MAJOR | | 55 | #define HAVE_MAJOR |
63 | #elif MAJOR_IN_SYSMACROS | | 56 | #elif MAJOR_IN_SYSMACROS |
64 | #include <sys/sysmacros.h> | | 57 | #include <sys/sysmacros.h> |
65 | #define HAVE_MAJOR | | 58 | #define HAVE_MAJOR |
66 | #endif | | 59 | #endif |
67 | #ifdef HAVE_UNISTD_H | | 60 | #ifdef HAVE_UNISTD_H |
68 | #include <unistd.h> | | 61 | #include <unistd.h> |
69 | #endif | | 62 | #endif |
70 | | | 63 | |
71 | #include "archive_pack_dev.h" | | 64 | #include "archive_pack_dev.h" |
72 | | | 65 | |
73 | static pack_t pack_netbsd; | | 66 | static pack_t pack_netbsd; |
74 | static pack_t pack_freebsd; | | 67 | static pack_t pack_freebsd; |
75 | static pack_t pack_8_8; | | 68 | static pack_t pack_8_8; |
76 | static pack_t pack_12_20; | | 69 | static pack_t pack_12_20; |
77 | static pack_t pack_14_18; | | 70 | static pack_t pack_14_18; |
78 | static pack_t pack_8_24; | | 71 | static pack_t pack_8_24; |
79 | static pack_t pack_bsdos; | | 72 | static pack_t pack_bsdos; |
80 | static int __LA_LIBC_CC compare_format(const void *, const void *); | | 73 | static int __LA_LIBC_CC compare_format(const void *, const void *); |
81 | | | 74 | |
82 | static const char iMajorError[] = "invalid major number"; | | 75 | static const char iMajorError[] = "invalid major number"; |
83 | static const char iMinorError[] = "invalid minor number"; | | 76 | static const char iMinorError[] = "invalid minor number"; |
84 | static const char tooManyFields[] = "too many fields for format"; | | 77 | static const char tooManyFields[] = "too many fields for format"; |
85 | | | 78 | |
86 | /* This is blatantly stolen from libarchive/archive_entry.c, | | 79 | /* This is blatantly stolen from libarchive/archive_entry.c, |
87 | * in an attempt to get this to play nice on MinGW... */ | | 80 | * in an attempt to get this to play nice on MinGW... */ |
88 | #if !defined(HAVE_MAJOR) && !defined(major) | | 81 | #if !defined(HAVE_MAJOR) && !defined(major) |
89 | /* Replacement for major/minor/makedev. */ | | 82 | /* Replacement for major/minor/makedev. */ |
90 | #define major(x) ((int)(0x00ff & ((x) >> 8))) | | 83 | #define major(x) ((int)(0x00ff & ((x) >> 8))) |
91 | #define minor(x) ((int)(0xffff00ff & (x))) | | 84 | #define minor(x) ((int)(0xffff00ff & (x))) |
92 | #define makedev(maj,min) ((0xff00 & ((maj)<<8)) | (0xffff00ff & (min))) | | 85 | #define makedev(maj,min) ((0xff00 & ((maj)<<8)) | (0xffff00ff & (min))) |
93 | #endif | | 86 | #endif |
94 | | | 87 | |
95 | /* Play games to come up with a suitable makedev() definition. */ | | 88 | /* Play games to come up with a suitable makedev() definition. */ |
96 | #ifdef __QNXNTO__ | | 89 | #ifdef __QNXNTO__ |
97 | /* QNX. <sigh> */ | | 90 | /* QNX. <sigh> */ |
98 | #include <sys/netmgr.h> | | 91 | #include <sys/netmgr.h> |
99 | #define apd_makedev(maj, min) makedev(ND_LOCAL_NODE, (maj), (min)) | | 92 | #define apd_makedev(maj, min) makedev(ND_LOCAL_NODE, (maj), (min)) |
100 | #elif defined makedev | | 93 | #elif defined makedev |
101 | /* There's a "makedev" macro. */ | | 94 | /* There's a "makedev" macro. */ |
102 | #define apd_makedev(maj, min) makedev((maj), (min)) | | 95 | #define apd_makedev(maj, min) makedev((maj), (min)) |
103 | #elif defined mkdev || ((defined _WIN32 || defined __WIN32__) && !defined(__CYGWIN__)) | | 96 | #elif defined mkdev || ((defined _WIN32 || defined __WIN32__) && !defined(__CYGWIN__)) |
104 | /* Windows. <sigh> */ | | 97 | /* Windows. <sigh> */ |
105 | #define apd_makedev(maj, min) mkdev((maj), (min)) | | 98 | #define apd_makedev(maj, min) mkdev((maj), (min)) |
106 | #else | | 99 | #else |
107 | /* There's a "makedev" function. */ | | 100 | /* There's a "makedev" function. */ |
108 | #define apd_makedev(maj, min) makedev((maj), (min)) | | 101 | #define apd_makedev(maj, min) makedev((maj), (min)) |
109 | #endif | | 102 | #endif |
110 | | | 103 | |
111 | /* exported */ | | 104 | /* exported */ |
112 | dev_t | | 105 | dev_t |
113 | pack_native(int n, unsigned long numbers[], const char **error) | | 106 | pack_native(int n, unsigned long numbers[], const char **error) |
114 | { | | 107 | { |
115 | dev_t dev = 0; | | 108 | dev_t dev = 0; |
116 | | | 109 | |
117 | if (n == 2) { | | 110 | if (n == 2) { |
118 | dev = apd_makedev(numbers[0], numbers[1]); | | 111 | dev = apd_makedev(numbers[0], numbers[1]); |
119 | if ((unsigned long)major(dev) != numbers[0]) | | 112 | if ((unsigned long)major(dev) != numbers[0]) |
120 | *error = iMajorError; | | 113 | *error = iMajorError; |
121 | else if ((unsigned long)minor(dev) != numbers[1]) | | 114 | else if ((unsigned long)minor(dev) != numbers[1]) |
122 | *error = iMinorError; | | 115 | *error = iMinorError; |
123 | } else | | 116 | } else |
124 | *error = tooManyFields; | | 117 | *error = tooManyFields; |
125 | return (dev); | | 118 | return (dev); |
126 | } | | 119 | } |
127 | | | 120 | |
128 | | | 121 | |
129 | static dev_t | | 122 | static dev_t |
130 | pack_netbsd(int n, unsigned long numbers[], const char **error) | | 123 | pack_netbsd(int n, unsigned long numbers[], const char **error) |
131 | { | | 124 | { |
132 | dev_t dev = 0; | | 125 | dev_t dev = 0; |
133 | | | 126 | |
134 | if (n == 2) { | | 127 | if (n == 2) { |
135 | dev = makedev_netbsd(numbers[0], numbers[1]); | | 128 | dev = makedev_netbsd(numbers[0], numbers[1]); |
136 | if ((unsigned long)major_netbsd(dev) != numbers[0]) | | 129 | if ((unsigned long)major_netbsd(dev) != numbers[0]) |
137 | *error = iMajorError; | | 130 | *error = iMajorError; |
138 | else if ((unsigned long)minor_netbsd(dev) != numbers[1]) | | 131 | else if ((unsigned long)minor_netbsd(dev) != numbers[1]) |
139 | *error = iMinorError; | | 132 | *error = iMinorError; |
140 | } else | | 133 | } else |
141 | *error = tooManyFields; | | 134 | *error = tooManyFields; |
142 | return (dev); | | 135 | return (dev); |
143 | } | | 136 | } |
144 | | | 137 | |
145 | | | 138 | |
146 | #define major_freebsd(x) ((int32_t)(((x) & 0x0000ff00) >> 8)) | | 139 | #define major_freebsd(x) ((int32_t)(((x) & 0x0000ff00) >> 8)) |
147 | #define minor_freebsd(x) ((int32_t)(((x) & 0xffff00ff) >> 0)) | | 140 | #define minor_freebsd(x) ((int32_t)(((x) & 0xffff00ff) >> 0)) |
148 | #define makedev_freebsd(x,y) ((dev_t)((((x) << 8) & 0x0000ff00) | \ | | 141 | #define makedev_freebsd(x,y) ((dev_t)((((x) << 8) & 0x0000ff00) | \ |
149 | (((y) << 0) & 0xffff00ff))) | | 142 | (((y) << 0) & 0xffff00ff))) |
150 | | | 143 | |
151 | static dev_t | | 144 | static dev_t |
152 | pack_freebsd(int n, unsigned long numbers[], const char **error) | | 145 | pack_freebsd(int n, unsigned long numbers[], const char **error) |
153 | { | | 146 | { |
154 | dev_t dev = 0; | | 147 | dev_t dev = 0; |
155 | | | 148 | |
156 | if (n == 2) { | | 149 | if (n == 2) { |
157 | dev = makedev_freebsd(numbers[0], numbers[1]); | | 150 | dev = makedev_freebsd(numbers[0], numbers[1]); |
158 | if ((unsigned long)major_freebsd(dev) != numbers[0]) | | 151 | if ((unsigned long)major_freebsd(dev) != numbers[0]) |
159 | *error = iMajorError; | | 152 | *error = iMajorError; |
160 | if ((unsigned long)minor_freebsd(dev) != numbers[1]) | | 153 | if ((unsigned long)minor_freebsd(dev) != numbers[1]) |
161 | *error = iMinorError; | | 154 | *error = iMinorError; |
162 | } else | | 155 | } else |
163 | *error = tooManyFields; | | 156 | *error = tooManyFields; |
164 | return (dev); | | 157 | return (dev); |
165 | } | | 158 | } |
166 | | | 159 | |
167 | | | 160 | |
168 | #define major_8_8(x) ((int32_t)(((x) & 0x0000ff00) >> 8)) | | 161 | #define major_8_8(x) ((int32_t)(((x) & 0x0000ff00) >> 8)) |
169 | #define minor_8_8(x) ((int32_t)(((x) & 0x000000ff) >> 0)) | | 162 | #define minor_8_8(x) ((int32_t)(((x) & 0x000000ff) >> 0)) |
170 | #define makedev_8_8(x,y) ((dev_t)((((x) << 8) & 0x0000ff00) | \ | | 163 | #define makedev_8_8(x,y) ((dev_t)((((x) << 8) & 0x0000ff00) | \ |
171 | (((y) << 0) & 0x000000ff))) | | 164 | (((y) << 0) & 0x000000ff))) |
172 | | | 165 | |
173 | static dev_t | | 166 | static dev_t |
174 | pack_8_8(int n, unsigned long numbers[], const char **error) | | 167 | pack_8_8(int n, unsigned long numbers[], const char **error) |
175 | { | | 168 | { |
176 | dev_t dev = 0; | | 169 | dev_t dev = 0; |
177 | | | 170 | |
178 | if (n == 2) { | | 171 | if (n == 2) { |
179 | dev = makedev_8_8(numbers[0], numbers[1]); | | 172 | dev = makedev_8_8(numbers[0], numbers[1]); |
180 | if ((unsigned long)major_8_8(dev) != numbers[0]) | | 173 | if ((unsigned long)major_8_8(dev) != numbers[0]) |
181 | *error = iMajorError; | | 174 | *error = iMajorError; |
182 | if ((unsigned long)minor_8_8(dev) != numbers[1]) | | 175 | if ((unsigned long)minor_8_8(dev) != numbers[1]) |
183 | *error = iMinorError; | | 176 | *error = iMinorError; |
184 | } else | | 177 | } else |
185 | *error = tooManyFields; | | 178 | *error = tooManyFields; |
186 | return (dev); | | 179 | return (dev); |
187 | } | | 180 | } |
188 | | | 181 | |
189 | | | 182 | |
190 | #define major_12_20(x) ((int32_t)(((x) & 0xfff00000) >> 20)) | | 183 | #define major_12_20(x) ((int32_t)(((x) & 0xfff00000) >> 20)) |
191 | #define minor_12_20(x) ((int32_t)(((x) & 0x000fffff) >> 0)) | | 184 | #define minor_12_20(x) ((int32_t)(((x) & 0x000fffff) >> 0)) |
192 | #define makedev_12_20(x,y) ((dev_t)((((x) << 20) & 0xfff00000) | \ | | 185 | #define makedev_12_20(x,y) ((dev_t)((((x) << 20) & 0xfff00000) | \ |
193 | (((y) << 0) & 0x000fffff))) | | 186 | (((y) << 0) & 0x000fffff))) |
194 | | | 187 | |
195 | static dev_t | | 188 | static dev_t |
196 | pack_12_20(int n, unsigned long numbers[], const char **error) | | 189 | pack_12_20(int n, unsigned long numbers[], const char **error) |
197 | { | | 190 | { |
198 | dev_t dev = 0; | | 191 | dev_t dev = 0; |
199 | | | 192 | |
200 | if (n == 2) { | | 193 | if (n == 2) { |
201 | dev = makedev_12_20(numbers[0], numbers[1]); | | 194 | dev = makedev_12_20(numbers[0], numbers[1]); |
202 | if ((unsigned long)major_12_20(dev) != numbers[0]) | | 195 | if ((unsigned long)major_12_20(dev) != numbers[0]) |
203 | *error = iMajorError; | | 196 | *error = iMajorError; |
204 | if ((unsigned long)minor_12_20(dev) != numbers[1]) | | 197 | if ((unsigned long)minor_12_20(dev) != numbers[1]) |
205 | *error = iMinorError; | | 198 | *error = iMinorError; |
206 | } else | | 199 | } else |
207 | *error = tooManyFields; | | 200 | *error = tooManyFields; |
208 | return (dev); | | 201 | return (dev); |
209 | } | | 202 | } |
210 | | | 203 | |
211 | | | 204 | |
212 | #define major_14_18(x) ((int32_t)(((x) & 0xfffc0000) >> 18)) | | 205 | #define major_14_18(x) ((int32_t)(((x) & 0xfffc0000) >> 18)) |
213 | #define minor_14_18(x) ((int32_t)(((x) & 0x0003ffff) >> 0)) | | 206 | #define minor_14_18(x) ((int32_t)(((x) & 0x0003ffff) >> 0)) |
214 | #define makedev_14_18(x,y) ((dev_t)((((x) << 18) & 0xfffc0000) | \ | | 207 | #define makedev_14_18(x,y) ((dev_t)((((x) << 18) & 0xfffc0000) | \ |
215 | (((y) << 0) & 0x0003ffff))) | | 208 | (((y) << 0) & 0x0003ffff))) |
216 | | | 209 | |
217 | static dev_t | | 210 | static dev_t |
218 | pack_14_18(int n, unsigned long numbers[], const char **error) | | 211 | pack_14_18(int n, unsigned long numbers[], const char **error) |
219 | { | | 212 | { |
220 | dev_t dev = 0; | | 213 | dev_t dev = 0; |
221 | | | 214 | |
222 | if (n == 2) { | | 215 | if (n == 2) { |
223 | dev = makedev_14_18(numbers[0], numbers[1]); | | 216 | dev = makedev_14_18(numbers[0], numbers[1]); |
224 | if ((unsigned long)major_14_18(dev) != numbers[0]) | | 217 | if ((unsigned long)major_14_18(dev) != numbers[0]) |
225 | *error = iMajorError; | | 218 | *error = iMajorError; |
226 | if ((unsigned long)minor_14_18(dev) != numbers[1]) | | 219 | if ((unsigned long)minor_14_18(dev) != numbers[1]) |
227 | *error = iMinorError; | | 220 | *error = iMinorError; |
228 | } else | | 221 | } else |
229 | *error = tooManyFields; | | 222 | *error = tooManyFields; |
230 | return (dev); | | 223 | return (dev); |
231 | } | | 224 | } |
232 | | | 225 | |
233 | | | 226 | |
234 | #define major_8_24(x) ((int32_t)(((x) & 0xff000000) >> 24)) | | 227 | #define major_8_24(x) ((int32_t)(((x) & 0xff000000) >> 24)) |
235 | #define minor_8_24(x) ((int32_t)(((x) & 0x00ffffff) >> 0)) | | 228 | #define minor_8_24(x) ((int32_t)(((x) & 0x00ffffff) >> 0)) |
236 | #define makedev_8_24(x,y) ((dev_t)((((x) << 24) & 0xff000000) | \ | | 229 | #define makedev_8_24(x,y) ((dev_t)((((x) << 24) & 0xff000000) | \ |
237 | (((y) << 0) & 0x00ffffff))) | | 230 | (((y) << 0) & 0x00ffffff))) |
238 | | | 231 | |
239 | static dev_t | | 232 | static dev_t |
240 | pack_8_24(int n, unsigned long numbers[], const char **error) | | 233 | pack_8_24(int n, unsigned long numbers[], const char **error) |
241 | { | | 234 | { |
242 | dev_t dev = 0; | | 235 | dev_t dev = 0; |
243 | | | 236 | |
244 | if (n == 2) { | | 237 | if (n == 2) { |
245 | dev = makedev_8_24(numbers[0], numbers[1]); | | 238 | dev = makedev_8_24(numbers[0], numbers[1]); |
246 | if ((unsigned long)major_8_24(dev) != numbers[0]) | | 239 | if ((unsigned long)major_8_24(dev) != numbers[0]) |
247 | *error = iMajorError; | | 240 | *error = iMajorError; |
248 | if ((unsigned long)minor_8_24(dev) != numbers[1]) | | 241 | if ((unsigned long)minor_8_24(dev) != numbers[1]) |
249 | *error = iMinorError; | | 242 | *error = iMinorError; |
250 | } else | | 243 | } else |
251 | *error = tooManyFields; | | 244 | *error = tooManyFields; |
252 | return (dev); | | 245 | return (dev); |
253 | } | | 246 | } |
254 | | | 247 | |
255 | | | 248 | |
256 | #define major_12_12_8(x) ((int32_t)(((x) & 0xfff00000) >> 20)) | | 249 | #define major_12_12_8(x) ((int32_t)(((x) & 0xfff00000) >> 20)) |
257 | #define unit_12_12_8(x) ((int32_t)(((x) & 0x000fff00) >> 8)) | | 250 | #define unit_12_12_8(x) ((int32_t)(((x) & 0x000fff00) >> 8)) |
258 | #define subunit_12_12_8(x) ((int32_t)(((x) & 0x000000ff) >> 0)) | | 251 | #define subunit_12_12_8(x) ((int32_t)(((x) & 0x000000ff) >> 0)) |
259 | #define makedev_12_12_8(x,y,z) ((dev_t)((((x) << 20) & 0xfff00000) | \ | | 252 | #define makedev_12_12_8(x,y,z) ((dev_t)((((x) << 20) & 0xfff00000) | \ |
260 | (((y) << 8) & 0x000fff00) | \ | | 253 | (((y) << 8) & 0x000fff00) | \ |
261 | (((z) << 0) & 0x000000ff))) | | 254 | (((z) << 0) & 0x000000ff))) |
262 | | | 255 | |
263 | static dev_t | | 256 | static dev_t |
264 | pack_bsdos(int n, unsigned long numbers[], const char **error) | | 257 | pack_bsdos(int n, unsigned long numbers[], const char **error) |
265 | { | | 258 | { |
266 | dev_t dev = 0; | | 259 | dev_t dev = 0; |
267 | | | 260 | |
268 | if (n == 2) { | | 261 | if (n == 2) { |
269 | dev = makedev_12_20(numbers[0], numbers[1]); | | 262 | dev = makedev_12_20(numbers[0], numbers[1]); |
270 | if ((unsigned long)major_12_20(dev) != numbers[0]) | | 263 | if ((unsigned long)major_12_20(dev) != numbers[0]) |
271 | *error = iMajorError; | | 264 | *error = iMajorError; |
272 | if ((unsigned long)minor_12_20(dev) != numbers[1]) | | 265 | if ((unsigned long)minor_12_20(dev) != numbers[1]) |
273 | *error = iMinorError; | | 266 | *error = iMinorError; |
274 | } else if (n == 3) { | | 267 | } else if (n == 3) { |
275 | dev = makedev_12_12_8(numbers[0], numbers[1], numbers[2]); | | 268 | dev = makedev_12_12_8(numbers[0], numbers[1], numbers[2]); |
276 | if ((unsigned long)major_12_12_8(dev) != numbers[0]) | | 269 | if ((unsigned long)major_12_12_8(dev) != numbers[0]) |
277 | *error = iMajorError; | | 270 | *error = iMajorError; |
278 | if ((unsigned long)unit_12_12_8(dev) != numbers[1]) | | 271 | if ((unsigned long)unit_12_12_8(dev) != numbers[1]) |
279 | *error = "invalid unit number"; | | 272 | *error = "invalid unit number"; |
280 | if ((unsigned long)subunit_12_12_8(dev) != numbers[2]) | | 273 | if ((unsigned long)subunit_12_12_8(dev) != numbers[2]) |
281 | *error = "invalid subunit number"; | | 274 | *error = "invalid subunit number"; |
282 | } else | | 275 | } else |
283 | *error = tooManyFields; | | 276 | *error = tooManyFields; |
284 | return (dev); | | 277 | return (dev); |
285 | } | | 278 | } |
286 | | | 279 | |
287 | | | 280 | |
288 | /* list of formats and pack functions */ | | 281 | /* list of formats and pack functions */ |
289 | /* this list must be sorted lexically */ | | 282 | /* this list must be sorted lexically */ |
290 | static const struct format { | | 283 | static const struct format { |
291 | const char *name; | | 284 | const char *name; |
292 | pack_t *pack; | | 285 | pack_t *pack; |
293 | } formats[] = { | | 286 | } formats[] = { |
294 | {"386bsd", pack_8_8}, | | 287 | {"386bsd", pack_8_8}, |
295 | {"4bsd", pack_8_8}, | | 288 | {"4bsd", pack_8_8}, |
296 | {"bsdos", pack_bsdos}, | | 289 | {"bsdos", pack_bsdos}, |
297 | {"freebsd", pack_freebsd}, | | 290 | {"freebsd", pack_freebsd}, |
298 | {"hpux", pack_8_24}, | | 291 | {"hpux", pack_8_24}, |
299 | {"isc", pack_8_8}, | | 292 | {"isc", pack_8_8}, |
300 | {"linux", pack_8_8}, | | 293 | {"linux", pack_8_8}, |
301 | {"native", pack_native}, | | 294 | {"native", pack_native}, |
302 | {"netbsd", pack_netbsd}, | | 295 | {"netbsd", pack_netbsd}, |
303 | {"osf1", pack_12_20}, | | 296 | {"osf1", pack_12_20}, |
304 | {"sco", pack_8_8}, | | 297 | {"sco", pack_8_8}, |
305 | {"solaris", pack_14_18}, | | 298 | {"solaris", pack_14_18}, |
306 | {"sunos", pack_8_8}, | | 299 | {"sunos", pack_8_8}, |
307 | {"svr3", pack_8_8}, | | 300 | {"svr3", pack_8_8}, |
308 | {"svr4", pack_14_18}, | | 301 | {"svr4", pack_14_18}, |
309 | {"ultrix", pack_8_8}, | | 302 | {"ultrix", pack_8_8}, |
310 | }; | | 303 | }; |
311 | | | 304 | |
312 | static int | | 305 | static int |
313 | __LA_LIBC_CC | | 306 | __LA_LIBC_CC |
314 | compare_format(const void *key, const void *element) | | 307 | compare_format(const void *key, const void *element) |
315 | { | | 308 | { |
316 | const char *name; | | 309 | const char *name; |
317 | const struct format *format; | | 310 | const struct format *format; |
318 | | | 311 | |
319 | name = key; | | 312 | name = key; |
320 | format = element; | | 313 | format = element; |
321 | | | 314 | |
322 | return (strcmp(name, format->name)); | | 315 | return (strcmp(name, format->name)); |
323 | } | | 316 | } |
324 | | | 317 | |
325 | | | 318 | |
326 | pack_t * | | 319 | pack_t * |
327 | pack_find(const char *name) | | 320 | pack_find(const char *name) |
328 | { | | 321 | { |
329 | struct format *format; | | 322 | struct format *format; |
330 | | | 323 | |
331 | format = bsearch(name, formats, | | 324 | format = bsearch(name, formats, |
332 | sizeof(formats)/sizeof(formats[0]), | | 325 | sizeof(formats)/sizeof(formats[0]), |
333 | sizeof(formats[0]), compare_format); | | 326 | sizeof(formats[0]), compare_format); |
334 | if (format == 0) | | 327 | if (format == 0) |
335 | return (NULL); | | 328 | return (NULL); |
336 | return (format->pack); | | 329 | return (format->pack); |
337 | } | | 330 | } |