audit: remove static local realms
[openafs.git] / src / tools / dumpscan / util.c
1 /*
2  * CMUCS AFStools
3  * dumpscan - routines for scanning and manipulating AFS volume dumps
4  *
5  * Copyright (c) 1998 Carnegie Mellon University
6  * All Rights Reserved.
7  *
8  * Permission to use, copy, modify and distribute this software and its
9  * documentation is hereby granted, provided that both the copyright
10  * notice and this permission notice appear in all copies of the
11  * software, derivative works or modified versions, and any portions
12  * thereof, and that both notices appear in supporting documentation.
13  *
14  * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS"
15  * CONDITION.  CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR
16  * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
17  *
18  * Carnegie Mellon requests users of this software to return to
19  *
20  *  Software Distribution Coordinator  or  Software_Distribution@CS.CMU.EDU
21  *  School of Computer Science
22  *  Carnegie Mellon University
23  *  Pittsburgh PA 15213-3890
24  *
25  * any improvements or extensions that they make and grant Carnegie Mellon
26  * the rights to redistribute these changes.
27  */
28
29 /* util.c - Useful utilities */
30
31 #include <errno.h>
32
33 #include "xf_errs.h"
34 #include "dumpscan.h"
35 #include "dumpscan_errs.h"
36 #include "dumpfmt.h"
37
38
39 /* Take care of errno, ERROR_XFILE_EOF, and ENOMEM return codes.
40  * Call whatever callbacks are necessary, and return the code to
41  * actually use.  If you don't want '0' to result in a DSERR_TAG,
42  * then you must translate it to DSERR_DONE before calling this.
43  */
44 /*** THIS FUNCTION INTENDED FOR INTERNAL USE ONLY ***/
45 int
46 handle_return(int r, XFILE * X, unsigned char tag, dump_parser * p)
47 {
48     dt_uint64 where, xwhere;
49
50     switch (r) {
51     case 0:
52         if (p->cb_error) {
53             xftell(X, &where);
54             sub64_32(xwhere, where, 1);
55             (p->cb_error) (DSERR_TAG, 1, p->err_refcon,
56                            (tag > 0x20 && tag < 0x7f)
57                            ? "Unexpected tag '%c' at %s = 0x%s" :
58                            "Unexpected tag 0x%02x at %s = 0x%s", tag,
59                            decimate_int64(&xwhere, 0), hexify_int64(&xwhere,
60                                                                     0));
61         }
62         return DSERR_TAG;
63
64     case ERROR_XFILE_EOF:
65         if (p->cb_error) {
66             xftell(X, &where);
67             (p->cb_error) (ERROR_XFILE_EOF, 1, p->err_refcon,
68                            "Unexpected EOF at %s = 0x%s",
69                            decimate_int64(&where, 0), hexify_int64(&where,
70                                                                    0));
71         }
72         return ERROR_XFILE_EOF;
73
74     case ENOMEM:
75         if (p->cb_error) {
76             xftell(X, &where);
77             (p->cb_error) (ENOMEM, 1, p->err_refcon,
78                            "Out of memory at %s = 0x%s",
79                            decimate_int64(&where, 0), hexify_int64(&where,
80                                                                    0));
81         }
82         return ENOMEM;
83
84     case DSERR_DONE:
85         return 0;
86
87     default:
88         /* For other negative valuees, the callback was already done */
89         if (r > 0 && p->cb_error)
90             (p->cb_error) (r, 1, p->err_refcon,
91                            "System error %d reading dump file", r);
92         return r;
93     }
94 }
95
96
97 /* Prepare a tag_parse_info for use by the dump parser. */
98 /* ** THIS FUNCTION INTENDED FOR INTERNAL USE ONLY ** */
99 void
100 prep_pi(dump_parser * p, tag_parse_info * pi)
101 {
102     memset(pi, 0, sizeof(tag_parse_info));
103     pi->err_refcon = p->err_refcon;
104     pi->cb_error = p->cb_error;
105
106     if (p->repair_flags & DSFIX_SKIP)
107         pi->flags |= TPFLAG_SKIP;
108     if ((p->flags & DSFLAG_SEEK) && (p->repair_flags & DSFIX_RSKIP))
109         pi->flags |= TPFLAG_RSKIP;
110 }
111
112
113 /* Does the designated location match a vnode?
114  * Returns 0 if yes, DSERR_FMT if no, something else on error
115  */
116 /*** THIS FUNCTION INTENDED FOR INTERNAL USE ONLY ***/
117 int
118 match_next_vnode(XFILE * X, dump_parser * p, dt_uint64 * where,
119                  afs_uint32 vnode)
120 {
121     afs_uint32 r, x, y, z;
122     unsigned char tag;
123
124     if ((r = xfseek(X, where)))
125         return r;
126     if ((r = ReadByte(X, &tag)))
127         return r;
128     switch (tag) {
129     case 3:                     /* A vnode? */
130         if ((r = ReadInt32(X, &x)))
131             return r;
132         if ((r = ReadInt32(X, &y)))
133             return r;
134         if ((r = ReadByte(X, &tag)))
135           return r;
136         if (!((vnode & 1) && !(x & 1) && x < vnode)
137             && !((vnode & 1) == (x & 1) && x > vnode))
138             return DSERR_FMT;
139         if (x > vnode && x - vnode > 10000)
140             return DSERR_FMT;
141         if (y < 0 || y > p->vol_uniquifier)
142             return DSERR_FMT;
143
144         /* Now, what follows the vnode/uniquifier? */
145         switch (tag) {
146         case 3:         /* Another vnode? - Only if this is a non-directory */
147             if (x & 1)
148                 return DSERR_FMT;
149             if ((r = ReadInt32(X, &z)))
150                 return r;
151             if (!((x & 1) && !(z & 1) && z < x)
152                 && !((x & 1) == (z & 1) && z > x))
153                 return DSERR_FMT;
154             return 0;
155
156         case 4:         /* Dump end - Only if this is a non-directory */
157             if (x & 1)
158                 return DSERR_FMT;
159             if ((r = ReadInt32(X, &z)))
160                 return r;
161             if (z != DUMPENDMAGIC)
162                 return DSERR_FMT;
163             return 0;
164
165         case 't':               /* Vnode type byte */
166             if ((r = ReadByte(X, &tag)))
167                 return r;
168             if ((tag == vFile || tag == vSymlink) && !(x & 1))
169                 return 0;
170             if (tag == vDirectory && (x & 1))
171                 return 0;
172             return DSERR_FMT;
173
174         default:
175             return DSERR_FMT;
176         }
177
178     case 4:                     /* A dump end? */
179         if ((r = ReadInt32(X, &x)))
180             return r;
181         if (x != DUMPENDMAGIC)
182             return DSERR_FMT;
183         return 0;
184
185     default:
186         return DSERR_FMT;
187     }
188 }