source: trunk/libtransmission/bencode-test.c @ 4869

Last change on this file since 4869 was 4869, checked in by charles, 14 years ago

part 1 of the bencode exploit fix:

  • better error checking for int & string parsing
  • add automated unit tests
File size: 3.3 KB
Line 
1#include <stdio.h>
2#include "transmission.h"
3#include "bencode.h"
4#include "utils.h" /* tr_free */
5
6#define VERBOSE 1
7
8int test = 0;
9
10#define check(A) { \
11    ++test; \
12    if (A) { \
13        if( VERBOSE ) \
14            fprintf( stderr, "PASS test #%d (%s, %d)\n", test, __FILE__, __LINE__ ); \
15    } else { \
16        if( VERBOSE ) \
17            fprintf( stderr, "FAIL test #%d (%s, %d)\n", test, __FILE__, __LINE__ ); \
18        return test; \
19    } \
20}
21
22static int
23testInt( void )
24{
25    uint8_t buf[128];
26    int64_t val;
27    int err;
28    const uint8_t * end;
29
30    /* good int string */
31    snprintf( (char*)buf, sizeof( buf ), "i64e" );
32    err = tr_bencParseInt( buf, 4, &end, &val );
33    check( err == 0 );
34    check( val == 64 );
35    check( end == buf + 4 );
36
37    /* missing 'e' */
38    end = NULL;
39    val = 888;
40    err = tr_bencParseInt( buf, 3, &end, &val );
41    check( err == TR_ERROR ); 
42    check( val == 888 );
43    check( end == NULL );
44
45    /* empty buffer */
46    err = tr_bencParseInt( buf, 0, &end, &val );
47    check( err == TR_ERROR ); 
48    check( val == 888 );
49    check( end == NULL );
50
51    /* bad number */
52    snprintf( (char*)buf, sizeof( buf ), "i6z4e" );
53    err = tr_bencParseInt( buf, 4, &end, &val );
54    check( err == TR_ERROR );
55    check( val == 888 );
56    check( end == NULL );
57
58    /* negative number */
59    snprintf( (char*)buf, sizeof( buf ), "i-3e" );
60    err = tr_bencParseInt( buf, 4, &end, &val );
61    check( err == TR_OK );
62    check( val == -3 );
63    check( end == buf + 4 );
64
65    /* zero */
66    snprintf( (char*)buf, sizeof( buf ), "i0e" );
67    err = tr_bencParseInt( buf, 4, &end, &val );
68    check( err == TR_OK );
69    check( val == 0 );
70    check( end == buf + 3 );
71
72    /* no leading zeroes allowed */
73    val = 0;
74    end = NULL;
75    snprintf( (char*)buf, sizeof( buf ), "i04e" );
76    err = tr_bencParseInt( buf, 4, &end, &val );
77    check( err == TR_ERROR );
78    check( val == 0 );
79    check( end == NULL );
80
81    return 0;
82}
83
84static int
85testStr( void )
86{
87    uint8_t buf[128];
88    int err;
89    const uint8_t * end;
90    uint8_t * str;
91    size_t len;
92
93    /* good string */
94    snprintf( (char*)buf, sizeof( buf ), "4:boat" );
95    err = tr_bencParseStr( buf, 6, &end, &str, &len );
96    check( err == TR_OK );
97    check( !strcmp( (char*)str, "boat" ) );
98    check( len == 4 );
99    check( end == buf + 6 );
100    tr_free( str );
101    str = NULL;
102    end = NULL;
103    len = 0;
104
105    /* string goes past end of buffer */
106    err = tr_bencParseStr( buf, 5, &end, &str, &len );
107    check( err == TR_ERROR );
108    check( str == NULL );
109    check( end == NULL );
110    check( !len );
111
112    /* empty string */
113    snprintf( (char*)buf, sizeof( buf ), "0:" );
114    err = tr_bencParseStr( buf, 2, &end, &str, &len );
115    check( err == TR_OK );
116    check( !*str );
117    check( !len );
118    check( end == buf + 2 );
119    tr_free( str );
120    str = NULL;
121    end = NULL;
122    len = 0;
123
124    /* short string */
125    snprintf( (char*)buf, sizeof( buf ), "3:boat" );
126    err = tr_bencParseStr( buf, 6, &end, &str, &len );
127    check( err == TR_OK );
128    check( !strcmp( (char*)str, "boa" ) );
129    check( len == 3 );
130    check( end == buf + 5 );
131    tr_free( str );
132    str = NULL;
133    end = NULL;
134    len = 0;
135
136    return 0;
137}
138 
139int
140main( void )
141{
142    int i;
143
144    if(( i = testInt( ) ))
145        return i;
146
147    if(( i = testStr( ) ))
148        return i;
149
150    return 0;
151}
Note: See TracBrowser for help on using the repository browser.