2
2
See the file COPYING for copying permission.
3
3
*/
4
4
5
+ #include <stddef.h>
6
+ #include <string.h> /* memset(), memcpy() */
7
+ #include <assert.h>
8
+ #include <limits.h> /* UINT_MAX */
9
+
10
+ #ifdef WIN32
11
+ #define getpid GetCurrentProcessId
12
+ #else
13
+ #include <sys/time.h> /* gettimeofday() */
14
+ #include <sys/types.h> /* getpid() */
15
+ #include <unistd.h> /* getpid() */
16
+ #endif
17
+
5
18
#define XML_BUILDING_EXPAT 1
6
19
7
- #ifdef COMPILED_FROM_DSP
20
+ #ifdef WIN32
8
21
#include "winconfig.h"
9
22
#elif defined(MACOS_CLASSIC )
10
23
#include "macconfig.h"
14
27
#include "watcomconfig.h"
15
28
#elif defined(HAVE_EXPAT_CONFIG_H )
16
29
#include <expat_config.h>
17
- #endif /* ndef COMPILED_FROM_DSP */
18
-
19
- #include <stddef.h>
20
- #include <string.h> /* memset(), memcpy() */
21
- #include <assert.h>
22
- #include <limits.h> /* UINT_MAX */
23
- #include <time.h> /* time() */
30
+ #endif /* ndef WIN32 */
24
31
25
32
#include "ascii.h"
26
33
#include "expat.h"
@@ -432,7 +439,7 @@ static ELEMENT_TYPE *
432
439
getElementType (XML_Parser parser , const ENCODING * enc ,
433
440
const char * ptr , const char * end );
434
441
435
- static unsigned long generate_hash_secret_salt (void );
442
+ static unsigned long generate_hash_secret_salt (XML_Parser parser );
436
443
static XML_Bool startParsing (XML_Parser parser );
437
444
438
445
static XML_Parser
@@ -691,19 +698,46 @@ static const XML_Char implicitContext[] = {
691
698
};
692
699
693
700
static unsigned long
694
- generate_hash_secret_salt (void )
701
+ gather_time_entropy (void )
695
702
{
696
- unsigned int seed = time (NULL ) % UINT_MAX ;
697
- srand (seed );
698
- return rand ();
703
+ #ifdef WIN32
704
+ FILETIME ft ;
705
+ GetSystemTimeAsFileTime (& ft ); /* never fails */
706
+ return ft .dwHighDateTime ^ ft .dwLowDateTime ;
707
+ #else
708
+ struct timeval tv ;
709
+ int gettimeofday_res ;
710
+
711
+ gettimeofday_res = gettimeofday (& tv , NULL );
712
+ assert (gettimeofday_res == 0 );
713
+
714
+ /* Microseconds time is <20 bits entropy */
715
+ return tv .tv_usec ;
716
+ #endif
717
+ }
718
+
719
+ static unsigned long
720
+ generate_hash_secret_salt (XML_Parser parser )
721
+ {
722
+ /* Process ID is 0 bits entropy if attacker has local access
723
+ * XML_Parser address is few bits of entropy if attacker has local access */
724
+ const unsigned long entropy =
725
+ gather_time_entropy () ^ getpid () ^ (unsigned long )parser ;
726
+
727
+ /* Factors are 2^31-1 and 2^61-1 (Mersenne primes M31 and M61) */
728
+ if (sizeof (unsigned long ) == 4 ) {
729
+ return entropy * 2147483647 ;
730
+ } else {
731
+ return entropy * (unsigned long )2305843009213693951 ;
732
+ }
699
733
}
700
734
701
735
static XML_Bool /* only valid for root parser */
702
736
startParsing (XML_Parser parser )
703
737
{
704
738
/* hash functions must be initialized before setContext() is called */
705
739
if (hash_secret_salt == 0 )
706
- hash_secret_salt = generate_hash_secret_salt ();
740
+ hash_secret_salt = generate_hash_secret_salt (parser );
707
741
if (ns ) {
708
742
/* implicit context only set for root parser, since child
709
743
parsers (i.e. external entity parsers) will inherit it
@@ -1695,15 +1729,15 @@ XML_GetBuffer(XML_Parser parser, int len)
1695
1729
if (len > bufferLim - bufferEnd ) {
1696
1730
#ifdef XML_CONTEXT_BYTES
1697
1731
int keep ;
1698
- #endif
1699
- int neededSize = len + (int )(bufferEnd - bufferPtr );
1732
+ #endif /* defined XML_CONTEXT_BYTES */
1733
+ /* Do not invoke signed arithmetic overflow: */
1734
+ int neededSize = (int ) ((unsigned )len + (unsigned )(bufferEnd - bufferPtr ));
1700
1735
if (neededSize < 0 ) {
1701
1736
errorCode = XML_ERROR_NO_MEMORY ;
1702
1737
return NULL ;
1703
1738
}
1704
1739
#ifdef XML_CONTEXT_BYTES
1705
1740
keep = (int )(bufferPtr - buffer );
1706
-
1707
1741
if (keep > XML_CONTEXT_BYTES )
1708
1742
keep = XML_CONTEXT_BYTES ;
1709
1743
neededSize += keep ;
@@ -1728,7 +1762,8 @@ XML_GetBuffer(XML_Parser parser, int len)
1728
1762
if (bufferSize == 0 )
1729
1763
bufferSize = INIT_BUFFER_SIZE ;
1730
1764
do {
1731
- bufferSize *= 2 ;
1765
+ /* Do not invoke signed arithmetic overflow: */
1766
+ bufferSize = (int ) (2U * (unsigned ) bufferSize );
1732
1767
} while (bufferSize < neededSize && bufferSize > 0 );
1733
1768
if (bufferSize <= 0 ) {
1734
1769
errorCode = XML_ERROR_NO_MEMORY ;
@@ -1855,7 +1890,7 @@ XML_Index XMLCALL
1855
1890
XML_GetCurrentByteIndex (XML_Parser parser )
1856
1891
{
1857
1892
if (eventPtr )
1858
- return parseEndByteIndex - (parseEndPtr - eventPtr );
1893
+ return ( XML_Index )( parseEndByteIndex - (parseEndPtr - eventPtr ) );
1859
1894
return -1 ;
1860
1895
}
1861
1896
@@ -2429,11 +2464,11 @@ doContent(XML_Parser parser,
2429
2464
for (;;) {
2430
2465
int bufSize ;
2431
2466
int convLen ;
2432
- XmlConvert (enc ,
2467
+ const enum XML_Convert_Result convert_res = XmlConvert (enc ,
2433
2468
& fromPtr , rawNameEnd ,
2434
2469
(ICHAR * * )& toPtr , (ICHAR * )tag -> bufEnd - 1 );
2435
2470
convLen = (int )(toPtr - (XML_Char * )tag -> buf );
2436
- if (fromPtr == rawNameEnd ) {
2471
+ if (( convert_res == XML_CONVERT_COMPLETED ) || ( convert_res == XML_CONVERT_INPUT_INCOMPLETE ) ) {
2437
2472
tag -> name .strLen = convLen ;
2438
2473
break ;
2439
2474
}
@@ -2654,11 +2689,11 @@ doContent(XML_Parser parser,
2654
2689
if (MUST_CONVERT (enc , s )) {
2655
2690
for (;;) {
2656
2691
ICHAR * dataPtr = (ICHAR * )dataBuf ;
2657
- XmlConvert (enc , & s , next , & dataPtr , (ICHAR * )dataBufEnd );
2692
+ const enum XML_Convert_Result convert_res = XmlConvert (enc , & s , next , & dataPtr , (ICHAR * )dataBufEnd );
2658
2693
* eventEndPP = s ;
2659
2694
charDataHandler (handlerArg , dataBuf ,
2660
2695
(int )(dataPtr - (ICHAR * )dataBuf ));
2661
- if (s == next )
2696
+ if (( convert_res == XML_CONVERT_COMPLETED ) || ( convert_res == XML_CONVERT_INPUT_INCOMPLETE ) )
2662
2697
break ;
2663
2698
* eventPP = s ;
2664
2699
}
@@ -3264,11 +3299,11 @@ doCdataSection(XML_Parser parser,
3264
3299
if (MUST_CONVERT (enc , s )) {
3265
3300
for (;;) {
3266
3301
ICHAR * dataPtr = (ICHAR * )dataBuf ;
3267
- XmlConvert (enc , & s , next , & dataPtr , (ICHAR * )dataBufEnd );
3302
+ const enum XML_Convert_Result convert_res = XmlConvert (enc , & s , next , & dataPtr , (ICHAR * )dataBufEnd );
3268
3303
* eventEndPP = next ;
3269
3304
charDataHandler (handlerArg , dataBuf ,
3270
3305
(int )(dataPtr - (ICHAR * )dataBuf ));
3271
- if (s == next )
3306
+ if (( convert_res == XML_CONVERT_COMPLETED ) || ( convert_res == XML_CONVERT_INPUT_INCOMPLETE ) )
3272
3307
break ;
3273
3308
* eventPP = s ;
3274
3309
}
@@ -4927,9 +4962,9 @@ internalEntityProcessor(XML_Parser parser,
4927
4962
4928
4963
static enum XML_Error PTRCALL
4929
4964
errorProcessor (XML_Parser parser ,
4930
- const char * s ,
4931
- const char * end ,
4932
- const char * * nextPtr )
4965
+ const char * UNUSED_P ( s ) ,
4966
+ const char * UNUSED_P ( end ) ,
4967
+ const char * * UNUSED_P ( nextPtr ) )
4933
4968
{
4934
4969
return errorCode ;
4935
4970
}
@@ -5345,6 +5380,7 @@ reportDefault(XML_Parser parser, const ENCODING *enc,
5345
5380
const char * s , const char * end )
5346
5381
{
5347
5382
if (MUST_CONVERT (enc , s )) {
5383
+ enum XML_Convert_Result convert_res ;
5348
5384
const char * * eventPP ;
5349
5385
const char * * eventEndPP ;
5350
5386
if (enc == encoding ) {
@@ -5357,11 +5393,11 @@ reportDefault(XML_Parser parser, const ENCODING *enc,
5357
5393
}
5358
5394
do {
5359
5395
ICHAR * dataPtr = (ICHAR * )dataBuf ;
5360
- XmlConvert (enc , & s , end , & dataPtr , (ICHAR * )dataBufEnd );
5396
+ convert_res = XmlConvert (enc , & s , end , & dataPtr , (ICHAR * )dataBufEnd );
5361
5397
* eventEndPP = s ;
5362
5398
defaultHandler (handlerArg , dataBuf , (int )(dataPtr - (ICHAR * )dataBuf ));
5363
5399
* eventPP = s ;
5364
- } while (s != end );
5400
+ } while (( convert_res != XML_CONVERT_COMPLETED ) && ( convert_res != XML_CONVERT_INPUT_INCOMPLETE ) );
5365
5401
}
5366
5402
else
5367
5403
defaultHandler (handlerArg , (XML_Char * )s , (int )((XML_Char * )end - (XML_Char * )s ));
@@ -6166,8 +6202,8 @@ poolAppend(STRING_POOL *pool, const ENCODING *enc,
6166
6202
if (!pool -> ptr && !poolGrow (pool ))
6167
6203
return NULL ;
6168
6204
for (;;) {
6169
- XmlConvert (enc , & ptr , end , (ICHAR * * )& (pool -> ptr ), (ICHAR * )pool -> end );
6170
- if (ptr == end )
6205
+ const enum XML_Convert_Result convert_res = XmlConvert (enc , & ptr , end , (ICHAR * * )& (pool -> ptr ), (ICHAR * )pool -> end );
6206
+ if (( convert_res == XML_CONVERT_COMPLETED ) || ( convert_res == XML_CONVERT_INPUT_INCOMPLETE ) )
6171
6207
break ;
6172
6208
if (!poolGrow (pool ))
6173
6209
return NULL ;
@@ -6251,8 +6287,13 @@ poolGrow(STRING_POOL *pool)
6251
6287
}
6252
6288
}
6253
6289
if (pool -> blocks && pool -> start == pool -> blocks -> s ) {
6254
- int blockSize = (int )(pool -> end - pool -> start )* 2 ;
6255
- BLOCK * temp = (BLOCK * )
6290
+ BLOCK * temp ;
6291
+ int blockSize = (int )((unsigned )(pool -> end - pool -> start )* 2U );
6292
+
6293
+ if (blockSize < 0 )
6294
+ return XML_FALSE ;
6295
+
6296
+ temp = (BLOCK * )
6256
6297
pool -> mem -> realloc_fcn (pool -> blocks ,
6257
6298
(offsetof(BLOCK , s )
6258
6299
+ blockSize * sizeof (XML_Char )));
@@ -6267,6 +6308,10 @@ poolGrow(STRING_POOL *pool)
6267
6308
else {
6268
6309
BLOCK * tem ;
6269
6310
int blockSize = (int )(pool -> end - pool -> start );
6311
+
6312
+ if (blockSize < 0 )
6313
+ return XML_FALSE ;
6314
+
6270
6315
if (blockSize < INIT_BLOCK_SIZE )
6271
6316
blockSize = INIT_BLOCK_SIZE ;
6272
6317
else
0 commit comments