Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
att
GitHub Repository: att/ast
Path: blob/master/src/cmd/dsslib/ip_t/itlie.h
1810 views
1
/***********************************************************************
2
* *
3
* This software is part of the ast package *
4
* Copyright (c) 2000-2011 AT&T Intellectual Property *
5
* and is licensed under the *
6
* Eclipse Public License, Version 1.0 *
7
* by AT&T Intellectual Property *
8
* *
9
* A copy of the License is available at *
10
* http://www.eclipse.org/org/documents/epl-v10.html *
11
* (with md5 checksum b35adb5213ca9657e911e9befb180842) *
12
* *
13
* Information and Software Systems Research *
14
* AT&T Research *
15
* Florham Park NJ *
16
* *
17
* Glenn Fowler <[email protected]> *
18
* Phong Vo <[email protected]> *
19
* *
20
***********************************************************************/
21
#pragma prototyped
22
/*
23
* include this file to instantiate tuple cx externalf/internalf
24
* parameterized on these macros
25
*
26
* ITLINT the tuple element integral type
27
* ITLEXTERNAL convert to external
28
* ITLINTERNAL convert to internal
29
*
30
* macros must be defined before include
31
* macros undefined after include
32
*
33
* Glenn Fowler
34
* AT&T Research
35
*/
36
37
#include <ctype.h>
38
39
/*
40
* pretty print an ITLINT tuple list from value->buffer into buf
41
*/
42
43
ssize_t
44
ITLEXTERNAL(Cx_t* cx, Cxtype_t* type, int dots, int tuple, int group, const char* details, Cxformat_t** formats, Cxvalue_t* value, char* buf, size_t size, Cxdisc_t* disc)
45
{
46
ITLINT* ap;
47
Sfio_t* sp;
48
char* sep;
49
char* bet;
50
char* s;
51
char* t;
52
ITLINT v;
53
int def;
54
int fmt;
55
int b;
56
int i;
57
int j;
58
int k;
59
int m;
60
int n;
61
int g;
62
63
if (j = value->buffer.size / sizeof(ITLINT))
64
{
65
sep = (char*)CXDETAILS(details, formats[0], type, "");
66
if (!(fmt = *sep++))
67
{
68
fmt = 'd';
69
sep = ",";
70
def = 1;
71
}
72
else if (fmt == 's')
73
def = 1;
74
else
75
def = sep == type->format.details;
76
if (!*sep)
77
sep = ",";
78
bet = ":";
79
sp = cx->buf;
80
ap = (ITLINT*)value->buffer.data;
81
i = 0;
82
j -= tuple - 1;
83
g = j + 1 + !group;
84
while (i < j)
85
{
86
if (i > g)
87
{
88
g = j + 1;
89
sfprintf(sp, "}");
90
t = sep;
91
}
92
else if (g == (j + 1) && ap[i] == (ITLINT)(~0) && i < (j - 1))
93
{
94
i++;
95
if (ap[i])
96
{
97
g = i + ap[i];
98
sfprintf(sp, "%s", sep);
99
t = "{";
100
}
101
else
102
t = sep;
103
i++;
104
}
105
else
106
t = sep;
107
for (k = 0; k < tuple; i++, k++, t = bet)
108
{
109
sfprintf(sp, "%s", t);
110
if (def && formats && formats[k] && formats[k]->map && !cxnum2str(cx, formats[k], (Cxinteger_t)ap[i], &s))
111
sfprintf(sp, "%s", s);
112
else if (ap[i])
113
switch (fmt)
114
{
115
case 'd':
116
sfprintf(sp, "%d", ap[i]);
117
break;
118
case 'o':
119
sfprintf(sp, "0%o", ap[i]);
120
break;
121
case 'x':
122
sfprintf(sp, "0x%0*x", sizeof(ITLINT) * 2, ap[i]);
123
break;
124
case '.':
125
n = 8;
126
goto dotted;
127
case '1':
128
case '2':
129
case '4':
130
case '8':
131
n = (n - '0') * 8;
132
dotted:
133
v = ap[i];
134
m = (1 << n) - 1;
135
b = sizeof(ITLINT) * 8;
136
if ((b / n) == 2 && !((v >> n) & m))
137
b = n;
138
while ((b -= n) >= 0)
139
sfprintf(sp, "%u%s", (v >> b) & m, b ? "." : "");
140
break;
141
default:
142
if (dots)
143
{
144
n = dots * 8;
145
goto dotted;
146
}
147
sfprintf(sp, "%u", ap[i]);
148
break;
149
}
150
else
151
sfputc(sp, '0');
152
}
153
}
154
if (g < (j + 1))
155
sfputc(sp, '}');
156
i = sfstrtell(sp);
157
if (!(s = sfstruse(sp)))
158
{
159
if (disc->errorf)
160
(*disc->errorf)(NiL, disc, ERROR_SYSTEM|2, "out of space");
161
return -1;
162
}
163
if (j = strlen(sep))
164
{
165
s += j;
166
i -= j;
167
}
168
}
169
else
170
{
171
s = "";
172
i = 0;
173
}
174
if ((i + 1) > size)
175
return i + 1;
176
memcpy(buf, s, i + 1);
177
return i;
178
}
179
180
/*
181
* parse an ITLINT tuple list from buf into value->buffer
182
* return the number of bytes consumed from buf
183
*/
184
185
ssize_t
186
ITLINTERNAL(Cx_t* cx, Cxvalue_t* value, int dots, int tuple, int group, const char* buf, size_t size, Vmalloc_t* vm, Cxdisc_t* disc)
187
{
188
register char* s;
189
register char* e;
190
register int t;
191
char* p;
192
Sfio_t* sp;
193
ITLINT* vp;
194
ITLINT n;
195
ITLINT m;
196
size_t o;
197
size_t z;
198
199
sp = cx->buf;
200
o = 0;
201
t = 0;
202
s = (char*)buf;
203
e = s + size;
204
if (!dots)
205
dots = 1;
206
dots *= 8;
207
m = 1;
208
m = (m << dots) - 1;
209
for (; s < e; s++)
210
if (*s == ':' || isdigit(*s))
211
{
212
t++;
213
if (*s == ':')
214
n = 0;
215
else
216
{
217
n = strntol(s, e - s, &p, 0);
218
for (;;)
219
{
220
s = p;
221
if (s >= e || *s != '.')
222
break;
223
n = (n << dots) | (strntol(s, e - s, &p, 0) & m);
224
}
225
}
226
sfwrite(sp, &n, sizeof(n));
227
if (group && n == (ITLINT)(~0))
228
{
229
n = 0;
230
sfwrite(sp, &n, sizeof(n));
231
n = (ITLINT)(~0);
232
sfwrite(sp, &n, sizeof(n));
233
}
234
if (s < e && *s != ':')
235
{
236
s--;
237
n = 0;
238
while (t++ < tuple)
239
sfwrite(sp, &n, sizeof(n));
240
t = 0;
241
}
242
}
243
else if (*s == '{')
244
{
245
if (group)
246
{
247
n = (ITLINT)(~0);
248
sfwrite(sp, &n, sizeof(n));
249
o = sfstrtell(sp) / sizeof(n);
250
sfwrite(sp, &n, sizeof(n));
251
}
252
}
253
else if (isalpha(*s) || *s == '?')
254
break;
255
if (z = sfstrtell(sp) / sizeof(n))
256
{
257
if (!vm)
258
vm = Vmregion;
259
if (!(vp = vmnewof(vm, 0, ITLINT, z, 0)))
260
{
261
if (disc->errorf)
262
(*disc->errorf)(NiL, disc, ERROR_SYSTEM|2, "out of space");
263
return -1;
264
}
265
memcpy(vp, sfstrseek(sp, 0, SEEK_SET), z * sizeof(n));
266
if (o)
267
vp[o] = z - o;
268
}
269
else
270
vp = 0;
271
value->buffer.data = vp;
272
value->buffer.size = z * sizeof(n);
273
return s - (char*)buf;
274
}
275
276
#undef ITLINT
277
#undef ITLEXTERNAL
278
#undef ITLINTERNAL
279
280