##// END OF EJS Templates
fix const annotation warning
Benoit Boissinot -
r6395:3f029453 default
parent child Browse files
Show More
@@ -1,168 +1,169 b''
1 1 /*
2 2 parsers.c - efficient content parsing
3 3
4 4 Copyright 2008 Matt Mackall <mpm@selenic.com> and others
5 5
6 6 This software may be used and distributed according to the terms of
7 7 the GNU General Public License, incorporated herein by reference.
8 8 */
9 9
10 10 #include <Python.h>
11 11 #include <ctype.h>
12 12 #include <string.h>
13 13
14 14 static int hexdigit(char c)
15 15 {
16 16 if (c >= '0' && c <= '9')
17 17 return c - '0';
18 18
19 19 if (c >= 'A' && c <= 'F')
20 20 return c - 'A' + 10;
21 21
22 22 if (c >= 'a' && c <= 'f')
23 23 return c - 'a' + 10;
24 24
25 25 return -1;
26 26 }
27 27
28 28 /*
29 29 * Turn a hex-encoded string into binary.
30 30 */
31 31 static PyObject *unhexlify(const char *str, int len)
32 32 {
33 33 PyObject *ret = NULL;
34 char *c, *d;
34 const char *c;
35 char *d;
35 36
36 37 if (len % 2) {
37 38 PyErr_SetString(PyExc_ValueError,
38 39 "input is not even in length");
39 40 goto bail;
40 41 }
41 42
42 43 ret = PyString_FromStringAndSize(NULL, len / 2);
43 44 if (!ret)
44 45 goto bail;
45 46
46 47 d = PyString_AsString(ret);
47 48 if (!d)
48 49 goto bail;
49 50
50 51 for (c = str; c < str + len;) {
51 52 int hi = hexdigit(*c++);
52 53 int lo = hexdigit(*c++);
53 54
54 55 if (hi == -1 || lo == -1) {
55 56 PyErr_SetString(PyExc_ValueError,
56 57 "input contains non-hex character");
57 58 goto bail;
58 59 }
59 60
60 61 *d++ = (hi << 4) | lo;
61 62 }
62 63
63 64 goto done;
64 65
65 66 bail:
66 67 Py_XDECREF(ret);
67 68 ret = NULL;
68 69 done:
69 70 return ret;
70 71 }
71 72
72 73 /*
73 74 * This code assumes that a manifest is stitched together with newline
74 75 * ('\n') characters.
75 76 */
76 77 static PyObject *parse_manifest(PyObject *self, PyObject *args)
77 78 {
78 79 PyObject *mfdict, *fdict;
79 80 char *str, *cur, *start, *zero;
80 81 int len;
81 82
82 83 if (!PyArg_ParseTuple(args, "O!O!s#:parse_manifest",
83 84 &PyDict_Type, &mfdict,
84 85 &PyDict_Type, &fdict,
85 86 &str, &len))
86 87 goto quit;
87 88
88 89 for (start = cur = str, zero = NULL; cur < str + len; cur++) {
89 90 PyObject *file = NULL, *node = NULL;
90 91 PyObject *flags = NULL;
91 92 int nlen;
92 93
93 94 if (!*cur) {
94 95 zero = cur;
95 96 continue;
96 97 }
97 98 else if (*cur != '\n')
98 99 continue;
99 100
100 101 if (!zero) {
101 102 PyErr_SetString(PyExc_ValueError,
102 103 "manifest entry has no separator");
103 104 goto quit;
104 105 }
105 106
106 107 file = PyString_FromStringAndSize(start, zero - start);
107 108 if (!file)
108 109 goto bail;
109 110
110 111 nlen = cur - zero - 1;
111 112
112 113 node = unhexlify(zero + 1, nlen > 40 ? 40 : nlen);
113 114 if (!node)
114 115 goto bail;
115 116
116 117 if (nlen > 40) {
117 118 PyObject *flags;
118 119
119 120 flags = PyString_FromStringAndSize(zero + 41,
120 121 nlen - 40);
121 122 if (!flags)
122 123 goto bail;
123 124
124 125 if (PyDict_SetItem(fdict, file, flags) == -1)
125 126 goto bail;
126 127 }
127 128
128 129 if (PyDict_SetItem(mfdict, file, node) == -1)
129 130 goto bail;
130 131
131 132 start = cur + 1;
132 133 zero = NULL;
133 134
134 135 Py_XDECREF(flags);
135 136 Py_XDECREF(node);
136 137 Py_XDECREF(file);
137 138 continue;
138 139 bail:
139 140 Py_XDECREF(flags);
140 141 Py_XDECREF(node);
141 142 Py_XDECREF(file);
142 143 goto quit;
143 144 }
144 145
145 146 if (len > 0 && *(cur - 1) != '\n') {
146 147 PyErr_SetString(PyExc_ValueError,
147 148 "manifest contains trailing garbage");
148 149 goto quit;
149 150 }
150 151
151 152 Py_INCREF(Py_None);
152 153 return Py_None;
153 154
154 155 quit:
155 156 return NULL;
156 157 }
157 158
158 159 static char parsers_doc[] = "Efficient content parsing.";
159 160
160 161 static PyMethodDef methods[] = {
161 162 {"parse_manifest", parse_manifest, METH_VARARGS, "parse a manifest\n"},
162 163 {NULL, NULL}
163 164 };
164 165
165 166 PyMODINIT_FUNC initparsers(void)
166 167 {
167 168 Py_InitModule3("parsers", methods, parsers_doc);
168 169 }
General Comments 0
You need to be logged in to leave comments. Login now