From 6c9f8e67de8a87a792499b1af81772f084ea2e1e Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 27 Aug 2014 03:28:50 +0000 Subject: [PATCH] Factor out the exception paths from sqlite3ValueToText() into a separate function so that the main routine is much faster for the common case of no required type or encoding conversions. FossilOrigin-Name: 1624916c6e9bc5dbcfa146b316a99ac8fecb13a9 --- manifest | 12 +++++----- manifest.uuid | 2 +- src/vdbemem.c | 61 ++++++++++++++++++++++++++++++++------------------- 3 files changed, 46 insertions(+), 29 deletions(-) diff --git a/manifest b/manifest index 5a5dcce860..9a75dd0703 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Performance\senhancement\sin\ssqlite3VdbeMemNulTerminate(). -D 2014-08-27T00:50:11.231 +C Factor\sout\sthe\sexception\spaths\sfrom\ssqlite3ValueToText()\sinto\sa\sseparate\nfunction\sso\sthat\sthe\smain\sroutine\sis\smuch\sfaster\sfor\sthe\scommon\scase\sof\nno\srequired\stype\sor\sencoding\sconversions. +D 2014-08-27T03:28:50.316 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5eb79e334a5de69c87740edd56af6527dd219308 F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -290,7 +290,7 @@ F src/vdbeInt.h df58400454823954cfb241e5858f07f37fc1fd78 F src/vdbeapi.c cda974083d7597f807640d344ffcf76d872201ce F src/vdbeaux.c dba006f67c9fd1b1d07ee7fb0fb38aa1905161d1 F src/vdbeblob.c 848238dc73e93e48432991bb5651bf87d865eca4 -F src/vdbemem.c 39cde2d8ddaa391055885caba9cb137ec2750474 +F src/vdbemem.c 9fc61d0860fd23399715fc436b2645154df08ce8 F src/vdbesort.c f7f5563bf7d4695ca8f3203f3bf9de96d04ed0b3 F src/vdbetrace.c 6f52bc0c51e144b7efdcfb2a8f771167a8816767 F src/vtab.c 019dbfd0406a7447c990e1f7bd1dfcdb8895697f @@ -1188,7 +1188,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P f1f94a971e031e784f8c30a6faf829df58709329 -R a4b7581e490aa7d71b634e963210e5ae +P f94cacc393e895522b92c9717c53357afc918d60 +R 0d26b1eecc3f76fc31005918debb0d62 U drh -Z d9bb31c0fee81f84beaf0ed2a801edba +Z 03245edbdb5b11cf6bf42be492d2d8e5 diff --git a/manifest.uuid b/manifest.uuid index 44b2a27745..40c815eed9 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -f94cacc393e895522b92c9717c53357afc918d60 \ No newline at end of file +1624916c6e9bc5dbcfa146b316a99ac8fecb13a9 \ No newline at end of file diff --git a/src/vdbemem.c b/src/vdbemem.c index 8457aa0da6..a76bd48865 100644 --- a/src/vdbemem.c +++ b/src/vdbemem.c @@ -919,31 +919,25 @@ int sqlite3VdbeMemFromBtree( return rc; } -/* This function is only available internally, it is not part of the -** external API. It works in a similar way to sqlite3_value_text(), -** except the data returned is in the encoding specified by the second -** parameter, which must be one of SQLITE_UTF16BE, SQLITE_UTF16LE or -** SQLITE_UTF8. -** -** (2006-02-16:) The enc value can be or-ed with SQLITE_UTF16_ALIGNED. -** If that is the case, then the result must be aligned on an even byte -** boundary. +/* +** The pVal argument is known to be a value other than NULL. +** Convert it into a string with encoding enc and return a pointer +** to a zero-terminated version of that string. */ -const void *sqlite3ValueText(sqlite3_value* pVal, u8 enc){ - if( !pVal ) return 0; - +SQLITE_NOINLINE const void *valueToText(sqlite3_value* pVal, u8 enc){ + assert( pVal!=0 ); assert( pVal->db==0 || sqlite3_mutex_held(pVal->db->mutex) ); assert( (enc&3)==(enc&~SQLITE_UTF16_ALIGNED) ); assert( (pVal->flags & MEM_RowSet)==0 ); - - if( pVal->flags&MEM_Null ){ - return 0; - } - assert( (MEM_Blob>>3) == MEM_Str ); - pVal->flags |= (pVal->flags & MEM_Blob)>>3; - ExpandBlob(pVal); - if( pVal->flags&MEM_Str ){ - sqlite3VdbeChangeEncoding(pVal, enc & ~SQLITE_UTF16_ALIGNED); + assert( (pVal->flags & (MEM_Null))==0 ); + if( pVal->flags & (MEM_Blob|MEM_Str) ){ + pVal->flags |= MEM_Str; + if( pVal->flags & MEM_Zero ){ + sqlite3VdbeMemExpandBlob(pVal); + } + if( pVal->enc != (enc & ~SQLITE_UTF16_ALIGNED) ){ + sqlite3VdbeChangeEncoding(pVal, enc & ~SQLITE_UTF16_ALIGNED); + } if( (enc & SQLITE_UTF16_ALIGNED)!=0 && 1==(1&SQLITE_PTR_TO_INT(pVal->z)) ){ assert( (pVal->flags & (MEM_Ephem|MEM_Static))!=0 ); if( sqlite3VdbeMemMakeWriteable(pVal)!=SQLITE_OK ){ @@ -952,7 +946,6 @@ const void *sqlite3ValueText(sqlite3_value* pVal, u8 enc){ } sqlite3VdbeMemNulTerminate(pVal); /* IMP: R-31275-44060 */ }else{ - assert( (pVal->flags&MEM_Blob)==0 ); sqlite3VdbeMemStringify(pVal, enc, 0); assert( 0==(1&SQLITE_PTR_TO_INT(pVal->z)) ); } @@ -965,6 +958,30 @@ const void *sqlite3ValueText(sqlite3_value* pVal, u8 enc){ } } +/* This function is only available internally, it is not part of the +** external API. It works in a similar way to sqlite3_value_text(), +** except the data returned is in the encoding specified by the second +** parameter, which must be one of SQLITE_UTF16BE, SQLITE_UTF16LE or +** SQLITE_UTF8. +** +** (2006-02-16:) The enc value can be or-ed with SQLITE_UTF16_ALIGNED. +** If that is the case, then the result must be aligned on an even byte +** boundary. +*/ +const void *sqlite3ValueText(sqlite3_value* pVal, u8 enc){ + if( !pVal ) return 0; + assert( pVal->db==0 || sqlite3_mutex_held(pVal->db->mutex) ); + assert( (enc&3)==(enc&~SQLITE_UTF16_ALIGNED) ); + assert( (pVal->flags & MEM_RowSet)==0 ); + if( (pVal->flags&(MEM_Str|MEM_Term))==(MEM_Str|MEM_Term) && pVal->enc==enc ){ + return pVal->z; + } + if( pVal->flags&MEM_Null ){ + return 0; + } + return valueToText(pVal, enc); +} + /* ** Create a new sqlite3_value object. */ -- 2.47.2