OLD | NEW |
| (Empty) |
1 From 0d13e8740021aeeb849662f03f49720287cabe0c Mon Sep 17 00:00:00 2001 | |
2 From: Scott Hess <shess@chromium.org> | |
3 Date: Fri, 26 Feb 2016 10:49:33 -0800 | |
4 Subject: [PATCH 13/13] [backport] Fix buffer overrun in ICU extension's | |
5 casemap functions. | |
6 | |
7 Original Chromium CL at https://codereview.chromium.org/1704103002 | |
8 | |
9 "Fix sqlite3's handling of casemapping result 3 times as long as input" | |
10 | |
11 SQLite interpretation at http://www.sqlite.org/src/info/b8dc1b9f5d413000 | |
12 | |
13 "Fix a potential buffer overflow in the ICU upper() function." | |
14 | |
15 BUG=586079 | |
16 --- | |
17 third_party/sqlite/src/ext/icu/icu.c | 48 +++++++++++++++++++++--------------- | |
18 third_party/sqlite/src/test/icu.test | 9 +++++++ | |
19 2 files changed, 37 insertions(+), 20 deletions(-) | |
20 | |
21 diff --git a/third_party/sqlite/src/ext/icu/icu.c b/third_party/sqlite/src/ext/i
cu/icu.c | |
22 index 5654366..263cd98 100644 | |
23 --- a/third_party/sqlite/src/ext/icu/icu.c | |
24 +++ b/third_party/sqlite/src/ext/icu/icu.c | |
25 @@ -355,11 +355,11 @@ static void icuRegexpFunc(sqlite3_context *p, int nArg, sq
lite3_value **apArg){ | |
26 */ | |
27 static void icuCaseFunc16(sqlite3_context *p, int nArg, sqlite3_value **apArg){ | |
28 const UChar *zInput; | |
29 - UChar *zOutput; | |
30 + UChar *zOutput = 0; | |
31 int nInput; | |
32 - int nOutput; | |
33 - | |
34 - UErrorCode status = U_ZERO_ERROR; | |
35 + int nOut; | |
36 + int cnt; | |
37 + UErrorCode status; | |
38 const char *zLocale = 0; | |
39 | |
40 assert(nArg==1 || nArg==2); | |
41 @@ -371,26 +371,34 @@ static void icuCaseFunc16(sqlite3_context *p, int nArg, sq
lite3_value **apArg){ | |
42 if( !zInput ){ | |
43 return; | |
44 } | |
45 - nInput = sqlite3_value_bytes16(apArg[0]); | |
46 - | |
47 - nOutput = nInput * 2 + 2; | |
48 - zOutput = sqlite3_malloc(nOutput); | |
49 - if( !zOutput ){ | |
50 + nOut = nInput = sqlite3_value_bytes16(apArg[0]); | |
51 + if( nOut==0 ){ | |
52 + sqlite3_result_text16(p, "", 0, SQLITE_STATIC); | |
53 return; | |
54 } | |
55 | |
56 - if( sqlite3_user_data(p) ){ | |
57 - u_strToUpper(zOutput, nOutput/2, zInput, nInput/2, zLocale, &status); | |
58 - }else{ | |
59 - u_strToLower(zOutput, nOutput/2, zInput, nInput/2, zLocale, &status); | |
60 - } | |
61 - | |
62 - if( !U_SUCCESS(status) ){ | |
63 - icuFunctionError(p, "u_strToLower()/u_strToUpper", status); | |
64 - return; | |
65 + for(cnt=0; cnt<2; cnt++){ | |
66 + UChar *zNew = sqlite3_realloc(zOutput, nOut); | |
67 + if( zNew==0 ){ | |
68 + sqlite3_free(zOutput); | |
69 + sqlite3_result_error_nomem(p); | |
70 + return; | |
71 + } | |
72 + zOutput = zNew; | |
73 + status = U_ZERO_ERROR; | |
74 + if( sqlite3_user_data(p) ){ | |
75 + nOut = 2*u_strToUpper(zOutput,nOut/2,zInput,nInput/2,zLocale,&status); | |
76 + }else{ | |
77 + nOut = 2*u_strToLower(zOutput,nOut/2,zInput,nInput/2,zLocale,&status); | |
78 + } | |
79 + if( !U_SUCCESS(status) ){ | |
80 + if( status==U_BUFFER_OVERFLOW_ERROR ) continue; | |
81 + icuFunctionError(p, | |
82 + sqlite3_user_data(p) ? "u_strToUpper()" : "u_strToLower", status); | |
83 + return; | |
84 + } | |
85 } | |
86 - | |
87 - sqlite3_result_text16(p, zOutput, -1, xFree); | |
88 + sqlite3_result_text16(p, zOutput, nOut, xFree); | |
89 } | |
90 | |
91 /* | |
92 diff --git a/third_party/sqlite/src/test/icu.test b/third_party/sqlite/src/test/
icu.test | |
93 index 73cb9b9..743bcfa 100644 | |
94 --- a/third_party/sqlite/src/test/icu.test | |
95 +++ b/third_party/sqlite/src/test/icu.test | |
96 @@ -72,6 +72,10 @@ test_expr icu-2.6 {i1=$::OGRAVE} {upper(i1)} $::OGRAVE | |
97 test_expr icu-2.7 {i1=$::szlig} {upper(i1)} "SS" | |
98 test_expr icu-2.8 {i1='SS'} {lower(i1)} "ss" | |
99 | |
100 +do_execsql_test icu-2.9 { | |
101 + SELECT upper(char(0xfb04,0xfb04,0xfb04,0xfb04)); | |
102 +} {FFLFFLFFLFFL} | |
103 + | |
104 # In turkish (locale="tr_TR"), the lower case version of I | |
105 # is "small dotless i" (code point 0x131 (decimal 305)). | |
106 # | |
107 @@ -133,4 +137,9 @@ do_catchsql_test icu-5.4 { | |
108 do_catchsql_test icu-5.4 { SELECT 'abc' REGEXP } {1 {near " ": syntax error}
} | |
109 do_catchsql_test icu-5.5 { SELECT 'abc' REGEXP, 1 } {1 {near ",": syntax error}
} | |
110 | |
111 + | |
112 +do_malloc_test icu-6.10 -sqlbody { | |
113 + SELECT upper(char(0xfb04,0xdf,0xfb04,0xe8,0xfb04)); | |
114 +} | |
115 + | |
116 finish_test | |
117 -- | |
118 2.7.0 | |
119 | |
OLD | NEW |