Annotation of src/usr.bin/hexdump/odsyntax.c, Revision 1.1.1.1
1.1 deraadt 1: /*-
2: * Copyright (c) 1990 The Regents of the University of California.
3: * All rights reserved.
4: *
5: * Redistribution and use in source and binary forms, with or without
6: * modification, are permitted provided that the following conditions
7: * are met:
8: * 1. Redistributions of source code must retain the above copyright
9: * notice, this list of conditions and the following disclaimer.
10: * 2. Redistributions in binary form must reproduce the above copyright
11: * notice, this list of conditions and the following disclaimer in the
12: * documentation and/or other materials provided with the distribution.
13: * 3. All advertising materials mentioning features or use of this software
14: * must display the following acknowledgement:
15: * This product includes software developed by the University of
16: * California, Berkeley and its contributors.
17: * 4. Neither the name of the University nor the names of its contributors
18: * may be used to endorse or promote products derived from this software
19: * without specific prior written permission.
20: *
21: * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
22: * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23: * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24: * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
25: * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26: * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
27: * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29: * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30: * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
31: * SUCH DAMAGE.
32: */
33:
34: #ifndef lint
35: /*static char sccsid[] = "from: @(#)odsyntax.c 5.4 (Berkeley) 3/8/91";*/
36: static char rcsid[] = "$Id: odsyntax.c,v 1.4 1993/08/01 18:14:46 mycroft Exp $";
37: #endif /* not lint */
38:
39: #include <sys/types.h>
40: #include <stdlib.h>
41: #include <stdio.h>
42: #include "hexdump.h"
43:
44: int deprecated;
45:
46: oldsyntax(argc, argvp)
47: int argc;
48: char ***argvp;
49: {
50: extern enum _vflag vflag;
51: extern FS *fshead;
52: extern char *optarg;
53: extern int length, optind;
54: int ch;
55: char **argv;
56: static void odprecede();
57:
58: deprecated = 1;
59: argv = *argvp;
60: while ((ch = getopt(argc, argv, "aBbcDdeFfHhIiLlOoPpswvXx")) != EOF)
61: switch (ch) {
62: case 'a':
63: odprecede();
64: add("16/1 \"%3_u \" \"\\n\"");
65: break;
66: case 'B':
67: case 'o':
68: odprecede();
69: add("8/2 \" %06o \" \"\\n\"");
70: break;
71: case 'b':
72: odprecede();
73: add("16/1 \"%03o \" \"\\n\"");
74: break;
75: case 'c':
76: odprecede();
77: add("16/1 \"%3_c \" \"\\n\"");
78: break;
79: case 'd':
80: odprecede();
81: add("8/2 \" %05u \" \"\\n\"");
82: break;
83: case 'D':
84: odprecede();
85: add("4/4 \" %010u \" \"\\n\"");
86: break;
87: case 'e': /* undocumented in od */
88: case 'F':
89: odprecede();
90: add("2/8 \" %21.14e \" \"\\n\"");
91: break;
92:
93: case 'f':
94: odprecede();
95: add("4/4 \" %14.7e \" \"\\n\"");
96: break;
97: case 'H':
98: case 'X':
99: odprecede();
100: add("4/4 \" %08x \" \"\\n\"");
101: break;
102: case 'h':
103: case 'x':
104: odprecede();
105: add("8/2 \" %04x \" \"\\n\"");
106: break;
107: case 'I':
108: case 'L':
109: case 'l':
110: odprecede();
111: add("4/4 \" %11d \" \"\\n\"");
112: break;
113: case 'i':
114: odprecede();
115: add("8/2 \" %6d \" \"\\n\"");
116: break;
117: case 'O':
118: odprecede();
119: add("4/4 \" %011o \" \"\\n\"");
120: break;
121: case 'v':
122: vflag = ALL;
123: break;
124: case 'P':
125: case 'p':
126: case 's':
127: case 'w':
128: case '?':
129: default:
130: (void)fprintf(stderr,
131: "od: od(1) has been deprecated for hexdump(1).\n");
132: if (ch != '?')
133: (void)fprintf(stderr,
134: "od: hexdump(1) compatibility doesn't support the -%c option%s\n",
135: ch, ch == 's' ? "; see strings(1)." : ".");
136: usage();
137: }
138:
139: if (!fshead) {
140: add("\"%07.7_Ao\n\"");
141: add("\"%07.7_ao \" 8/2 \"%06o \" \"\\n\"");
142: }
143:
144: argc -= optind;
145: *argvp += optind;
146:
147: odoffset(argc, argvp);
148: }
149:
150: #define ishexdigit(c) \
151: (c >= '0' && c <= '9' || c >= 'a' && c <= 'f' || c >= 'A' && c <= 'F')
152:
153: odoffset(argc, argvp)
154: int argc;
155: char ***argvp;
156: {
157: extern off_t skip;
158: register char *num, *p;
159: int base;
160: char *end;
161:
162: /*
163: * The offset syntax of od(1) was genuinely bizarre. First, if
164: * it started with a plus it had to be an offset. Otherwise, if
165: * there were at least two arguments, a number or lower-case 'x'
166: * followed by a number makes it an offset. By default it was
167: * octal; if it started with 'x' or '0x' it was hex. If it ended
168: * in a '.', it was decimal. If a 'b' or 'B' was appended, it
169: * multiplied the number by 512 or 1024 byte units. There was
170: * no way to assign a block count to a hex offset.
171: *
172: * We assumes it's a file if the offset is bad.
173: */
174: p = **argvp;
175: if (!p)
176: return;
177: if (*p != '+' && (argc < 2 ||
178: (!isdigit(p[0]) && (p[0] != 'x' || !ishexdigit(p[1])))))
179: return;
180:
181: base = 0;
182: /*
183: * skip over leading '+', 'x[0-9a-fA-f]' or '0x', and
184: * set base.
185: */
186: if (p[0] == '+')
187: ++p;
188: if (p[0] == 'x' && ishexdigit(p[1])) {
189: ++p;
190: base = 16;
191: } else if (p[0] == '0' && p[1] == 'x') {
192: p += 2;
193: base = 16;
194: }
195:
196: /* skip over the number */
197: if (base == 16)
198: for (num = p; ishexdigit(*p); ++p);
199: else
200: for (num = p; isdigit(*p); ++p);
201:
202: /* check for no number */
203: if (num == p)
204: return;
205:
206: /* if terminates with a '.', base is decimal */
207: if (*p == '.') {
208: if (base)
209: return;
210: base = 10;
211: }
212:
213: skip = strtol(num, &end, base ? base : 8);
214:
215: /* if end isn't the same as p, we got a non-octal digit */
216: if (end != p)
217: skip = 0;
218: else {
219: if (*p) {
220: if (*p == 'b')
221: skip *= 512;
222: else if (*p == 'B')
223: skip *= 1024;
224: ++p;
225: }
226: if (*p)
227: skip = 0;
228: else {
229: ++*argvp;
230: /*
231: * If the offset uses a non-octal base, the base of
232: * the offset is changed as well. This isn't pretty,
233: * but it's easy.
234: */
235: #define TYPE_OFFSET 7
236: if (base == 16) {
237: fshead->nextfu->fmt[TYPE_OFFSET] = 'x';
238: fshead->nextfs->nextfu->fmt[TYPE_OFFSET] = 'x';
239: } else if (base == 10) {
240: fshead->nextfu->fmt[TYPE_OFFSET] = 'd';
241: fshead->nextfs->nextfu->fmt[TYPE_OFFSET] = 'd';
242: }
243: }
244: }
245: }
246:
247: static void
248: odprecede()
249: {
250: static int first = 1;
251:
252: if (first) {
253: first = 0;
254: add("\"%07.7_Ao\n\"");
255: add("\"%07.7_ao \"");
256: } else
257: add("\" \"");
258: }