aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/func.c16
-rw-r--r--src/sqlite.h.in17
2 files changed, 22 insertions, 11 deletions
diff --git a/src/func.c b/src/func.c
index 16de6bbbd..3a1879ca6 100644
--- a/src/func.c
+++ b/src/func.c
@@ -332,16 +332,15 @@ static void upperFunc(sqlite3_context *context, int argc, sqlite3_value **argv){
if( z2 ){
z1 = contextMalloc(context, ((i64)n)+1);
if( z1 ){
- memcpy(z1, z2, n+1);
- for(i=0; z1[i]; i++){
- z1[i] = (char)sqlite3Toupper(z1[i]);
+ for(i=0; i<n; i++){
+ z1[i] = (char)sqlite3Toupper(z2[i]);
}
- sqlite3_result_text(context, z1, -1, sqlite3_free);
+ sqlite3_result_text(context, z1, n, sqlite3_free);
}
}
}
static void lowerFunc(sqlite3_context *context, int argc, sqlite3_value **argv){
- u8 *z1;
+ char *z1;
const char *z2;
int i, n;
UNUSED_PARAMETER(argc);
@@ -352,11 +351,10 @@ static void lowerFunc(sqlite3_context *context, int argc, sqlite3_value **argv){
if( z2 ){
z1 = contextMalloc(context, ((i64)n)+1);
if( z1 ){
- memcpy(z1, z2, n+1);
- for(i=0; z1[i]; i++){
- z1[i] = sqlite3Tolower(z1[i]);
+ for(i=0; i<n; i++){
+ z1[i] = sqlite3Tolower(z2[i]);
}
- sqlite3_result_text(context, (char *)z1, -1, sqlite3_free);
+ sqlite3_result_text(context, z1, n, sqlite3_free);
}
}
}
diff --git a/src/sqlite.h.in b/src/sqlite.h.in
index 3d210c31d..833d9c5ce 100644
--- a/src/sqlite.h.in
+++ b/src/sqlite.h.in
@@ -2799,7 +2799,8 @@ int sqlite3_limit(sqlite3*, int id, int newVal);
** that the supplied string is nul-terminated, then there is a small
** performance advantage to be gained by passing an nByte parameter that
** is equal to the number of bytes in the input string <i>including</i>
-** the nul-terminator bytes.
+** the nul-terminator bytes as this saves SQLite from having to
+** make a copy of the input string.
**
** ^If pzTail is not NULL then *pzTail is made to point to the first byte
** past the end of the first SQL statement in zSql. These routines only
@@ -3020,6 +3021,13 @@ typedef struct sqlite3_context sqlite3_context;
** number of <u>bytes</u> in the value, not the number of characters.)^
** ^If the fourth parameter is negative, the length of the string is
** the number of bytes up to the first zero terminator.
+** If a non-negative fourth parameter is provided to sqlite3_bind_text()
+** or sqlite3_bind_text16() then that parameter must be the byte offset
+** where the NUL terminator would occur assuming the string were NUL
+** terminated. If any NUL characters occur at byte offsets less than
+** the value of the fourth parameter then the resulting string value will
+** contain embedded NULs. The result of expressions involving strings
+** with embedded NULs is undefined.
**
** ^The fifth argument to sqlite3_bind_blob(), sqlite3_bind_text(), and
** sqlite3_bind_text16() is a destructor used to dispose of the BLOB or
@@ -4038,7 +4046,12 @@ typedef void (*sqlite3_destructor_type)(void*);
** ^If the 3rd parameter to the sqlite3_result_text* interfaces
** is non-negative, then as many bytes (not characters) of the text
** pointed to by the 2nd parameter are taken as the application-defined
-** function result.
+** function result. If the 3rd parameter is non-negative, then it
+** must be the byte offset into the string where the NUL terminator would
+** appear if the string where NUL terminated. If any NUL characters occur
+** in the string at a byte offset that is less than the value of the 3rd
+** parameter, then the resulting string will contain embedded NULs and the
+** result of expressions operating on strings with embedded NULs is undefined.
** ^If the 4th parameter to the sqlite3_result_text* interfaces
** or sqlite3_result_blob is a non-NULL pointer, then SQLite calls that
** function as the destructor on the text or BLOB result when it has