1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
|
-
+
|
/*
* tclBinary.c --
*
* This file contains the implementation of the "binary" Tcl built-in
* command and the Tcl binary data object.
*
* Copyright (c) 1997 by Sun Microsystems, Inc.
* Copyright (c) 1998-1999 by Scriptics Corporation.
*
* See the file "license.terms" for information on usage and redistribution of
* this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
* RCS: @(#) $Id: tclBinary.c,v 1.32 2006/11/07 14:10:51 dkf Exp $
* RCS: @(#) $Id: tclBinary.c,v 1.33 2007/02/20 23:24:04 nijtmans Exp $
*/
#include "tclInt.h"
#include "tclTomMath.h"
#include <math.h>
|
| ︙ | | |
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
|
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
|
-
+
|
static Tcl_Obj * ScanNumber(unsigned char *buffer, int type,
int flags, Tcl_HashTable **numberCachePtr);
static int SetByteArrayFromAny(Tcl_Interp *interp,
Tcl_Obj *objPtr);
static void UpdateStringOfByteArray(Tcl_Obj *listPtr);
static void DeleteScanNumberCache(Tcl_HashTable *numberCachePtr);
static int NeedReversing(int format);
static void CopyNumber(CONST void *from, void *to,
static void CopyNumber(const void *from, void *to,
unsigned int length, int type);
/*
* The following object type represents an array of bytes. An array of bytes
* is not equivalent to an internationalized string. Conceptually, a string is
* an array of 16-bit quantities organized as a sequence of properly formed
* UTF-8 characters, while a ByteArray is an array of 8-bit quantities.
|
| ︙ | | |
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
|
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
|
-
+
-
+
|
*/
#ifdef TCL_MEM_DEBUG
#undef Tcl_NewByteArrayObj
Tcl_Obj *
Tcl_NewByteArrayObj(
CONST unsigned char *bytes, /* The array of bytes used to initialize the
const unsigned char *bytes, /* The array of bytes used to initialize the
* new object. */
int length) /* Length of the array of bytes, which must be
* >= 0. */
{
return Tcl_DbNewByteArrayObj(bytes, length, "unknown", 0);
}
#else /* if not TCL_MEM_DEBUG */
Tcl_Obj *
Tcl_NewByteArrayObj(
CONST unsigned char *bytes, /* The array of bytes used to initialize the
const unsigned char *bytes, /* The array of bytes used to initialize the
* new object. */
int length) /* Length of the array of bytes, which must be
* >= 0. */
{
Tcl_Obj *objPtr;
TclNewObj(objPtr);
|
| ︙ | | |
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
|
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
|
-
+
-
+
-
+
-
+
|
*----------------------------------------------------------------------
*/
#ifdef TCL_MEM_DEBUG
Tcl_Obj *
Tcl_DbNewByteArrayObj(
CONST unsigned char *bytes, /* The array of bytes used to initialize the
const unsigned char *bytes, /* The array of bytes used to initialize the
* new object. */
int length, /* Length of the array of bytes, which must be
* >= 0. */
CONST char *file, /* The name of the source file calling this
const char *file, /* The name of the source file calling this
* procedure; used for debugging. */
int line) /* Line number in the source file; used for
* debugging. */
{
Tcl_Obj *objPtr;
TclDbNewObj(objPtr, file, line);
Tcl_SetByteArrayObj(objPtr, bytes, length);
return objPtr;
}
#else /* if not TCL_MEM_DEBUG */
Tcl_Obj *
Tcl_DbNewByteArrayObj(
CONST unsigned char *bytes, /* The array of bytes used to initialize the
const unsigned char *bytes, /* The array of bytes used to initialize the
* new object. */
int length, /* Length of the array of bytes, which must be
* >= 0. */
CONST char *file, /* The name of the source file calling this
const char *file, /* The name of the source file calling this
* procedure; used for debugging. */
int line) /* Line number in the source file; used for
* debugging. */
{
return Tcl_NewByteArrayObj(bytes, length);
}
#endif /* TCL_MEM_DEBUG */
|
| ︙ | | |
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
|
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
|
-
+
|
*
*----------------------------------------------------------------------
*/
void
Tcl_SetByteArrayObj(
Tcl_Obj *objPtr, /* Object to initialize as a ByteArray. */
CONST unsigned char *bytes, /* The array of bytes to use as the new
const unsigned char *bytes, /* The array of bytes to use as the new
* value. */
int length) /* Length of the array of bytes, which must be
* >= 0. */
{
ByteArray *byteArrayPtr;
if (Tcl_IsShared(objPtr)) {
|
| ︙ | | |
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
|
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
|
-
+
+
-
+
-
+
|
*/
int
Tcl_BinaryObjCmd(
ClientData dummy, /* Not used. */
Tcl_Interp *interp, /* Current interpreter. */
int objc, /* Number of arguments. */
Tcl_Obj *CONST objv[]) /* Argument objects. */
Tcl_Obj *const objv[]) /* Argument objects. */
{
int arg; /* Index of next argument to consume. */
int value = 0; /* Current integer value to be packed.
* Initialized to avoid compiler warning. */
char cmd; /* Current format character. */
int count; /* Count associated with current format
* character. */
int flags; /* Format field flags */
char *format; /* Pointer to current position in format
* string. */
Tcl_Obj *resultPtr = NULL; /* Object holding result buffer. */
unsigned char *buffer; /* Start of result buffer. */
unsigned char *cursor; /* Current position within result buffer. */
unsigned char *maxPos; /* Greatest position within result buffer that
* cursor has visited.*/
const char *errorString;
char *errorString, *errorValue, *str;
char *errorValue, *str;
int offset, size, length, index;
static CONST char *options[] = {
static const char *options[] = {
"format", "scan", NULL
};
enum options {
BINARY_FORMAT, BINARY_SCAN
};
if (objc < 2) {
|
| ︙ | | |
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168
1169
|
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168
1169
1170
|
-
+
|
break;
}
case 'h':
case 'H': {
char *dest;
unsigned char *src;
int i;
static CONST char hexdigit[] = "0123456789abcdef";
static const char hexdigit[] = "0123456789abcdef";
if (arg >= objc) {
DeleteScanNumberCache(numberCachePtr);
goto badIndex;
}
if (count == BINARY_ALL) {
count = (length - offset)*2;
|
| ︙ | | |
1537
1538
1539
1540
1541
1542
1543
1544
1545
1546
1547
1548
1549
1550
1551
1552
1553
1554
1555
1556
1557
1558
1559
1560
1561
|
1538
1539
1540
1541
1542
1543
1544
1545
1546
1547
1548
1549
1550
1551
1552
1553
1554
1555
1556
1557
1558
1559
1560
1561
1562
|
-
+
-
+
|
* Copies length bytes
*
*----------------------------------------------------------------------
*/
static void
CopyNumber(
CONST void *from, /* source */
const void *from, /* source */
void *to, /* destination */
unsigned int length, /* Number of bytes to copy */
int type) /* What type of thing are we copying? */
{
switch (NeedReversing(type)) {
case 0:
memcpy(to, from, length);
break;
case 1: {
CONST unsigned char *fromPtr = from;
const unsigned char *fromPtr = from;
unsigned char *toPtr = to;
switch (length) {
case 4:
toPtr[0] = fromPtr[3];
toPtr[1] = fromPtr[2];
toPtr[2] = fromPtr[1];
|
| ︙ | | |
1571
1572
1573
1574
1575
1576
1577
1578
1579
1580
1581
1582
1583
1584
1585
1586
1587
1588
1589
1590
1591
1592
1593
1594
1595
1596
1597
1598
1599
|
1572
1573
1574
1575
1576
1577
1578
1579
1580
1581
1582
1583
1584
1585
1586
1587
1588
1589
1590
1591
1592
1593
1594
1595
1596
1597
1598
1599
1600
|
-
+
-
+
|
toPtr[6] = fromPtr[1];
toPtr[7] = fromPtr[0];
break;
}
break;
}
case 2: {
CONST unsigned char *fromPtr = from;
const unsigned char *fromPtr = from;
unsigned char *toPtr = to;
toPtr[0] = fromPtr[4];
toPtr[1] = fromPtr[5];
toPtr[2] = fromPtr[6];
toPtr[3] = fromPtr[7];
toPtr[4] = fromPtr[0];
toPtr[5] = fromPtr[1];
toPtr[6] = fromPtr[2];
toPtr[7] = fromPtr[3];
break;
}
case 3: {
CONST unsigned char *fromPtr = from;
const unsigned char *fromPtr = from;
unsigned char *toPtr = to;
toPtr[0] = fromPtr[3];
toPtr[1] = fromPtr[2];
toPtr[2] = fromPtr[1];
toPtr[3] = fromPtr[0];
toPtr[4] = fromPtr[7];
|
| ︙ | | |