| | @@ -16,11 +16,11 @@ |
| 16 | 16 | ** if you want a wrapper to interface SQLite with your choice of programming |
| 17 | 17 | ** language. The code for the "sqlite3" command-line shell is also in a |
| 18 | 18 | ** separate file. This file contains only code for the core SQLite library. |
| 19 | 19 | ** |
| 20 | 20 | ** The content in this amalgamation comes from Fossil check-in |
| 21 | | -** 9adab8b2bef4130abd358d53384cb5f4dd69 with changes in files: |
| 21 | +** 4733d351ec2376291f093ba8d2ba71d82c6f with changes in files: |
| 22 | 22 | ** |
| 23 | 23 | ** |
| 24 | 24 | */ |
| 25 | 25 | #ifndef SQLITE_AMALGAMATION |
| 26 | 26 | #define SQLITE_CORE 1 |
| | @@ -467,14 +467,14 @@ |
| 467 | 467 | ** [sqlite3_libversion_number()], [sqlite3_sourceid()], |
| 468 | 468 | ** [sqlite_version()] and [sqlite_source_id()]. |
| 469 | 469 | */ |
| 470 | 470 | #define SQLITE_VERSION "3.52.0" |
| 471 | 471 | #define SQLITE_VERSION_NUMBER 3052000 |
| 472 | | -#define SQLITE_SOURCE_ID "2026-01-09 00:41:35 9adab8b2bef4130abd358d53384cb5f4dd691b808336bb7102793b0165b1c516" |
| 472 | +#define SQLITE_SOURCE_ID "2026-01-26 10:53:24 4733d351ec2376291f093ba8d2ba71d82c6f100c68dc860eee0532986c154e71" |
| 473 | 473 | #define SQLITE_SCM_BRANCH "trunk" |
| 474 | 474 | #define SQLITE_SCM_TAGS "" |
| 475 | | -#define SQLITE_SCM_DATETIME "2026-01-09T00:41:35.433Z" |
| 475 | +#define SQLITE_SCM_DATETIME "2026-01-26T10:53:24.426Z" |
| 476 | 476 | |
| 477 | 477 | /* |
| 478 | 478 | ** CAPI3REF: Run-Time Library Version Numbers |
| 479 | 479 | ** KEYWORDS: sqlite3_version sqlite3_sourceid |
| 480 | 480 | ** |
| | @@ -5194,12 +5194,12 @@ |
| 5194 | 5194 | ** it should be a pointer to well-formed UTF8 text. |
| 5195 | 5195 | ** ^If the third parameter to sqlite3_bind_text16() is not NULL, then |
| 5196 | 5196 | ** it should be a pointer to well-formed UTF16 text. |
| 5197 | 5197 | ** ^If the third parameter to sqlite3_bind_text64() is not NULL, then |
| 5198 | 5198 | ** it should be a pointer to a well-formed unicode string that is |
| 5199 | | -** either UTF8 if the sixth parameter is SQLITE_UTF8, or UTF16 |
| 5200 | | -** otherwise. |
| 5199 | +** either UTF8 if the sixth parameter is SQLITE_UTF8 or SQLITE_UTF8_ZT, |
| 5200 | +** or UTF16 otherwise. |
| 5201 | 5201 | ** |
| 5202 | 5202 | ** [[byte-order determination rules]] ^The byte-order of |
| 5203 | 5203 | ** UTF16 input text is determined by the byte-order mark (BOM, U+FEFF) |
| 5204 | 5204 | ** found in the first character, which is removed, or in the absence of a BOM |
| 5205 | 5205 | ** the byte order is the native byte order of the host |
| | @@ -5241,14 +5241,19 @@ |
| 5241 | 5241 | ** ^ (3) The constant, [SQLITE_TRANSIENT], may be passed to indicate that the |
| 5242 | 5242 | ** object is to be copied prior to the return from sqlite3_bind_*(). ^The |
| 5243 | 5243 | ** object and pointer to it must remain valid until then. ^SQLite will then |
| 5244 | 5244 | ** manage the lifetime of its private copy. |
| 5245 | 5245 | ** |
| 5246 | | -** ^The sixth argument to sqlite3_bind_text64() must be one of |
| 5247 | | -** [SQLITE_UTF8], [SQLITE_UTF16], [SQLITE_UTF16BE], or [SQLITE_UTF16LE] |
| 5248 | | -** to specify the encoding of the text in the third parameter. If |
| 5249 | | -** the sixth argument to sqlite3_bind_text64() is not one of the |
| 5246 | +** ^The sixth argument (the E argument) |
| 5247 | +** to sqlite3_bind_text64(S,K,Z,N,D,E) must be one of |
| 5248 | +** [SQLITE_UTF8], [SQLITE_UTF8_ZT], [SQLITE_UTF16], [SQLITE_UTF16BE], |
| 5249 | +** or [SQLITE_UTF16LE] to specify the encoding of the text in the |
| 5250 | +** third parameter, Z. The special value [SQLITE_UTF8_ZT] means that the |
| 5251 | +** string argument is both UTF-8 encoded and is zero-terminated. In other |
| 5252 | +** words, SQLITE_UTF8_ZT means that the Z array is allocated to hold at |
| 5253 | +** least N+1 bytes and that the Z[N] byte is zero. If |
| 5254 | +** the E argument to sqlite3_bind_text64(S,K,Z,N,D,E) is not one of the |
| 5250 | 5255 | ** allowed values shown above, or if the text encoding is different |
| 5251 | 5256 | ** from the encoding specified by the sixth parameter, then the behavior |
| 5252 | 5257 | ** is undefined. |
| 5253 | 5258 | ** |
| 5254 | 5259 | ** ^The sqlite3_bind_zeroblob() routine binds a BLOB of length N that |
| | @@ -6111,17 +6116,63 @@ |
| 6111 | 6116 | /* |
| 6112 | 6117 | ** CAPI3REF: Text Encodings |
| 6113 | 6118 | ** |
| 6114 | 6119 | ** These constants define integer codes that represent the various |
| 6115 | 6120 | ** text encodings supported by SQLite. |
| 6121 | +** |
| 6122 | +** <dl> |
| 6123 | +** [[SQLITE_UTF8]] <dt>SQLITE_UTF8</dt><dd>Text is encoding as UTF-8</dd> |
| 6124 | +** |
| 6125 | +** [[SQLITE_UTF16LE]] <dt>SQLITE_UTF16LE</dt><dd>Text is encoding as UTF-16 |
| 6126 | +** with each code point being expressed "little endian" - the least significant |
| 6127 | +** byte first. This is the usual encoding, for example on Windows.</dd> |
| 6128 | +** |
| 6129 | +** [[SQLITE_UTF16BE]] <dt>SQLITE_UTF16BE</dt><dd>Text is encoding as UTF-16 |
| 6130 | +** with each code point being expressed "big endian" - the most significant |
| 6131 | +** byte first. This encoding is less common, but is still sometimes seen, |
| 6132 | +** specially on older systems. |
| 6133 | +** |
| 6134 | +** [[SQLITE_UTF16]] <dt>SQLITE_UTF16</dt><dd>Text is encoding as UTF-16 |
| 6135 | +** with each code point being expressed either little endian or as big |
| 6136 | +** endian, according to the native endianness of the host computer. |
| 6137 | +** |
| 6138 | +** [[SQLITE_ANY]] <dt>SQLITE_ANY</dt><dd>This encoding value may only be used |
| 6139 | +** to declare the preferred text for [application-defined SQL functions] |
| 6140 | +** created using [sqlite3_create_function()] and similar. If the preferred |
| 6141 | +** encoding (the 4th parameter to sqlite3_create_function() - the eTextRep |
| 6142 | +** parameter) is SQLITE_ANY, that indicates that the function does not have |
| 6143 | +** a preference regarding the text encoding of its parameters and can take |
| 6144 | +** any text encoding that the SQLite core find convenient to supply. This |
| 6145 | +** option is deprecated. Please do not use it in new applications. |
| 6146 | +** |
| 6147 | +** [[SQLITE_UTF16_ALIGNED]] <dt>SQLITE_UTF16_ALIGNED</dt><dd>This encoding |
| 6148 | +** value may be used as the 3rd parameter (the eTextRep parameter) to |
| 6149 | +** [sqlite3_create_collation()] and similar. This encoding value means |
| 6150 | +** that the application-defined collating sequence created expects its |
| 6151 | +** input strings to be in UTF16 in native byte order, and that the start |
| 6152 | +** of the strings must be aligned to a 2-byte boundary. |
| 6153 | +** |
| 6154 | +** [[SQLITE_UTF8_ZT]] <dt>SQLITE_UTF8_ZT</dt><dd>This option can only be |
| 6155 | +** used to specify the text encoding to strings input to [sqlite3_result_text64()] |
| 6156 | +** and [sqlite3_bind_text64()]. It means that the input string (call it "z") |
| 6157 | +** is UTF-8 encoded and that it is zero-terminated. If the length parameter |
| 6158 | +** (call it "n") is non-negative, this encoding option means that the caller |
| 6159 | +** guarantees that z array contains at least n+1 bytes and that the z[n] |
| 6160 | +** byte has a value of zero. |
| 6161 | +** This option gives the same output as SQLITE_UTF8, but can be more efficient |
| 6162 | +** by avoiding the need to make a copy of the input string, in some cases. |
| 6163 | +** However, if z is allocated to hold fewer than n+1 bytes or if the |
| 6164 | +** z[n] byte is not zero, undefined behavior may result. |
| 6165 | +** </dl> |
| 6116 | 6166 | */ |
| 6117 | 6167 | #define SQLITE_UTF8 1 /* IMP: R-37514-35566 */ |
| 6118 | 6168 | #define SQLITE_UTF16LE 2 /* IMP: R-03371-37637 */ |
| 6119 | 6169 | #define SQLITE_UTF16BE 3 /* IMP: R-51971-34154 */ |
| 6120 | 6170 | #define SQLITE_UTF16 4 /* Use native byte order */ |
| 6121 | 6171 | #define SQLITE_ANY 5 /* Deprecated */ |
| 6122 | 6172 | #define SQLITE_UTF16_ALIGNED 8 /* sqlite3_create_collation only */ |
| 6173 | +#define SQLITE_UTF8_ZT 16 /* Zero-terminated UTF8 */ |
| 6123 | 6174 | |
| 6124 | 6175 | /* |
| 6125 | 6176 | ** CAPI3REF: Function Flags |
| 6126 | 6177 | ** |
| 6127 | 6178 | ** These constants may be ORed together with the |
| | @@ -6738,14 +6789,18 @@ |
| 6738 | 6789 | ** ^The sqlite3_result_text(), sqlite3_result_text16(), |
| 6739 | 6790 | ** sqlite3_result_text16le(), and sqlite3_result_text16be() interfaces |
| 6740 | 6791 | ** set the return value of the application-defined function to be |
| 6741 | 6792 | ** a text string which is represented as UTF-8, UTF-16 native byte order, |
| 6742 | 6793 | ** UTF-16 little endian, or UTF-16 big endian, respectively. |
| 6743 | | -** ^The sqlite3_result_text64() interface sets the return value of an |
| 6794 | +** ^The sqlite3_result_text64(C,Z,N,D,E) interface sets the return value of an |
| 6744 | 6795 | ** application-defined function to be a text string in an encoding |
| 6745 | | -** specified by the fifth (and last) parameter, which must be one |
| 6746 | | -** of [SQLITE_UTF8], [SQLITE_UTF16], [SQLITE_UTF16BE], or [SQLITE_UTF16LE]. |
| 6796 | +** specified the E parameter, which must be one |
| 6797 | +** of [SQLITE_UTF8], [SQLITE_UTF8_ZT], [SQLITE_UTF16], [SQLITE_UTF16BE], |
| 6798 | +** or [SQLITE_UTF16LE]. ^The special value [SQLITE_UTF8_ZT] means that |
| 6799 | +** the result text is both UTF-8 and zero-terminated. In other words, |
| 6800 | +** SQLITE_UTF8_ZT means that the Z array holds at least N+1 byes and that |
| 6801 | +** the Z[N] is zero. |
| 6747 | 6802 | ** ^SQLite takes the text result from the application from |
| 6748 | 6803 | ** the 2nd parameter of the sqlite3_result_text* interfaces. |
| 6749 | 6804 | ** ^If the 3rd parameter to any of the sqlite3_result_text* interfaces |
| 6750 | 6805 | ** other than sqlite3_result_text64() is negative, then SQLite computes |
| 6751 | 6806 | ** the string length itself by searching the 2nd parameter for the first |
| | @@ -6828,11 +6883,11 @@ |
| 6828 | 6883 | SQLITE_API void sqlite3_result_error_code(sqlite3_context*, int); |
| 6829 | 6884 | SQLITE_API void sqlite3_result_int(sqlite3_context*, int); |
| 6830 | 6885 | SQLITE_API void sqlite3_result_int64(sqlite3_context*, sqlite3_int64); |
| 6831 | 6886 | SQLITE_API void sqlite3_result_null(sqlite3_context*); |
| 6832 | 6887 | SQLITE_API void sqlite3_result_text(sqlite3_context*, const char*, int, void(*)(void*)); |
| 6833 | | -SQLITE_API void sqlite3_result_text64(sqlite3_context*, const char*,sqlite3_uint64, |
| 6888 | +SQLITE_API void sqlite3_result_text64(sqlite3_context*, const char *z, sqlite3_uint64 n, |
| 6834 | 6889 | void(*)(void*), unsigned char encoding); |
| 6835 | 6890 | SQLITE_API void sqlite3_result_text16(sqlite3_context*, const void*, int, void(*)(void*)); |
| 6836 | 6891 | SQLITE_API void sqlite3_result_text16le(sqlite3_context*, const void*, int,void(*)(void*)); |
| 6837 | 6892 | SQLITE_API void sqlite3_result_text16be(sqlite3_context*, const void*, int,void(*)(void*)); |
| 6838 | 6893 | SQLITE_API void sqlite3_result_value(sqlite3_context*, sqlite3_value*); |
| | @@ -14373,10 +14428,31 @@ |
| 14373 | 14428 | #ifndef SQLITE_MAX_LENGTH |
| 14374 | 14429 | # define SQLITE_MAX_LENGTH 1000000000 |
| 14375 | 14430 | #endif |
| 14376 | 14431 | #define SQLITE_MIN_LENGTH 30 /* Minimum value for the length limit */ |
| 14377 | 14432 | |
| 14433 | +/* |
| 14434 | +** Maximum size of any single memory allocation. |
| 14435 | +** |
| 14436 | +** This is not a limit on the total amount of memory used. This is |
| 14437 | +** a limit on the size parameter to sqlite3_malloc() and sqlite3_realloc(). |
| 14438 | +** |
| 14439 | +** The upper bound is slightly less than 2GiB: 0x7ffffeff == 2,147,483,391 |
| 14440 | +** This provides a 256-byte safety margin for defense against 32-bit |
| 14441 | +** signed integer overflow bugs when computing memory allocation sizes. |
| 14442 | +** Paranoid applications might want to reduce the maximum allocation size |
| 14443 | +** further for an even larger safety margin. 0x3fffffff or 0x0fffffff |
| 14444 | +** or even smaller would be reasonable upper bounds on the size of a memory |
| 14445 | +** allocations for most applications. |
| 14446 | +*/ |
| 14447 | +#ifndef SQLITE_MAX_ALLOCATION_SIZE |
| 14448 | +# define SQLITE_MAX_ALLOCATION_SIZE 2147483391 |
| 14449 | +#endif |
| 14450 | +#if SQLITE_MAX_ALLOCATION_SIZE>2147483391 |
| 14451 | +# error Maximum size for SQLITE_MAX_ALLOCATION_SIZE is 2147483391 |
| 14452 | +#endif |
| 14453 | + |
| 14378 | 14454 | /* |
| 14379 | 14455 | ** This is the maximum number of |
| 14380 | 14456 | ** |
| 14381 | 14457 | ** * Columns in a table |
| 14382 | 14458 | ** * Columns in an index |
| | @@ -20223,31 +20299,17 @@ |
| 20223 | 20299 | }; |
| 20224 | 20300 | |
| 20225 | 20301 | /* |
| 20226 | 20302 | ** An instance of the following structure contains all information |
| 20227 | 20303 | ** needed to generate code for a single SELECT statement. |
| 20228 | | -** |
| 20229 | | -** See the header comment on the computeLimitRegisters() routine for a |
| 20230 | | -** detailed description of the meaning of the iLimit and iOffset fields. |
| 20231 | | -** |
| 20232 | | -** addrOpenEphm[] entries contain the address of OP_OpenEphemeral opcodes. |
| 20233 | | -** These addresses must be stored so that we can go back and fill in |
| 20234 | | -** the P4_KEYINFO and P2 parameters later. Neither the KeyInfo nor |
| 20235 | | -** the number of columns in P2 can be computed at the same time |
| 20236 | | -** as the OP_OpenEphm instruction is coded because not |
| 20237 | | -** enough information about the compound query is known at that point. |
| 20238 | | -** The KeyInfo for addrOpenTran[0] and [1] contains collating sequences |
| 20239 | | -** for the result set. The KeyInfo for addrOpenEphm[2] contains collating |
| 20240 | | -** sequences for the ORDER BY clause. |
| 20241 | 20304 | */ |
| 20242 | 20305 | struct Select { |
| 20243 | 20306 | u8 op; /* One of: TK_UNION TK_ALL TK_INTERSECT TK_EXCEPT */ |
| 20244 | 20307 | LogEst nSelectRow; /* Estimated number of result rows */ |
| 20245 | 20308 | u32 selFlags; /* Various SF_* values */ |
| 20246 | 20309 | int iLimit, iOffset; /* Memory registers holding LIMIT & OFFSET counters */ |
| 20247 | 20310 | u32 selId; /* Unique identifier number for this SELECT */ |
| 20248 | | - int addrOpenEphm[2]; /* OP_OpenEphem opcodes related to this select */ |
| 20249 | 20311 | ExprList *pEList; /* The fields of the result */ |
| 20250 | 20312 | SrcList *pSrc; /* The FROM clause */ |
| 20251 | 20313 | Expr *pWhere; /* The WHERE clause */ |
| 20252 | 20314 | ExprList *pGroupBy; /* The GROUP BY clause */ |
| 20253 | 20315 | Expr *pHaving; /* The HAVING clause */ |
| | @@ -20275,28 +20337,28 @@ |
| 20275 | 20337 | #define SF_Distinct 0x0000001 /* Output should be DISTINCT */ |
| 20276 | 20338 | #define SF_All 0x0000002 /* Includes the ALL keyword */ |
| 20277 | 20339 | #define SF_Resolved 0x0000004 /* Identifiers have been resolved */ |
| 20278 | 20340 | #define SF_Aggregate 0x0000008 /* Contains agg functions or a GROUP BY */ |
| 20279 | 20341 | #define SF_HasAgg 0x0000010 /* Contains aggregate functions */ |
| 20280 | | -#define SF_UsesEphemeral 0x0000020 /* Uses the OpenEphemeral opcode */ |
| 20342 | +/* 0x0000020 // available for reuse */ |
| 20281 | 20343 | #define SF_Expanded 0x0000040 /* sqlite3SelectExpand() called on this */ |
| 20282 | 20344 | #define SF_HasTypeInfo 0x0000080 /* FROM subqueries have Table metadata */ |
| 20283 | 20345 | #define SF_Compound 0x0000100 /* Part of a compound query */ |
| 20284 | 20346 | #define SF_Values 0x0000200 /* Synthesized from VALUES clause */ |
| 20285 | 20347 | #define SF_MultiValue 0x0000400 /* Single VALUES term with multiple rows */ |
| 20286 | 20348 | #define SF_NestedFrom 0x0000800 /* Part of a parenthesized FROM clause */ |
| 20287 | 20349 | #define SF_MinMaxAgg 0x0001000 /* Aggregate containing min() or max() */ |
| 20288 | 20350 | #define SF_Recursive 0x0002000 /* The recursive part of a recursive CTE */ |
| 20289 | 20351 | #define SF_FixedLimit 0x0004000 /* nSelectRow set by a constant LIMIT */ |
| 20290 | | -#define SF_MaybeConvert 0x0008000 /* Need convertCompoundSelectToSubquery() */ |
| 20352 | +/* 0x0008000 // available for reuse */ |
| 20291 | 20353 | #define SF_Converted 0x0010000 /* By convertCompoundSelectToSubquery() */ |
| 20292 | 20354 | #define SF_IncludeHidden 0x0020000 /* Include hidden columns in output */ |
| 20293 | 20355 | #define SF_ComplexResult 0x0040000 /* Result contains subquery or function */ |
| 20294 | 20356 | #define SF_WhereBegin 0x0080000 /* Really a WhereBegin() call. Debug Only */ |
| 20295 | 20357 | #define SF_WinRewrite 0x0100000 /* Window function rewrite accomplished */ |
| 20296 | 20358 | #define SF_View 0x0200000 /* SELECT statement is a view */ |
| 20297 | | -#define SF_NoopOrderBy 0x0400000 /* ORDER BY is ignored for this query */ |
| 20359 | +/* 0x0400000 // available for reuse */ |
| 20298 | 20360 | #define SF_UFSrcCheck 0x0800000 /* Check pSrc as required by UPDATE...FROM */ |
| 20299 | 20361 | #define SF_PushDown 0x1000000 /* Modified by WHERE-clause push-down opt */ |
| 20300 | 20362 | #define SF_MultiPart 0x2000000 /* Has multiple incompatible PARTITIONs */ |
| 20301 | 20363 | #define SF_CopyCte 0x4000000 /* SELECT statement is a copy of a CTE */ |
| 20302 | 20364 | #define SF_OrderByReqd 0x8000000 /* The ORDER BY clause may not be omitted */ |
| | @@ -20312,15 +20374,10 @@ |
| 20312 | 20374 | /* |
| 20313 | 20375 | ** The results of a SELECT can be distributed in several ways, as defined |
| 20314 | 20376 | ** by one of the following macros. The "SRT" prefix means "SELECT Result |
| 20315 | 20377 | ** Type". |
| 20316 | 20378 | ** |
| 20317 | | -** SRT_Union Store results as a key in a temporary index |
| 20318 | | -** identified by pDest->iSDParm. |
| 20319 | | -** |
| 20320 | | -** SRT_Except Remove results from the temporary index pDest->iSDParm. |
| 20321 | | -** |
| 20322 | 20379 | ** SRT_Exists Store a 1 in memory cell pDest->iSDParm if the result |
| 20323 | 20380 | ** set is not empty. |
| 20324 | 20381 | ** |
| 20325 | 20382 | ** SRT_Discard Throw the results away. This is used by SELECT |
| 20326 | 20383 | ** statements within triggers whose only purpose is |
| | @@ -20380,34 +20437,32 @@ |
| 20380 | 20437 | ** column returned by the SELECT is used as the integer |
| 20381 | 20438 | ** key. If (pDest->iSDParm>0), then the table is an index |
| 20382 | 20439 | ** table. (pDest->iSDParm) is the number of key columns in |
| 20383 | 20440 | ** each index record in this case. |
| 20384 | 20441 | */ |
| 20385 | | -#define SRT_Union 1 /* Store result as keys in an index */ |
| 20386 | | -#define SRT_Except 2 /* Remove result from a UNION index */ |
| 20387 | | -#define SRT_Exists 3 /* Store 1 if the result is not empty */ |
| 20388 | | -#define SRT_Discard 4 /* Do not save the results anywhere */ |
| 20389 | | -#define SRT_DistFifo 5 /* Like SRT_Fifo, but unique results only */ |
| 20390 | | -#define SRT_DistQueue 6 /* Like SRT_Queue, but unique results only */ |
| 20442 | +#define SRT_Exists 1 /* Store 1 if the result is not empty */ |
| 20443 | +#define SRT_Discard 2 /* Do not save the results anywhere */ |
| 20444 | +#define SRT_DistFifo 3 /* Like SRT_Fifo, but unique results only */ |
| 20445 | +#define SRT_DistQueue 4 /* Like SRT_Queue, but unique results only */ |
| 20391 | 20446 | |
| 20392 | 20447 | /* The DISTINCT clause is ignored for all of the above. Not that |
| 20393 | 20448 | ** IgnorableDistinct() implies IgnorableOrderby() */ |
| 20394 | 20449 | #define IgnorableDistinct(X) ((X->eDest)<=SRT_DistQueue) |
| 20395 | 20450 | |
| 20396 | | -#define SRT_Queue 7 /* Store result in an queue */ |
| 20397 | | -#define SRT_Fifo 8 /* Store result as data with an automatic rowid */ |
| 20451 | +#define SRT_Queue 5 /* Store result in an queue */ |
| 20452 | +#define SRT_Fifo 6 /* Store result as data with an automatic rowid */ |
| 20398 | 20453 | |
| 20399 | 20454 | /* The ORDER BY clause is ignored for all of the above */ |
| 20400 | 20455 | #define IgnorableOrderby(X) ((X->eDest)<=SRT_Fifo) |
| 20401 | 20456 | |
| 20402 | | -#define SRT_Output 9 /* Output each row of result */ |
| 20403 | | -#define SRT_Mem 10 /* Store result in a memory cell */ |
| 20404 | | -#define SRT_Set 11 /* Store results as keys in an index */ |
| 20405 | | -#define SRT_EphemTab 12 /* Create transient tab and store like SRT_Table */ |
| 20406 | | -#define SRT_Coroutine 13 /* Generate a single row of result */ |
| 20407 | | -#define SRT_Table 14 /* Store result as data with an automatic rowid */ |
| 20408 | | -#define SRT_Upfrom 15 /* Store result as data with rowid */ |
| 20457 | +#define SRT_Output 7 /* Output each row of result */ |
| 20458 | +#define SRT_Mem 8 /* Store result in a memory cell */ |
| 20459 | +#define SRT_Set 9 /* Store results as keys in an index */ |
| 20460 | +#define SRT_EphemTab 10 /* Create transient tab and store like SRT_Table */ |
| 20461 | +#define SRT_Coroutine 11 /* Generate a single row of result */ |
| 20462 | +#define SRT_Table 12 /* Store result as data with an automatic rowid */ |
| 20463 | +#define SRT_Upfrom 13 /* Store result as data with rowid */ |
| 20409 | 20464 | |
| 20410 | 20465 | /* |
| 20411 | 20466 | ** An instance of this object describes where to put of the results of |
| 20412 | 20467 | ** a SELECT statement. |
| 20413 | 20468 | */ |
| | @@ -24510,10 +24565,11 @@ |
| 24510 | 24565 | SQLITE_PRIVATE int sqlite3VdbeMemCopy(Mem*, const Mem*); |
| 24511 | 24566 | SQLITE_PRIVATE void sqlite3VdbeMemShallowCopy(Mem*, const Mem*, int); |
| 24512 | 24567 | SQLITE_PRIVATE void sqlite3VdbeMemMove(Mem*, Mem*); |
| 24513 | 24568 | SQLITE_PRIVATE int sqlite3VdbeMemNulTerminate(Mem*); |
| 24514 | 24569 | SQLITE_PRIVATE int sqlite3VdbeMemSetStr(Mem*, const char*, i64, u8, void(*)(void*)); |
| 24570 | +SQLITE_PRIVATE int sqlite3VdbeMemSetText(Mem*, const char*, i64, void(*)(void*)); |
| 24515 | 24571 | SQLITE_PRIVATE void sqlite3VdbeMemSetInt64(Mem*, i64); |
| 24516 | 24572 | #ifdef SQLITE_OMIT_FLOATING_POINT |
| 24517 | 24573 | # define sqlite3VdbeMemSetDouble sqlite3VdbeMemSetInt64 |
| 24518 | 24574 | #else |
| 24519 | 24575 | SQLITE_PRIVATE void sqlite3VdbeMemSetDouble(Mem*, double); |
| | @@ -31356,31 +31412,10 @@ |
| 31356 | 31412 | sqlite3StatusUp(SQLITE_STATUS_MALLOC_COUNT, 1); |
| 31357 | 31413 | } |
| 31358 | 31414 | *pp = p; |
| 31359 | 31415 | } |
| 31360 | 31416 | |
| 31361 | | -/* |
| 31362 | | -** Maximum size of any single memory allocation. |
| 31363 | | -** |
| 31364 | | -** This is not a limit on the total amount of memory used. This is |
| 31365 | | -** a limit on the size parameter to sqlite3_malloc() and sqlite3_realloc(). |
| 31366 | | -** |
| 31367 | | -** The upper bound is slightly less than 2GiB: 0x7ffffeff == 2,147,483,391 |
| 31368 | | -** This provides a 256-byte safety margin for defense against 32-bit |
| 31369 | | -** signed integer overflow bugs when computing memory allocation sizes. |
| 31370 | | -** Paranoid applications might want to reduce the maximum allocation size |
| 31371 | | -** further for an even larger safety margin. 0x3fffffff or 0x0fffffff |
| 31372 | | -** or even smaller would be reasonable upper bounds on the size of a memory |
| 31373 | | -** allocations for most applications. |
| 31374 | | -*/ |
| 31375 | | -#ifndef SQLITE_MAX_ALLOCATION_SIZE |
| 31376 | | -# define SQLITE_MAX_ALLOCATION_SIZE 2147483391 |
| 31377 | | -#endif |
| 31378 | | -#if SQLITE_MAX_ALLOCATION_SIZE>2147483391 |
| 31379 | | -# error Maximum size for SQLITE_MAX_ALLOCATION_SIZE is 2147483391 |
| 31380 | | -#endif |
| 31381 | | - |
| 31382 | 31417 | /* |
| 31383 | 31418 | ** Allocate memory. This routine is like sqlite3_malloc() except that it |
| 31384 | 31419 | ** assumes the memory subsystem has already been initialized. |
| 31385 | 31420 | */ |
| 31386 | 31421 | SQLITE_PRIVATE void *sqlite3Malloc(u64 n){ |
| | @@ -31600,12 +31635,11 @@ |
| 31600 | 31635 | } |
| 31601 | 31636 | if( nBytes==0 ){ |
| 31602 | 31637 | sqlite3_free(pOld); /* IMP: R-26507-47431 */ |
| 31603 | 31638 | return 0; |
| 31604 | 31639 | } |
| 31605 | | - if( nBytes>=0x7fffff00 ){ |
| 31606 | | - /* The 0x7ffff00 limit term is explained in comments on sqlite3Malloc() */ |
| 31640 | + if( nBytes>SQLITE_MAX_ALLOCATION_SIZE ){ |
| 31607 | 31641 | return 0; |
| 31608 | 31642 | } |
| 31609 | 31643 | nOld = sqlite3MallocSize(pOld); |
| 31610 | 31644 | /* IMPLEMENTATION-OF: R-46199-30249 SQLite guarantees that the second |
| 31611 | 31645 | ** argument to xRealloc is always a value returned by a prior call to |
| | @@ -77429,11 +77463,11 @@ |
| 77429 | 77463 | } |
| 77430 | 77464 | assert( cursorHoldsMutex(pCur) ); |
| 77431 | 77465 | |
| 77432 | 77466 | getCellInfo(pCur); |
| 77433 | 77467 | aPayload = pCur->info.pPayload; |
| 77434 | | - assert( offset+amt <= pCur->info.nPayload ); |
| 77468 | + assert( (u64)offset+(u64)amt <= (u64)pCur->info.nPayload ); |
| 77435 | 77469 | |
| 77436 | 77470 | assert( aPayload > pPage->aData ); |
| 77437 | 77471 | if( (uptr)(aPayload - pPage->aData) > (pBt->usableSize - pCur->info.nLocal) ){ |
| 77438 | 77472 | /* Trying to read or write past the end of the data is an error. The |
| 77439 | 77473 | ** conditional above is really: |
| | @@ -77986,11 +78020,11 @@ |
| 77986 | 78020 | SQLITE_PRIVATE int sqlite3BtreeIsEmpty(BtCursor *pCur, int *pRes){ |
| 77987 | 78021 | int rc; |
| 77988 | 78022 | |
| 77989 | 78023 | assert( cursorOwnsBtShared(pCur) ); |
| 77990 | 78024 | assert( sqlite3_mutex_held(pCur->pBtree->db->mutex) ); |
| 77991 | | - if( pCur->eState==CURSOR_VALID ){ |
| 78025 | + if( NEVER(pCur->eState==CURSOR_VALID) ){ |
| 77992 | 78026 | *pRes = 0; |
| 77993 | 78027 | return SQLITE_OK; |
| 77994 | 78028 | } |
| 77995 | 78029 | rc = moveToRoot(pCur); |
| 77996 | 78030 | if( rc==SQLITE_EMPTY ){ |
| | @@ -85879,10 +85913,88 @@ |
| 85879 | 85913 | #endif |
| 85880 | 85914 | |
| 85881 | 85915 | |
| 85882 | 85916 | return SQLITE_OK; |
| 85883 | 85917 | } |
| 85918 | + |
| 85919 | +/* Like sqlite3VdbeMemSetStr() except: |
| 85920 | +** |
| 85921 | +** enc is always SQLITE_UTF8 |
| 85922 | +** pMem->db is always non-NULL |
| 85923 | +*/ |
| 85924 | +SQLITE_PRIVATE int sqlite3VdbeMemSetText( |
| 85925 | + Mem *pMem, /* Memory cell to set to string value */ |
| 85926 | + const char *z, /* String pointer */ |
| 85927 | + i64 n, /* Bytes in string, or negative */ |
| 85928 | + void (*xDel)(void*) /* Destructor function */ |
| 85929 | +){ |
| 85930 | + i64 nByte = n; /* New value for pMem->n */ |
| 85931 | + u16 flags; |
| 85932 | + |
| 85933 | + assert( pMem!=0 ); |
| 85934 | + assert( pMem->db!=0 ); |
| 85935 | + assert( sqlite3_mutex_held(pMem->db->mutex) ); |
| 85936 | + assert( !sqlite3VdbeMemIsRowSet(pMem) ); |
| 85937 | + |
| 85938 | + /* If z is a NULL pointer, set pMem to contain an SQL NULL. */ |
| 85939 | + if( !z ){ |
| 85940 | + sqlite3VdbeMemSetNull(pMem); |
| 85941 | + return SQLITE_OK; |
| 85942 | + } |
| 85943 | + |
| 85944 | + if( nByte<0 ){ |
| 85945 | + nByte = strlen(z); |
| 85946 | + flags = MEM_Str|MEM_Term; |
| 85947 | + }else{ |
| 85948 | + flags = MEM_Str; |
| 85949 | + } |
| 85950 | + if( nByte>(i64)pMem->db->aLimit[SQLITE_LIMIT_LENGTH] ){ |
| 85951 | + if( xDel && xDel!=SQLITE_TRANSIENT ){ |
| 85952 | + if( xDel==SQLITE_DYNAMIC ){ |
| 85953 | + sqlite3DbFree(pMem->db, (void*)z); |
| 85954 | + }else{ |
| 85955 | + xDel((void*)z); |
| 85956 | + } |
| 85957 | + } |
| 85958 | + sqlite3VdbeMemSetNull(pMem); |
| 85959 | + return sqlite3ErrorToParser(pMem->db, SQLITE_TOOBIG); |
| 85960 | + } |
| 85961 | + |
| 85962 | + /* The following block sets the new values of Mem.z and Mem.xDel. It |
| 85963 | + ** also sets a flag in local variable "flags" to indicate the memory |
| 85964 | + ** management (one of MEM_Dyn or MEM_Static). |
| 85965 | + */ |
| 85966 | + if( xDel==SQLITE_TRANSIENT ){ |
| 85967 | + i64 nAlloc = nByte + 1; |
| 85968 | + testcase( nAlloc==31 ); |
| 85969 | + testcase( nAlloc==32 ); |
| 85970 | + if( sqlite3VdbeMemClearAndResize(pMem, (int)MAX(nAlloc,32)) ){ |
| 85971 | + return SQLITE_NOMEM_BKPT; |
| 85972 | + } |
| 85973 | + assert( pMem->z!=0 ); |
| 85974 | + memcpy(pMem->z, z, nByte); |
| 85975 | + pMem->z[nByte] = 0; |
| 85976 | + }else{ |
| 85977 | + sqlite3VdbeMemRelease(pMem); |
| 85978 | + pMem->z = (char *)z; |
| 85979 | + if( xDel==SQLITE_DYNAMIC ){ |
| 85980 | + pMem->zMalloc = pMem->z; |
| 85981 | + pMem->szMalloc = sqlite3DbMallocSize(pMem->db, pMem->zMalloc); |
| 85982 | + pMem->xDel = 0; |
| 85983 | + }else if( xDel==SQLITE_STATIC ){ |
| 85984 | + pMem->xDel = xDel; |
| 85985 | + flags |= MEM_Static; |
| 85986 | + }else{ |
| 85987 | + pMem->xDel = xDel; |
| 85988 | + flags |= MEM_Dyn; |
| 85989 | + } |
| 85990 | + } |
| 85991 | + pMem->flags = flags; |
| 85992 | + pMem->n = (int)(nByte & 0x7fffffff); |
| 85993 | + pMem->enc = SQLITE_UTF8; |
| 85994 | + return SQLITE_OK; |
| 85995 | +} |
| 85884 | 85996 | |
| 85885 | 85997 | /* |
| 85886 | 85998 | ** Move data out of a btree key or data field and into a Mem structure. |
| 85887 | 85999 | ** The data is payload from the entry that pCur is currently pointing |
| 85888 | 86000 | ** to. offset and amt determine what portion of the data or key to retrieve. |
| | @@ -85903,11 +86015,16 @@ |
| 85903 | 86015 | u32 amt, /* Number of bytes to return. */ |
| 85904 | 86016 | Mem *pMem /* OUT: Return data in this Mem structure. */ |
| 85905 | 86017 | ){ |
| 85906 | 86018 | int rc; |
| 85907 | 86019 | pMem->flags = MEM_Null; |
| 85908 | | - if( sqlite3BtreeMaxRecordSize(pCur)<offset+amt ){ |
| 86020 | + testcase( amt==SQLITE_MAX_ALLOCATION_SIZE-1 ); |
| 86021 | + testcase( amt==SQLITE_MAX_ALLOCATION_SIZE ); |
| 86022 | + if( amt>=SQLITE_MAX_ALLOCATION_SIZE ){ |
| 86023 | + return SQLITE_NOMEM_BKPT; |
| 86024 | + } |
| 86025 | + if( (u64)amt + (u64)offset > (u64)sqlite3BtreeMaxRecordSize(pCur) ){ |
| 85909 | 86026 | return SQLITE_CORRUPT_BKPT; |
| 85910 | 86027 | } |
| 85911 | 86028 | if( SQLITE_OK==(rc = sqlite3VdbeMemClearAndResize(pMem, amt+1)) ){ |
| 85912 | 86029 | rc = sqlite3BtreePayload(pCur, offset, amt, pMem->z); |
| 85913 | 86030 | if( rc==SQLITE_OK ){ |
| | @@ -89587,11 +89704,11 @@ |
| 89587 | 89704 | assert( !zName || xDel!=SQLITE_DYNAMIC ); |
| 89588 | 89705 | return SQLITE_NOMEM_BKPT; |
| 89589 | 89706 | } |
| 89590 | 89707 | assert( p->aColName!=0 ); |
| 89591 | 89708 | pColName = &(p->aColName[idx+var*p->nResAlloc]); |
| 89592 | | - rc = sqlite3VdbeMemSetStr(pColName, zName, -1, SQLITE_UTF8, xDel); |
| 89709 | + rc = sqlite3VdbeMemSetText(pColName, zName, -1, xDel); |
| 89593 | 89710 | assert( rc!=0 || !zName || (pColName->flags&MEM_Term)!=0 ); |
| 89594 | 89711 | return rc; |
| 89595 | 89712 | } |
| 89596 | 89713 | |
| 89597 | 89714 | /* |
| | @@ -92665,11 +92782,27 @@ |
| 92665 | 92782 | int n, /* Bytes in string, or negative */ |
| 92666 | 92783 | u8 enc, /* Encoding of z. 0 for BLOBs */ |
| 92667 | 92784 | void (*xDel)(void*) /* Destructor function */ |
| 92668 | 92785 | ){ |
| 92669 | 92786 | Mem *pOut = pCtx->pOut; |
| 92670 | | - int rc = sqlite3VdbeMemSetStr(pOut, z, n, enc, xDel); |
| 92787 | + int rc; |
| 92788 | + if( enc==SQLITE_UTF8 ){ |
| 92789 | + rc = sqlite3VdbeMemSetText(pOut, z, n, xDel); |
| 92790 | + }else if( enc==SQLITE_UTF8_ZT ){ |
| 92791 | + /* It is usually considered improper to assert() on an input. However, |
| 92792 | + ** the following assert() is checking for inputs that are documented |
| 92793 | + ** to result in undefined behavior. */ |
| 92794 | + assert( z==0 |
| 92795 | + || n<0 |
| 92796 | + || n>pOut->db->aLimit[SQLITE_LIMIT_LENGTH] |
| 92797 | + || z[n]==0 |
| 92798 | + ); |
| 92799 | + rc = sqlite3VdbeMemSetText(pOut, z, n, xDel); |
| 92800 | + pOut->flags |= MEM_Term; |
| 92801 | + }else{ |
| 92802 | + rc = sqlite3VdbeMemSetStr(pOut, z, n, enc, xDel); |
| 92803 | + } |
| 92671 | 92804 | if( rc ){ |
| 92672 | 92805 | if( rc==SQLITE_TOOBIG ){ |
| 92673 | 92806 | sqlite3_result_error_toobig(pCtx); |
| 92674 | 92807 | }else{ |
| 92675 | 92808 | /* The only errors possible from sqlite3VdbeMemSetStr are |
| | @@ -92858,11 +92991,11 @@ |
| 92858 | 92991 | return; |
| 92859 | 92992 | } |
| 92860 | 92993 | #endif |
| 92861 | 92994 | assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); |
| 92862 | 92995 | assert( xDel!=SQLITE_DYNAMIC ); |
| 92863 | | - if( enc!=SQLITE_UTF8 ){ |
| 92996 | + if( enc!=SQLITE_UTF8 && enc!=SQLITE_UTF8_ZT ){ |
| 92864 | 92997 | if( enc==SQLITE_UTF16 ) enc = SQLITE_UTF16NATIVE; |
| 92865 | 92998 | n &= ~(u64)1; |
| 92866 | 92999 | } |
| 92867 | 93000 | if( n>0x7fffffff ){ |
| 92868 | 93001 | (void)invokeValueDestructor(z, xDel, pCtx); |
| | @@ -93318,11 +93451,11 @@ |
| 93318 | 93451 | if( rc==SQLITE_OK ){ |
| 93319 | 93452 | u32 sz; /* Size of current row in bytes */ |
| 93320 | 93453 | Mem sMem; /* Raw content of current row */ |
| 93321 | 93454 | memset(&sMem, 0, sizeof(sMem)); |
| 93322 | 93455 | sz = sqlite3BtreePayloadSize(pRhs->pCsr); |
| 93323 | | - rc = sqlite3VdbeMemFromBtreeZeroOffset(pRhs->pCsr,(int)sz,&sMem); |
| 93456 | + rc = sqlite3VdbeMemFromBtreeZeroOffset(pRhs->pCsr,sz,&sMem); |
| 93324 | 93457 | if( rc==SQLITE_OK ){ |
| 93325 | 93458 | u8 *zBuf = (u8*)sMem.z; |
| 93326 | 93459 | u32 iSerial; |
| 93327 | 93460 | sqlite3_value *pOut = pRhs->pOut; |
| 93328 | 93461 | int iOff = 1 + getVarint32(&zBuf[1], iSerial); |
| | @@ -93967,17 +94100,29 @@ |
| 93967 | 94100 | rc = vdbeUnbind(p, (u32)(i-1)); |
| 93968 | 94101 | if( rc==SQLITE_OK ){ |
| 93969 | 94102 | assert( p!=0 && p->aVar!=0 && i>0 && i<=p->nVar ); /* tag-20240917-01 */ |
| 93970 | 94103 | if( zData!=0 ){ |
| 93971 | 94104 | pVar = &p->aVar[i-1]; |
| 93972 | | - rc = sqlite3VdbeMemSetStr(pVar, zData, nData, encoding, xDel); |
| 93973 | | - if( rc==SQLITE_OK ){ |
| 93974 | | - if( encoding==0 ){ |
| 93975 | | - pVar->enc = ENC(p->db); |
| 93976 | | - }else{ |
| 93977 | | - rc = sqlite3VdbeChangeEncoding(pVar, ENC(p->db)); |
| 93978 | | - } |
| 94105 | + if( encoding==SQLITE_UTF8 ){ |
| 94106 | + rc = sqlite3VdbeMemSetText(pVar, zData, nData, xDel); |
| 94107 | + }else if( encoding==SQLITE_UTF8_ZT ){ |
| 94108 | + /* It is usually consider improper to assert() on an input. |
| 94109 | + ** However, the following assert() is checking for inputs |
| 94110 | + ** that are documented to result in undefined behavior. */ |
| 94111 | + assert( zData==0 |
| 94112 | + || nData<0 |
| 94113 | + || nData>pVar->db->aLimit[SQLITE_LIMIT_LENGTH] |
| 94114 | + || ((u8*)zData)[nData]==0 |
| 94115 | + ); |
| 94116 | + rc = sqlite3VdbeMemSetText(pVar, zData, nData, xDel); |
| 94117 | + pVar->flags |= MEM_Term; |
| 94118 | + }else{ |
| 94119 | + rc = sqlite3VdbeMemSetStr(pVar, zData, nData, encoding, xDel); |
| 94120 | + if( encoding==0 ) pVar->enc = ENC(p->db); |
| 94121 | + } |
| 94122 | + if( rc==SQLITE_OK && encoding!=0 ){ |
| 94123 | + rc = sqlite3VdbeChangeEncoding(pVar, ENC(p->db)); |
| 93979 | 94124 | } |
| 93980 | 94125 | if( rc ){ |
| 93981 | 94126 | sqlite3Error(p->db, rc); |
| 93982 | 94127 | rc = sqlite3ApiExit(p->db, rc); |
| 93983 | 94128 | } |
| | @@ -94085,11 +94230,11 @@ |
| 94085 | 94230 | sqlite3_uint64 nData, |
| 94086 | 94231 | void (*xDel)(void*), |
| 94087 | 94232 | unsigned char enc |
| 94088 | 94233 | ){ |
| 94089 | 94234 | assert( xDel!=SQLITE_DYNAMIC ); |
| 94090 | | - if( enc!=SQLITE_UTF8 ){ |
| 94235 | + if( enc!=SQLITE_UTF8 && enc!=SQLITE_UTF8_ZT ){ |
| 94091 | 94236 | if( enc==SQLITE_UTF16 ) enc = SQLITE_UTF16NATIVE; |
| 94092 | 94237 | nData &= ~(u64)1; |
| 94093 | 94238 | } |
| 94094 | 94239 | return bindText(pStmt, i, zData, nData, xDel, enc); |
| 94095 | 94240 | } |
| | @@ -101783,24 +101928,19 @@ |
| 101783 | 101928 | rc = sqlite3VdbeSorterWrite(pC, pIn2); |
| 101784 | 101929 | if( rc) goto abort_due_to_error; |
| 101785 | 101930 | break; |
| 101786 | 101931 | } |
| 101787 | 101932 | |
| 101788 | | -/* Opcode: IdxDelete P1 P2 P3 * P5 |
| 101933 | +/* Opcode: IdxDelete P1 P2 P3 * * |
| 101789 | 101934 | ** Synopsis: key=r[P2@P3] |
| 101790 | 101935 | ** |
| 101791 | 101936 | ** The content of P3 registers starting at register P2 form |
| 101792 | 101937 | ** an unpacked index key. This opcode removes that entry from the |
| 101793 | 101938 | ** index opened by cursor P1. |
| 101794 | 101939 | ** |
| 101795 | | -** If P5 is not zero, then raise an SQLITE_CORRUPT_INDEX error |
| 101796 | | -** if no matching index entry is found. This happens when running |
| 101797 | | -** an UPDATE or DELETE statement and the index entry to be updated |
| 101798 | | -** or deleted is not found. For some uses of IdxDelete |
| 101799 | | -** (example: the EXCEPT operator) it does not matter that no matching |
| 101800 | | -** entry is found. For those cases, P5 is zero. Also, do not raise |
| 101801 | | -** this (self-correcting and non-critical) error if in writable_schema mode. |
| 101940 | +** Raise an SQLITE_CORRUPT_INDEX error if no matching index entry is found |
| 101941 | +** and not in writable_schema mode. |
| 101802 | 101942 | */ |
| 101803 | 101943 | case OP_IdxDelete: { |
| 101804 | 101944 | VdbeCursor *pC; |
| 101805 | 101945 | BtCursor *pCrsr; |
| 101806 | 101946 | int res; |
| | @@ -101822,11 +101962,11 @@ |
| 101822 | 101962 | rc = sqlite3BtreeIndexMoveto(pCrsr, &r, &res); |
| 101823 | 101963 | if( rc ) goto abort_due_to_error; |
| 101824 | 101964 | if( res==0 ){ |
| 101825 | 101965 | rc = sqlite3BtreeDelete(pCrsr, BTREE_AUXDELETE); |
| 101826 | 101966 | if( rc ) goto abort_due_to_error; |
| 101827 | | - }else if( pOp->p5 && !sqlite3WritableSchema(db) ){ |
| 101967 | + }else if( !sqlite3WritableSchema(db) ){ |
| 101828 | 101968 | rc = sqlite3ReportError(SQLITE_CORRUPT_INDEX, __LINE__, "index corruption"); |
| 101829 | 101969 | goto abort_due_to_error; |
| 101830 | 101970 | } |
| 101831 | 101971 | assert( pC->deferredMoveto==0 ); |
| 101832 | 101972 | pC->cacheStatus = CACHE_STALE; |
| | @@ -113272,13 +113412,11 @@ |
| 113272 | 113412 | pNew->pNext = pNext; |
| 113273 | 113413 | pNew->pPrior = 0; |
| 113274 | 113414 | pNew->pLimit = sqlite3ExprDup(db, p->pLimit, flags); |
| 113275 | 113415 | pNew->iLimit = 0; |
| 113276 | 113416 | pNew->iOffset = 0; |
| 113277 | | - pNew->selFlags = p->selFlags & ~(u32)SF_UsesEphemeral; |
| 113278 | | - pNew->addrOpenEphm[0] = -1; |
| 113279 | | - pNew->addrOpenEphm[1] = -1; |
| 113417 | + pNew->selFlags = p->selFlags; |
| 113280 | 113418 | pNew->nSelectRow = p->nSelectRow; |
| 113281 | 113419 | pNew->pWith = sqlite3WithDup(db, p->pWith); |
| 113282 | 113420 | #ifndef SQLITE_OMIT_WINDOWFUNC |
| 113283 | 113421 | pNew->pWin = 0; |
| 113284 | 113422 | pNew->pWinDefn = sqlite3WindowListDup(db, p->pWinDefn); |
| | @@ -115496,12 +115634,13 @@ |
| 115496 | 115634 | if( destIfFalse==destIfNull ){ |
| 115497 | 115635 | /* Combine Step 3 and Step 5 into a single opcode */ |
| 115498 | 115636 | if( ExprHasProperty(pExpr, EP_Subrtn) ){ |
| 115499 | 115637 | const VdbeOp *pOp = sqlite3VdbeGetOp(v, pExpr->y.sub.iAddr); |
| 115500 | 115638 | assert( pOp->opcode==OP_Once || pParse->nErr ); |
| 115501 | | - if( pOp->opcode==OP_Once && pOp->p3>0 ){ /* tag-202407032019 */ |
| 115502 | | - assert( OptimizationEnabled(pParse->db, SQLITE_BloomFilter) ); |
| 115639 | + if( pOp->p3>0 ){ /* tag-202407032019 */ |
| 115640 | + assert( OptimizationEnabled(pParse->db, SQLITE_BloomFilter) |
| 115641 | + || pParse->nErr ); |
| 115503 | 115642 | sqlite3VdbeAddOp4Int(v, OP_Filter, pOp->p3, destIfFalse, |
| 115504 | 115643 | rLhs, nVector); VdbeCoverage(v); |
| 115505 | 115644 | } |
| 115506 | 115645 | } |
| 115507 | 115646 | sqlite3VdbeAddOp4Int(v, OP_NotFound, iTab, destIfFalse, |
| | @@ -132240,11 +132379,10 @@ |
| 132240 | 132379 | VdbeModuleComment((v, "GenRowIdxDel for %s", pIdx->zName)); |
| 132241 | 132380 | r1 = sqlite3GenerateIndexKey(pParse, pIdx, iDataCur, 0, 1, |
| 132242 | 132381 | &iPartIdxLabel, pPrior, r1); |
| 132243 | 132382 | sqlite3VdbeAddOp3(v, OP_IdxDelete, iIdxCur+i, r1, |
| 132244 | 132383 | pIdx->uniqNotNull ? pIdx->nKeyCol : pIdx->nColumn); |
| 132245 | | - sqlite3VdbeChangeP5(v, 1); /* Cause IdxDelete to error if no entry found */ |
| 132246 | 132384 | sqlite3ResolvePartIdxLabel(pParse, iPartIdxLabel); |
| 132247 | 132385 | pPrior = pIdx; |
| 132248 | 132386 | } |
| 132249 | 132387 | } |
| 132250 | 132388 | |
| | @@ -133587,11 +133725,11 @@ |
| 133587 | 133725 | }else{ |
| 133588 | 133726 | goto unistr_error; |
| 133589 | 133727 | } |
| 133590 | 133728 | } |
| 133591 | 133729 | zOut[j] = 0; |
| 133592 | | - sqlite3_result_text64(context, zOut, j, sqlite3_free, SQLITE_UTF8); |
| 133730 | + sqlite3_result_text64(context, zOut, j, sqlite3_free, SQLITE_UTF8_ZT); |
| 133593 | 133731 | return; |
| 133594 | 133732 | |
| 133595 | 133733 | unistr_error: |
| 133596 | 133734 | sqlite3_free(zOut); |
| 133597 | 133735 | sqlite3_result_error(context, "invalid Unicode escape", -1); |
| | @@ -133680,11 +133818,11 @@ |
| 133680 | 133818 | *zOut++ = 0x80 + (u8)((c>>6) & 0x3F); |
| 133681 | 133819 | *zOut++ = 0x80 + (u8)(c & 0x3F); |
| 133682 | 133820 | } \ |
| 133683 | 133821 | } |
| 133684 | 133822 | *zOut = 0; |
| 133685 | | - sqlite3_result_text64(context, (char*)z, zOut-z, sqlite3_free, SQLITE_UTF8); |
| 133823 | + sqlite3_result_text64(context, (char*)z, zOut-z,sqlite3_free,SQLITE_UTF8_ZT); |
| 133686 | 133824 | } |
| 133687 | 133825 | |
| 133688 | 133826 | /* |
| 133689 | 133827 | ** The hex() function. Interpret the argument as a blob. Return |
| 133690 | 133828 | ** a hexadecimal rendering as text. |
| | @@ -133709,11 +133847,11 @@ |
| 133709 | 133847 | *(z++) = hexdigits[(c>>4)&0xf]; |
| 133710 | 133848 | *(z++) = hexdigits[c&0xf]; |
| 133711 | 133849 | } |
| 133712 | 133850 | *z = 0; |
| 133713 | 133851 | sqlite3_result_text64(context, zHex, (u64)(z-zHex), |
| 133714 | | - sqlite3_free, SQLITE_UTF8); |
| 133852 | + sqlite3_free, SQLITE_UTF8_ZT); |
| 133715 | 133853 | } |
| 133716 | 133854 | } |
| 133717 | 133855 | |
| 133718 | 133856 | /* |
| 133719 | 133857 | ** Buffer zStr contains nStr bytes of utf-8 encoded text. Return 1 if zStr |
| | @@ -134047,11 +134185,11 @@ |
| 134047 | 134185 | } |
| 134048 | 134186 | } |
| 134049 | 134187 | } |
| 134050 | 134188 | z[j] = 0; |
| 134051 | 134189 | assert( j<=n ); |
| 134052 | | - sqlite3_result_text64(context, z, j, sqlite3_free, SQLITE_UTF8); |
| 134190 | + sqlite3_result_text64(context, z, j, sqlite3_free, SQLITE_UTF8_ZT); |
| 134053 | 134191 | } |
| 134054 | 134192 | |
| 134055 | 134193 | /* |
| 134056 | 134194 | ** The CONCAT(...) function. Generate a string result that is the |
| 134057 | 134195 | ** concatentation of all non-null arguments. |
| | @@ -141235,10 +141373,11 @@ |
| 141235 | 141373 | int (*set_errmsg)(sqlite3*,int,const char*); |
| 141236 | 141374 | int (*db_status64)(sqlite3*,int,sqlite3_int64*,sqlite3_int64*,int); |
| 141237 | 141375 | /* Version 3.52.0 and later */ |
| 141238 | 141376 | void (*str_truncate)(sqlite3_str*,int); |
| 141239 | 141377 | void (*str_free)(sqlite3_str*); |
| 141378 | + int (*carray_bind)(sqlite3_stmt*,int,void*,int,int,void(*)(void*)); |
| 141240 | 141379 | }; |
| 141241 | 141380 | |
| 141242 | 141381 | /* |
| 141243 | 141382 | ** This is the function signature used for all extension entry points. It |
| 141244 | 141383 | ** is also defined in the file "loadext.c". |
| | @@ -141576,10 +141715,11 @@ |
| 141576 | 141715 | #define sqlite3_set_errmsg sqlite3_api->set_errmsg |
| 141577 | 141716 | #define sqlite3_db_status64 sqlite3_api->db_status64 |
| 141578 | 141717 | /* Version 3.52.0 and later */ |
| 141579 | 141718 | #define sqlite3_str_truncate sqlite3_api->str_truncate |
| 141580 | 141719 | #define sqlite3_str_free sqlite3_api->str_free |
| 141720 | +#define sqlite3_carray_bind sqlite3_api->carray_bind |
| 141581 | 141721 | #endif /* !defined(SQLITE_CORE) && !defined(SQLITE_OMIT_LOAD_EXTENSION) */ |
| 141582 | 141722 | |
| 141583 | 141723 | #if !defined(SQLITE_CORE) && !defined(SQLITE_OMIT_LOAD_EXTENSION) |
| 141584 | 141724 | /* This case when the file really is being compiled as a loadable |
| 141585 | 141725 | ** extension */ |
| | @@ -142105,11 +142245,16 @@ |
| 142105 | 142245 | /* Version 3.51.0 and later */ |
| 142106 | 142246 | sqlite3_set_errmsg, |
| 142107 | 142247 | sqlite3_db_status64, |
| 142108 | 142248 | /* Version 3.52.0 and later */ |
| 142109 | 142249 | sqlite3_str_truncate, |
| 142110 | | - sqlite3_str_free |
| 142250 | + sqlite3_str_free, |
| 142251 | +#ifdef SQLITE_ENABLE_CARRAY |
| 142252 | + sqlite3_carray_bind |
| 142253 | +#else |
| 142254 | + 0 |
| 142255 | +#endif |
| 142111 | 142256 | }; |
| 142112 | 142257 | |
| 142113 | 142258 | /* True if x is the directory separator character |
| 142114 | 142259 | */ |
| 142115 | 142260 | #if SQLITE_OS_WIN |
| | @@ -147528,12 +147673,10 @@ |
| 147528 | 147673 | pNew->op = TK_SELECT; |
| 147529 | 147674 | pNew->selFlags = selFlags; |
| 147530 | 147675 | pNew->iLimit = 0; |
| 147531 | 147676 | pNew->iOffset = 0; |
| 147532 | 147677 | pNew->selId = ++pParse->nSelect; |
| 147533 | | - pNew->addrOpenEphm[0] = -1; |
| 147534 | | - pNew->addrOpenEphm[1] = -1; |
| 147535 | 147678 | pNew->nSelectRow = 0; |
| 147536 | 147679 | if( pSrc==0 ) pSrc = sqlite3DbMallocZero(pParse->db, SZ_SRCLIST_1); |
| 147537 | 147680 | pNew->pSrc = pSrc; |
| 147538 | 147681 | pNew->pWhere = pWhere; |
| 147539 | 147682 | pNew->pGroupBy = pGroupBy; |
| | @@ -148677,33 +148820,10 @@ |
| 148677 | 148820 | codeOffset(v, p->iOffset, iContinue); |
| 148678 | 148821 | } |
| 148679 | 148822 | } |
| 148680 | 148823 | |
| 148681 | 148824 | switch( eDest ){ |
| 148682 | | - /* In this mode, write each query result to the key of the temporary |
| 148683 | | - ** table iParm. |
| 148684 | | - */ |
| 148685 | | -#ifndef SQLITE_OMIT_COMPOUND_SELECT |
| 148686 | | - case SRT_Union: { |
| 148687 | | - int r1; |
| 148688 | | - r1 = sqlite3GetTempReg(pParse); |
| 148689 | | - sqlite3VdbeAddOp3(v, OP_MakeRecord, regResult, nResultCol, r1); |
| 148690 | | - sqlite3VdbeAddOp4Int(v, OP_IdxInsert, iParm, r1, regResult, nResultCol); |
| 148691 | | - sqlite3ReleaseTempReg(pParse, r1); |
| 148692 | | - break; |
| 148693 | | - } |
| 148694 | | - |
| 148695 | | - /* Construct a record from the query result, but instead of |
| 148696 | | - ** saving that record, use it as a key to delete elements from |
| 148697 | | - ** the temporary table iParm. |
| 148698 | | - */ |
| 148699 | | - case SRT_Except: { |
| 148700 | | - sqlite3VdbeAddOp3(v, OP_IdxDelete, iParm, regResult, nResultCol); |
| 148701 | | - break; |
| 148702 | | - } |
| 148703 | | -#endif /* SQLITE_OMIT_COMPOUND_SELECT */ |
| 148704 | | - |
| 148705 | 148825 | /* Store the result as data using a unique key. |
| 148706 | 148826 | */ |
| 148707 | 148827 | case SRT_Fifo: |
| 148708 | 148828 | case SRT_DistFifo: |
| 148709 | 148829 | case SRT_Table: |
| | @@ -149986,11 +150106,11 @@ |
| 149986 | 150106 | ** |
| 149987 | 150107 | ** Space to hold the KeyInfo structure is obtained from malloc. The calling |
| 149988 | 150108 | ** function is responsible for ensuring that this structure is eventually |
| 149989 | 150109 | ** freed. |
| 149990 | 150110 | */ |
| 149991 | | -static KeyInfo *multiSelectOrderByKeyInfo(Parse *pParse, Select *p, int nExtra){ |
| 150111 | +static KeyInfo *multiSelectByMergeKeyInfo(Parse *pParse, Select *p, int nExtra){ |
| 149992 | 150112 | ExprList *pOrderBy = p->pOrderBy; |
| 149993 | 150113 | int nOrderBy = ALWAYS(pOrderBy!=0) ? pOrderBy->nExpr : 0; |
| 149994 | 150114 | sqlite3 *db = pParse->db; |
| 149995 | 150115 | KeyInfo *pRet = sqlite3KeyInfoAlloc(db, nOrderBy+nExtra, 1); |
| 149996 | 150116 | if( pRet ){ |
| | @@ -150121,21 +150241,41 @@ |
| 150121 | 150241 | |
| 150122 | 150242 | /* Allocate cursors for Current, Queue, and Distinct. */ |
| 150123 | 150243 | regCurrent = ++pParse->nMem; |
| 150124 | 150244 | sqlite3VdbeAddOp3(v, OP_OpenPseudo, iCurrent, regCurrent, nCol); |
| 150125 | 150245 | if( pOrderBy ){ |
| 150126 | | - KeyInfo *pKeyInfo = multiSelectOrderByKeyInfo(pParse, p, 1); |
| 150246 | + KeyInfo *pKeyInfo = multiSelectByMergeKeyInfo(pParse, p, 1); |
| 150127 | 150247 | sqlite3VdbeAddOp4(v, OP_OpenEphemeral, iQueue, pOrderBy->nExpr+2, 0, |
| 150128 | 150248 | (char*)pKeyInfo, P4_KEYINFO); |
| 150129 | 150249 | destQueue.pOrderBy = pOrderBy; |
| 150130 | 150250 | }else{ |
| 150131 | 150251 | sqlite3VdbeAddOp2(v, OP_OpenEphemeral, iQueue, nCol); |
| 150132 | 150252 | } |
| 150133 | 150253 | VdbeComment((v, "Queue table")); |
| 150134 | 150254 | if( iDistinct ){ |
| 150135 | | - p->addrOpenEphm[0] = sqlite3VdbeAddOp2(v, OP_OpenEphemeral, iDistinct, 0); |
| 150136 | | - p->selFlags |= SF_UsesEphemeral; |
| 150255 | + /* Generate an ephemeral table used to enforce distinctness on the |
| 150256 | + ** output of the recursive part of the CTE. |
| 150257 | + */ |
| 150258 | + KeyInfo *pKeyInfo; /* Collating sequence for the result set */ |
| 150259 | + CollSeq **apColl; /* For looping through pKeyInfo->aColl[] */ |
| 150260 | + |
| 150261 | + assert( p->pNext==0 ); |
| 150262 | + assert( p->pEList!=0 ); |
| 150263 | + nCol = p->pEList->nExpr; |
| 150264 | + pKeyInfo = sqlite3KeyInfoAlloc(pParse->db, nCol, 1); |
| 150265 | + if( pKeyInfo ){ |
| 150266 | + for(i=0, apColl=pKeyInfo->aColl; i<nCol; i++, apColl++){ |
| 150267 | + *apColl = multiSelectCollSeq(pParse, p, i); |
| 150268 | + if( 0==*apColl ){ |
| 150269 | + *apColl = pParse->db->pDfltColl; |
| 150270 | + } |
| 150271 | + } |
| 150272 | + sqlite3VdbeAddOp4(v, OP_OpenEphemeral, iDistinct, nCol, 0, |
| 150273 | + (void*)pKeyInfo, P4_KEYINFO); |
| 150274 | + }else{ |
| 150275 | + assert( pParse->nErr>0 ); |
| 150276 | + } |
| 150137 | 150277 | } |
| 150138 | 150278 | |
| 150139 | 150279 | /* Detach the ORDER BY clause from the compound SELECT */ |
| 150140 | 150280 | p->pOrderBy = 0; |
| 150141 | 150281 | |
| | @@ -150206,11 +150346,11 @@ |
| 150206 | 150346 | return; |
| 150207 | 150347 | } |
| 150208 | 150348 | #endif /* SQLITE_OMIT_CTE */ |
| 150209 | 150349 | |
| 150210 | 150350 | /* Forward references */ |
| 150211 | | -static int multiSelectOrderBy( |
| 150351 | +static int multiSelectByMerge( |
| 150212 | 150352 | Parse *pParse, /* Parsing context */ |
| 150213 | 150353 | Select *p, /* The right-most of SELECTs to be coded */ |
| 150214 | 150354 | SelectDest *pDest /* What to do with query results */ |
| 150215 | 150355 | ); |
| 150216 | 150356 | |
| | @@ -150355,317 +150495,80 @@ |
| 150355 | 150495 | #ifndef SQLITE_OMIT_CTE |
| 150356 | 150496 | if( (p->selFlags & SF_Recursive)!=0 && hasAnchor(p) ){ |
| 150357 | 150497 | generateWithRecursiveQuery(pParse, p, &dest); |
| 150358 | 150498 | }else |
| 150359 | 150499 | #endif |
| 150360 | | - |
| 150361 | | - /* Compound SELECTs that have an ORDER BY clause are handled separately. |
| 150362 | | - */ |
| 150363 | 150500 | if( p->pOrderBy ){ |
| 150364 | | - return multiSelectOrderBy(pParse, p, pDest); |
| 150501 | + /* If the compound has an ORDER BY clause, then always use the merge |
| 150502 | + ** algorithm. */ |
| 150503 | + return multiSelectByMerge(pParse, p, pDest); |
| 150504 | + }else if( p->op!=TK_ALL ){ |
| 150505 | + /* If the compound is EXCEPT, INTERSECT, or UNION (anything other than |
| 150506 | + ** UNION ALL) then also always use the merge algorithm. However, the |
| 150507 | + ** multiSelectByMerge() routine requires that the compound have an |
| 150508 | + ** ORDER BY clause, and it doesn't right now. So invent one first. */ |
| 150509 | + Expr *pOne = sqlite3ExprInt32(db, 1); |
| 150510 | + p->pOrderBy = sqlite3ExprListAppend(pParse, 0, pOne); |
| 150511 | + if( pParse->nErr ) goto multi_select_end; |
| 150512 | + assert( p->pOrderBy!=0 ); |
| 150513 | + p->pOrderBy->a[0].u.x.iOrderByCol = 1; |
| 150514 | + return multiSelectByMerge(pParse, p, pDest); |
| 150365 | 150515 | }else{ |
| 150516 | + /* For a UNION ALL compound without ORDER BY, simply run the left |
| 150517 | + ** query, then run the right query */ |
| 150518 | + int addr = 0; |
| 150519 | + int nLimit = 0; /* Initialize to suppress harmless compiler warning */ |
| 150366 | 150520 | |
| 150367 | 150521 | #ifndef SQLITE_OMIT_EXPLAIN |
| 150368 | 150522 | if( pPrior->pPrior==0 ){ |
| 150369 | 150523 | ExplainQueryPlan((pParse, 1, "COMPOUND QUERY")); |
| 150370 | 150524 | ExplainQueryPlan((pParse, 1, "LEFT-MOST SUBQUERY")); |
| 150371 | 150525 | } |
| 150372 | 150526 | #endif |
| 150373 | | - |
| 150374 | | - /* Generate code for the left and right SELECT statements. |
| 150375 | | - */ |
| 150376 | | - switch( p->op ){ |
| 150377 | | - case TK_ALL: { |
| 150378 | | - int addr = 0; |
| 150379 | | - int nLimit = 0; /* Initialize to suppress harmless compiler warning */ |
| 150380 | | - assert( !pPrior->pLimit ); |
| 150381 | | - pPrior->iLimit = p->iLimit; |
| 150382 | | - pPrior->iOffset = p->iOffset; |
| 150383 | | - pPrior->pLimit = p->pLimit; |
| 150384 | | - TREETRACE(0x200, pParse, p, ("multiSelect UNION ALL left...\n")); |
| 150385 | | - rc = sqlite3Select(pParse, pPrior, &dest); |
| 150386 | | - pPrior->pLimit = 0; |
| 150387 | | - if( rc ){ |
| 150388 | | - goto multi_select_end; |
| 150389 | | - } |
| 150390 | | - p->pPrior = 0; |
| 150391 | | - p->iLimit = pPrior->iLimit; |
| 150392 | | - p->iOffset = pPrior->iOffset; |
| 150393 | | - if( p->iLimit ){ |
| 150394 | | - addr = sqlite3VdbeAddOp1(v, OP_IfNot, p->iLimit); VdbeCoverage(v); |
| 150395 | | - VdbeComment((v, "Jump ahead if LIMIT reached")); |
| 150396 | | - if( p->iOffset ){ |
| 150397 | | - sqlite3VdbeAddOp3(v, OP_OffsetLimit, |
| 150398 | | - p->iLimit, p->iOffset+1, p->iOffset); |
| 150399 | | - } |
| 150400 | | - } |
| 150401 | | - ExplainQueryPlan((pParse, 1, "UNION ALL")); |
| 150402 | | - TREETRACE(0x200, pParse, p, ("multiSelect UNION ALL right...\n")); |
| 150403 | | - rc = sqlite3Select(pParse, p, &dest); |
| 150404 | | - testcase( rc!=SQLITE_OK ); |
| 150405 | | - pDelete = p->pPrior; |
| 150406 | | - p->pPrior = pPrior; |
| 150407 | | - p->nSelectRow = sqlite3LogEstAdd(p->nSelectRow, pPrior->nSelectRow); |
| 150408 | | - if( p->pLimit |
| 150409 | | - && sqlite3ExprIsInteger(p->pLimit->pLeft, &nLimit, pParse) |
| 150410 | | - && nLimit>0 && p->nSelectRow > sqlite3LogEst((u64)nLimit) |
| 150411 | | - ){ |
| 150412 | | - p->nSelectRow = sqlite3LogEst((u64)nLimit); |
| 150413 | | - } |
| 150414 | | - if( addr ){ |
| 150415 | | - sqlite3VdbeJumpHere(v, addr); |
| 150416 | | - } |
| 150417 | | - break; |
| 150418 | | - } |
| 150419 | | - case TK_EXCEPT: |
| 150420 | | - case TK_UNION: { |
| 150421 | | - int unionTab; /* Cursor number of the temp table holding result */ |
| 150422 | | - u8 op = 0; /* One of the SRT_ operations to apply to self */ |
| 150423 | | - int priorOp; /* The SRT_ operation to apply to prior selects */ |
| 150424 | | - Expr *pLimit; /* Saved values of p->nLimit */ |
| 150425 | | - int addr; |
| 150426 | | - int emptyBypass = 0; /* IfEmpty opcode to bypass RHS */ |
| 150427 | | - SelectDest uniondest; |
| 150428 | | - |
| 150429 | | - |
| 150430 | | - testcase( p->op==TK_EXCEPT ); |
| 150431 | | - testcase( p->op==TK_UNION ); |
| 150432 | | - priorOp = SRT_Union; |
| 150433 | | - if( dest.eDest==priorOp ){ |
| 150434 | | - /* We can reuse a temporary table generated by a SELECT to our |
| 150435 | | - ** right. |
| 150436 | | - */ |
| 150437 | | - assert( p->pLimit==0 ); /* Not allowed on leftward elements */ |
| 150438 | | - unionTab = dest.iSDParm; |
| 150439 | | - }else{ |
| 150440 | | - /* We will need to create our own temporary table to hold the |
| 150441 | | - ** intermediate results. |
| 150442 | | - */ |
| 150443 | | - unionTab = pParse->nTab++; |
| 150444 | | - assert( p->pOrderBy==0 ); |
| 150445 | | - addr = sqlite3VdbeAddOp2(v, OP_OpenEphemeral, unionTab, 0); |
| 150446 | | - assert( p->addrOpenEphm[0] == -1 ); |
| 150447 | | - p->addrOpenEphm[0] = addr; |
| 150448 | | - findRightmost(p)->selFlags |= SF_UsesEphemeral; |
| 150449 | | - assert( p->pEList ); |
| 150450 | | - } |
| 150451 | | - |
| 150452 | | - |
| 150453 | | - /* Code the SELECT statements to our left |
| 150454 | | - */ |
| 150455 | | - assert( !pPrior->pOrderBy ); |
| 150456 | | - sqlite3SelectDestInit(&uniondest, priorOp, unionTab); |
| 150457 | | - TREETRACE(0x200, pParse, p, ("multiSelect EXCEPT/UNION left...\n")); |
| 150458 | | - rc = sqlite3Select(pParse, pPrior, &uniondest); |
| 150459 | | - if( rc ){ |
| 150460 | | - goto multi_select_end; |
| 150461 | | - } |
| 150462 | | - |
| 150463 | | - /* Code the current SELECT statement |
| 150464 | | - */ |
| 150465 | | - if( p->op==TK_EXCEPT ){ |
| 150466 | | - op = SRT_Except; |
| 150467 | | - emptyBypass = sqlite3VdbeAddOp1(v, OP_IfEmpty, unionTab); |
| 150468 | | - VdbeCoverage(v); |
| 150469 | | - }else{ |
| 150470 | | - assert( p->op==TK_UNION ); |
| 150471 | | - op = SRT_Union; |
| 150472 | | - } |
| 150473 | | - p->pPrior = 0; |
| 150474 | | - pLimit = p->pLimit; |
| 150475 | | - p->pLimit = 0; |
| 150476 | | - uniondest.eDest = op; |
| 150477 | | - ExplainQueryPlan((pParse, 1, "%s USING TEMP B-TREE", |
| 150478 | | - sqlite3SelectOpName(p->op))); |
| 150479 | | - TREETRACE(0x200, pParse, p, ("multiSelect EXCEPT/UNION right...\n")); |
| 150480 | | - rc = sqlite3Select(pParse, p, &uniondest); |
| 150481 | | - testcase( rc!=SQLITE_OK ); |
| 150482 | | - assert( p->pOrderBy==0 ); |
| 150483 | | - pDelete = p->pPrior; |
| 150484 | | - p->pPrior = pPrior; |
| 150485 | | - p->pOrderBy = 0; |
| 150486 | | - if( p->op==TK_UNION ){ |
| 150487 | | - p->nSelectRow = sqlite3LogEstAdd(p->nSelectRow, pPrior->nSelectRow); |
| 150488 | | - } |
| 150489 | | - if( emptyBypass ) sqlite3VdbeJumpHere(v, emptyBypass); |
| 150490 | | - sqlite3ExprDelete(db, p->pLimit); |
| 150491 | | - p->pLimit = pLimit; |
| 150492 | | - p->iLimit = 0; |
| 150493 | | - p->iOffset = 0; |
| 150494 | | - |
| 150495 | | - /* Convert the data in the temporary table into whatever form |
| 150496 | | - ** it is that we currently need. |
| 150497 | | - */ |
| 150498 | | - assert( unionTab==dest.iSDParm || dest.eDest!=priorOp ); |
| 150499 | | - assert( p->pEList || db->mallocFailed ); |
| 150500 | | - if( dest.eDest!=priorOp && db->mallocFailed==0 ){ |
| 150501 | | - int iCont, iBreak, iStart; |
| 150502 | | - iBreak = sqlite3VdbeMakeLabel(pParse); |
| 150503 | | - iCont = sqlite3VdbeMakeLabel(pParse); |
| 150504 | | - computeLimitRegisters(pParse, p, iBreak); |
| 150505 | | - sqlite3VdbeAddOp2(v, OP_Rewind, unionTab, iBreak); VdbeCoverage(v); |
| 150506 | | - iStart = sqlite3VdbeCurrentAddr(v); |
| 150507 | | - selectInnerLoop(pParse, p, unionTab, |
| 150508 | | - 0, 0, &dest, iCont, iBreak); |
| 150509 | | - sqlite3VdbeResolveLabel(v, iCont); |
| 150510 | | - sqlite3VdbeAddOp2(v, OP_Next, unionTab, iStart); VdbeCoverage(v); |
| 150511 | | - sqlite3VdbeResolveLabel(v, iBreak); |
| 150512 | | - sqlite3VdbeAddOp2(v, OP_Close, unionTab, 0); |
| 150513 | | - } |
| 150514 | | - break; |
| 150515 | | - } |
| 150516 | | - default: assert( p->op==TK_INTERSECT ); { |
| 150517 | | - int tab1, tab2; |
| 150518 | | - int iCont, iBreak, iStart; |
| 150519 | | - Expr *pLimit; |
| 150520 | | - int addr, iLimit, iOffset; |
| 150521 | | - SelectDest intersectdest; |
| 150522 | | - int r1; |
| 150523 | | - int emptyBypass; |
| 150524 | | - |
| 150525 | | - /* INTERSECT is different from the others since it requires |
| 150526 | | - ** two temporary tables. Hence it has its own case. Begin |
| 150527 | | - ** by allocating the tables we will need. |
| 150528 | | - */ |
| 150529 | | - tab1 = pParse->nTab++; |
| 150530 | | - tab2 = pParse->nTab++; |
| 150531 | | - assert( p->pOrderBy==0 ); |
| 150532 | | - |
| 150533 | | - addr = sqlite3VdbeAddOp2(v, OP_OpenEphemeral, tab1, 0); |
| 150534 | | - assert( p->addrOpenEphm[0] == -1 ); |
| 150535 | | - p->addrOpenEphm[0] = addr; |
| 150536 | | - findRightmost(p)->selFlags |= SF_UsesEphemeral; |
| 150537 | | - assert( p->pEList ); |
| 150538 | | - |
| 150539 | | - /* Code the SELECTs to our left into temporary table "tab1". |
| 150540 | | - */ |
| 150541 | | - sqlite3SelectDestInit(&intersectdest, SRT_Union, tab1); |
| 150542 | | - TREETRACE(0x400, pParse, p, ("multiSelect INTERSECT left...\n")); |
| 150543 | | - rc = sqlite3Select(pParse, pPrior, &intersectdest); |
| 150544 | | - if( rc ){ |
| 150545 | | - goto multi_select_end; |
| 150546 | | - } |
| 150547 | | - |
| 150548 | | - /* Initialize LIMIT counters before checking to see if the LHS |
| 150549 | | - ** is empty, in case the jump is taken */ |
| 150550 | | - iBreak = sqlite3VdbeMakeLabel(pParse); |
| 150551 | | - computeLimitRegisters(pParse, p, iBreak); |
| 150552 | | - emptyBypass = sqlite3VdbeAddOp1(v, OP_IfEmpty, tab1); VdbeCoverage(v); |
| 150553 | | - |
| 150554 | | - /* Code the current SELECT into temporary table "tab2" |
| 150555 | | - */ |
| 150556 | | - addr = sqlite3VdbeAddOp2(v, OP_OpenEphemeral, tab2, 0); |
| 150557 | | - assert( p->addrOpenEphm[1] == -1 ); |
| 150558 | | - p->addrOpenEphm[1] = addr; |
| 150559 | | - |
| 150560 | | - /* Disable prior SELECTs and the LIMIT counters during the computation |
| 150561 | | - ** of the RHS select */ |
| 150562 | | - pLimit = p->pLimit; |
| 150563 | | - iLimit = p->iLimit; |
| 150564 | | - iOffset = p->iOffset; |
| 150565 | | - p->pPrior = 0; |
| 150566 | | - p->pLimit = 0; |
| 150567 | | - p->iLimit = 0; |
| 150568 | | - p->iOffset = 0; |
| 150569 | | - |
| 150570 | | - intersectdest.iSDParm = tab2; |
| 150571 | | - ExplainQueryPlan((pParse, 1, "%s USING TEMP B-TREE", |
| 150572 | | - sqlite3SelectOpName(p->op))); |
| 150573 | | - TREETRACE(0x400, pParse, p, ("multiSelect INTERSECT right...\n")); |
| 150574 | | - rc = sqlite3Select(pParse, p, &intersectdest); |
| 150575 | | - testcase( rc!=SQLITE_OK ); |
| 150576 | | - pDelete = p->pPrior; |
| 150577 | | - p->pPrior = pPrior; |
| 150578 | | - if( p->nSelectRow>pPrior->nSelectRow ){ |
| 150579 | | - p->nSelectRow = pPrior->nSelectRow; |
| 150580 | | - } |
| 150581 | | - sqlite3ExprDelete(db, p->pLimit); |
| 150582 | | - |
| 150583 | | - /* Reinstate the LIMIT counters prior to running the final intersect */ |
| 150584 | | - p->pLimit = pLimit; |
| 150585 | | - p->iLimit = iLimit; |
| 150586 | | - p->iOffset = iOffset; |
| 150587 | | - |
| 150588 | | - /* Generate code to take the intersection of the two temporary |
| 150589 | | - ** tables. |
| 150590 | | - */ |
| 150591 | | - if( rc ) break; |
| 150592 | | - assert( p->pEList ); |
| 150593 | | - sqlite3VdbeAddOp1(v, OP_Rewind, tab1); |
| 150594 | | - r1 = sqlite3GetTempReg(pParse); |
| 150595 | | - iStart = sqlite3VdbeAddOp2(v, OP_RowData, tab1, r1); |
| 150596 | | - iCont = sqlite3VdbeMakeLabel(pParse); |
| 150597 | | - sqlite3VdbeAddOp4Int(v, OP_NotFound, tab2, iCont, r1, 0); |
| 150598 | | - VdbeCoverage(v); |
| 150599 | | - sqlite3ReleaseTempReg(pParse, r1); |
| 150600 | | - selectInnerLoop(pParse, p, tab1, |
| 150601 | | - 0, 0, &dest, iCont, iBreak); |
| 150602 | | - sqlite3VdbeResolveLabel(v, iCont); |
| 150603 | | - sqlite3VdbeAddOp2(v, OP_Next, tab1, iStart); VdbeCoverage(v); |
| 150604 | | - sqlite3VdbeResolveLabel(v, iBreak); |
| 150605 | | - sqlite3VdbeAddOp2(v, OP_Close, tab2, 0); |
| 150606 | | - sqlite3VdbeJumpHere(v, emptyBypass); |
| 150607 | | - sqlite3VdbeAddOp2(v, OP_Close, tab1, 0); |
| 150608 | | - break; |
| 150609 | | - } |
| 150610 | | - } |
| 150611 | | - |
| 150612 | | - #ifndef SQLITE_OMIT_EXPLAIN |
| 150527 | + assert( !pPrior->pLimit ); |
| 150528 | + pPrior->iLimit = p->iLimit; |
| 150529 | + pPrior->iOffset = p->iOffset; |
| 150530 | + pPrior->pLimit = sqlite3ExprDup(db, p->pLimit, 0); |
| 150531 | + TREETRACE(0x200, pParse, p, ("multiSelect UNION ALL left...\n")); |
| 150532 | + rc = sqlite3Select(pParse, pPrior, &dest); |
| 150533 | + sqlite3ExprDelete(db, pPrior->pLimit); |
| 150534 | + pPrior->pLimit = 0; |
| 150535 | + if( rc ){ |
| 150536 | + goto multi_select_end; |
| 150537 | + } |
| 150538 | + p->pPrior = 0; |
| 150539 | + p->iLimit = pPrior->iLimit; |
| 150540 | + p->iOffset = pPrior->iOffset; |
| 150541 | + if( p->iLimit ){ |
| 150542 | + addr = sqlite3VdbeAddOp1(v, OP_IfNot, p->iLimit); VdbeCoverage(v); |
| 150543 | + VdbeComment((v, "Jump ahead if LIMIT reached")); |
| 150544 | + if( p->iOffset ){ |
| 150545 | + sqlite3VdbeAddOp3(v, OP_OffsetLimit, |
| 150546 | + p->iLimit, p->iOffset+1, p->iOffset); |
| 150547 | + } |
| 150548 | + } |
| 150549 | + ExplainQueryPlan((pParse, 1, "UNION ALL")); |
| 150550 | + TREETRACE(0x200, pParse, p, ("multiSelect UNION ALL right...\n")); |
| 150551 | + rc = sqlite3Select(pParse, p, &dest); |
| 150552 | + testcase( rc!=SQLITE_OK ); |
| 150553 | + pDelete = p->pPrior; |
| 150554 | + p->pPrior = pPrior; |
| 150555 | + p->nSelectRow = sqlite3LogEstAdd(p->nSelectRow, pPrior->nSelectRow); |
| 150556 | + if( p->pLimit |
| 150557 | + && sqlite3ExprIsInteger(p->pLimit->pLeft, &nLimit, pParse) |
| 150558 | + && nLimit>0 && p->nSelectRow > sqlite3LogEst((u64)nLimit) |
| 150559 | + ){ |
| 150560 | + p->nSelectRow = sqlite3LogEst((u64)nLimit); |
| 150561 | + } |
| 150562 | + if( addr ){ |
| 150563 | + sqlite3VdbeJumpHere(v, addr); |
| 150564 | + } |
| 150565 | +#ifndef SQLITE_OMIT_EXPLAIN |
| 150613 | 150566 | if( p->pNext==0 ){ |
| 150614 | 150567 | ExplainQueryPlanPop(pParse); |
| 150615 | 150568 | } |
| 150616 | | - #endif |
| 150617 | | - } |
| 150618 | | - if( pParse->nErr ) goto multi_select_end; |
| 150619 | | - |
| 150620 | | - /* Compute collating sequences used by |
| 150621 | | - ** temporary tables needed to implement the compound select. |
| 150622 | | - ** Attach the KeyInfo structure to all temporary tables. |
| 150623 | | - ** |
| 150624 | | - ** This section is run by the right-most SELECT statement only. |
| 150625 | | - ** SELECT statements to the left always skip this part. The right-most |
| 150626 | | - ** SELECT might also skip this part if it has no ORDER BY clause and |
| 150627 | | - ** no temp tables are required. |
| 150628 | | - */ |
| 150629 | | - if( p->selFlags & SF_UsesEphemeral ){ |
| 150630 | | - int i; /* Loop counter */ |
| 150631 | | - KeyInfo *pKeyInfo; /* Collating sequence for the result set */ |
| 150632 | | - Select *pLoop; /* For looping through SELECT statements */ |
| 150633 | | - CollSeq **apColl; /* For looping through pKeyInfo->aColl[] */ |
| 150634 | | - int nCol; /* Number of columns in result set */ |
| 150635 | | - |
| 150636 | | - assert( p->pNext==0 ); |
| 150637 | | - assert( p->pEList!=0 ); |
| 150638 | | - nCol = p->pEList->nExpr; |
| 150639 | | - pKeyInfo = sqlite3KeyInfoAlloc(db, nCol, 1); |
| 150640 | | - if( !pKeyInfo ){ |
| 150641 | | - rc = SQLITE_NOMEM_BKPT; |
| 150642 | | - goto multi_select_end; |
| 150643 | | - } |
| 150644 | | - for(i=0, apColl=pKeyInfo->aColl; i<nCol; i++, apColl++){ |
| 150645 | | - *apColl = multiSelectCollSeq(pParse, p, i); |
| 150646 | | - if( 0==*apColl ){ |
| 150647 | | - *apColl = db->pDfltColl; |
| 150648 | | - } |
| 150649 | | - } |
| 150650 | | - |
| 150651 | | - for(pLoop=p; pLoop; pLoop=pLoop->pPrior){ |
| 150652 | | - for(i=0; i<2; i++){ |
| 150653 | | - int addr = pLoop->addrOpenEphm[i]; |
| 150654 | | - if( addr<0 ){ |
| 150655 | | - /* If [0] is unused then [1] is also unused. So we can |
| 150656 | | - ** always safely abort as soon as the first unused slot is found */ |
| 150657 | | - assert( pLoop->addrOpenEphm[1]<0 ); |
| 150658 | | - break; |
| 150659 | | - } |
| 150660 | | - sqlite3VdbeChangeP2(v, addr, nCol); |
| 150661 | | - sqlite3VdbeChangeP4(v, addr, (char*)sqlite3KeyInfoRef(pKeyInfo), |
| 150662 | | - P4_KEYINFO); |
| 150663 | | - pLoop->addrOpenEphm[i] = -1; |
| 150664 | | - } |
| 150665 | | - } |
| 150666 | | - sqlite3KeyInfoUnref(pKeyInfo); |
| 150569 | +#endif |
| 150667 | 150570 | } |
| 150668 | 150571 | |
| 150669 | 150572 | multi_select_end: |
| 150670 | 150573 | pDest->iSdst = dest.iSdst; |
| 150671 | 150574 | pDest->nSdst = dest.nSdst; |
| | @@ -150693,12 +150596,12 @@ |
| 150693 | 150596 | |
| 150694 | 150597 | /* |
| 150695 | 150598 | ** Code an output subroutine for a coroutine implementation of a |
| 150696 | 150599 | ** SELECT statement. |
| 150697 | 150600 | ** |
| 150698 | | -** The data to be output is contained in pIn->iSdst. There are |
| 150699 | | -** pIn->nSdst columns to be output. pDest is where the output should |
| 150601 | +** The data to be output is contained in an array of pIn->nSdst registers |
| 150602 | +** starting at register pIn->iSdst. pDest is where the output should |
| 150700 | 150603 | ** be sent. |
| 150701 | 150604 | ** |
| 150702 | 150605 | ** regReturn is the number of the register holding the subroutine |
| 150703 | 150606 | ** return address. |
| 150704 | 150607 | ** |
| | @@ -150723,10 +150626,12 @@ |
| 150723 | 150626 | ){ |
| 150724 | 150627 | Vdbe *v = pParse->pVdbe; |
| 150725 | 150628 | int iContinue; |
| 150726 | 150629 | int addr; |
| 150727 | 150630 | |
| 150631 | + assert( pIn->eDest==SRT_Coroutine ); |
| 150632 | + |
| 150728 | 150633 | addr = sqlite3VdbeCurrentAddr(v); |
| 150729 | 150634 | iContinue = sqlite3VdbeMakeLabel(pParse); |
| 150730 | 150635 | |
| 150731 | 150636 | /* Suppress duplicates for UNION, EXCEPT, and INTERSECT |
| 150732 | 150637 | */ |
| | @@ -150744,26 +150649,63 @@ |
| 150744 | 150649 | |
| 150745 | 150650 | /* Suppress the first OFFSET entries if there is an OFFSET clause |
| 150746 | 150651 | */ |
| 150747 | 150652 | codeOffset(v, p->iOffset, iContinue); |
| 150748 | 150653 | |
| 150749 | | - assert( pDest->eDest!=SRT_Exists ); |
| 150750 | | - assert( pDest->eDest!=SRT_Table ); |
| 150751 | 150654 | switch( pDest->eDest ){ |
| 150752 | 150655 | /* Store the result as data using a unique key. |
| 150753 | 150656 | */ |
| 150657 | + case SRT_Fifo: |
| 150658 | + case SRT_DistFifo: |
| 150659 | + case SRT_Table: |
| 150754 | 150660 | case SRT_EphemTab: { |
| 150755 | 150661 | int r1 = sqlite3GetTempReg(pParse); |
| 150756 | 150662 | int r2 = sqlite3GetTempReg(pParse); |
| 150663 | + int iParm = pDest->iSDParm; |
| 150664 | + testcase( pDest->eDest==SRT_Table ); |
| 150665 | + testcase( pDest->eDest==SRT_EphemTab ); |
| 150666 | + testcase( pDest->eDest==SRT_Fifo ); |
| 150667 | + testcase( pDest->eDest==SRT_DistFifo ); |
| 150757 | 150668 | sqlite3VdbeAddOp3(v, OP_MakeRecord, pIn->iSdst, pIn->nSdst, r1); |
| 150758 | | - sqlite3VdbeAddOp2(v, OP_NewRowid, pDest->iSDParm, r2); |
| 150759 | | - sqlite3VdbeAddOp3(v, OP_Insert, pDest->iSDParm, r1, r2); |
| 150669 | +#if !defined(SQLITE_ENABLE_NULL_TRIM) && defined(SQLITE_DEBUG) |
| 150670 | + /* A destination of SRT_Table and a non-zero iSDParm2 parameter means |
| 150671 | + ** that this is an "UPDATE ... FROM" on a virtual table or view. In this |
| 150672 | + ** case set the p5 parameter of the OP_MakeRecord to OPFLAG_NOCHNG_MAGIC. |
| 150673 | + ** This does not affect operation in any way - it just allows MakeRecord |
| 150674 | + ** to process OPFLAG_NOCHANGE values without an assert() failing. */ |
| 150675 | + if( pDest->eDest==SRT_Table && pDest->iSDParm2 ){ |
| 150676 | + sqlite3VdbeChangeP5(v, OPFLAG_NOCHNG_MAGIC); |
| 150677 | + } |
| 150678 | +#endif |
| 150679 | +#ifndef SQLITE_OMIT_CTE |
| 150680 | + if( pDest->eDest==SRT_DistFifo ){ |
| 150681 | + /* If the destination is DistFifo, then cursor (iParm+1) is open |
| 150682 | + ** on an ephemeral index that is used to enforce uniqueness on the |
| 150683 | + ** total result. At this point, we are processing the setup portion |
| 150684 | + ** of the recursive CTE using the merge algorithm, so the results are |
| 150685 | + ** guaranteed to be unique anyhow. But we still need to populate the |
| 150686 | + ** (iParm+1) cursor for use by the subsequent recursive phase. |
| 150687 | + */ |
| 150688 | + sqlite3VdbeAddOp4Int(v, OP_IdxInsert, iParm+1, r1, |
| 150689 | + pIn->iSdst, pIn->nSdst); |
| 150690 | + } |
| 150691 | +#endif |
| 150692 | + sqlite3VdbeAddOp2(v, OP_NewRowid, iParm, r2); |
| 150693 | + sqlite3VdbeAddOp3(v, OP_Insert, iParm, r1, r2); |
| 150760 | 150694 | sqlite3VdbeChangeP5(v, OPFLAG_APPEND); |
| 150761 | 150695 | sqlite3ReleaseTempReg(pParse, r2); |
| 150762 | 150696 | sqlite3ReleaseTempReg(pParse, r1); |
| 150763 | 150697 | break; |
| 150764 | 150698 | } |
| 150699 | + |
| 150700 | + /* If any row exist in the result set, record that fact and abort. |
| 150701 | + */ |
| 150702 | + case SRT_Exists: { |
| 150703 | + sqlite3VdbeAddOp2(v, OP_Integer, 1, pDest->iSDParm); |
| 150704 | + /* The LIMIT clause will terminate the loop for us */ |
| 150705 | + break; |
| 150706 | + } |
| 150765 | 150707 | |
| 150766 | 150708 | #ifndef SQLITE_OMIT_SUBQUERY |
| 150767 | 150709 | /* If we are creating a set for an "expr IN (SELECT ...)". |
| 150768 | 150710 | */ |
| 150769 | 150711 | case SRT_Set: { |
| | @@ -150806,14 +150748,74 @@ |
| 150806 | 150748 | } |
| 150807 | 150749 | sqlite3ExprCodeMove(pParse, pIn->iSdst, pDest->iSdst, pIn->nSdst); |
| 150808 | 150750 | sqlite3VdbeAddOp1(v, OP_Yield, pDest->iSDParm); |
| 150809 | 150751 | break; |
| 150810 | 150752 | } |
| 150753 | + |
| 150754 | +#ifndef SQLITE_OMIT_CTE |
| 150755 | + /* Write the results into a priority queue that is order according to |
| 150756 | + ** pDest->pOrderBy (in pSO). pDest->iSDParm (in iParm) is the cursor for an |
| 150757 | + ** index with pSO->nExpr+2 columns. Build a key using pSO for the first |
| 150758 | + ** pSO->nExpr columns, then make sure all keys are unique by adding a |
| 150759 | + ** final OP_Sequence column. The last column is the record as a blob. |
| 150760 | + */ |
| 150761 | + case SRT_DistQueue: |
| 150762 | + case SRT_Queue: { |
| 150763 | + int nKey; |
| 150764 | + int r1, r2, r3, ii; |
| 150765 | + ExprList *pSO; |
| 150766 | + int iParm = pDest->iSDParm; |
| 150767 | + pSO = pDest->pOrderBy; |
| 150768 | + assert( pSO ); |
| 150769 | + nKey = pSO->nExpr; |
| 150770 | + r1 = sqlite3GetTempReg(pParse); |
| 150771 | + r2 = sqlite3GetTempRange(pParse, nKey+2); |
| 150772 | + r3 = r2+nKey+1; |
| 150773 | + |
| 150774 | +#if 0 /* <-- Why the next block of code is commented out: (tag-20260125-a) |
| 150775 | + ** |
| 150776 | + ** If the destination is DistQueue, then cursor (iParm+1) is open |
| 150777 | + ** on a second ephemeral index that holds all values previously |
| 150778 | + ** added to the queue. This code only runs during the setup phase |
| 150779 | + ** using the merge algorithm, and so the values here are already |
| 150780 | + ** guaranteed to be unique. |
| 150781 | + */ |
| 150782 | + if( pDest->eDest==SRT_DistQueue ){ |
| 150783 | + addrTest = sqlite3VdbeAddOp4Int(v, OP_Found, iParm+1, 0, |
| 150784 | + pIn->iSdst, pIn->nSdst); |
| 150785 | + VdbeCoverage(v); |
| 150786 | + } |
| 150787 | +#endif |
| 150788 | + sqlite3VdbeAddOp3(v, OP_MakeRecord, pIn->iSdst, pIn->nSdst, r3); |
| 150789 | + if( pDest->eDest==SRT_DistQueue ){ |
| 150790 | + sqlite3VdbeAddOp2(v, OP_IdxInsert, iParm+1, r3); |
| 150791 | + sqlite3VdbeChangeP5(v, OPFLAG_USESEEKRESULT); |
| 150792 | + } |
| 150793 | + for(ii=0; ii<nKey; ii++){ |
| 150794 | + sqlite3VdbeAddOp2(v, OP_SCopy, |
| 150795 | + pIn->iSdst + pSO->a[ii].u.x.iOrderByCol - 1, |
| 150796 | + r2+ii); |
| 150797 | + } |
| 150798 | + sqlite3VdbeAddOp2(v, OP_Sequence, iParm, r2+nKey); |
| 150799 | + sqlite3VdbeAddOp3(v, OP_MakeRecord, r2, nKey+2, r1); |
| 150800 | + sqlite3VdbeAddOp4Int(v, OP_IdxInsert, iParm, r1, r2, nKey+2); |
| 150801 | +#if 0 /* tag-20260125-a */ |
| 150802 | + if( addrTest ) sqlite3VdbeJumpHere(v, addrTest); |
| 150803 | +#endif |
| 150804 | + sqlite3ReleaseTempReg(pParse, r1); |
| 150805 | + sqlite3ReleaseTempRange(pParse, r2, nKey+2); |
| 150806 | + break; |
| 150807 | + } |
| 150808 | +#endif /* SQLITE_OMIT_CTE */ |
| 150809 | + |
| 150810 | + /* Ignore the output */ |
| 150811 | + case SRT_Discard: { |
| 150812 | + break; |
| 150813 | + } |
| 150811 | 150814 | |
| 150812 | 150815 | /* If none of the above, then the result destination must be |
| 150813 | | - ** SRT_Output. This routine is never called with any other |
| 150814 | | - ** destination other than the ones handled above or SRT_Output. |
| 150816 | + ** SRT_Output. |
| 150815 | 150817 | ** |
| 150816 | 150818 | ** For SRT_Output, results are stored in a sequence of registers. |
| 150817 | 150819 | ** Then the OP_ResultRow opcode is used to cause sqlite3_step() to |
| 150818 | 150820 | ** return the next row of result. |
| 150819 | 150821 | */ |
| | @@ -150837,12 +150839,13 @@ |
| 150837 | 150839 | |
| 150838 | 150840 | return addr; |
| 150839 | 150841 | } |
| 150840 | 150842 | |
| 150841 | 150843 | /* |
| 150842 | | -** Alternative compound select code generator for cases when there |
| 150843 | | -** is an ORDER BY clause. |
| 150844 | +** Generate code for a compound SELECT statement using a merge |
| 150845 | +** algorithm. The compound must have an ORDER BY clause for this |
| 150846 | +** to work. |
| 150844 | 150847 | ** |
| 150845 | 150848 | ** We assume a query of the following form: |
| 150846 | 150849 | ** |
| 150847 | 150850 | ** <selectA> <operator> <selectB> ORDER BY <orderbylist> |
| 150848 | 150851 | ** |
| | @@ -150855,11 +150858,11 @@ |
| 150855 | 150858 | ** outA: Move the output of the selectA coroutine into the output |
| 150856 | 150859 | ** of the compound query. |
| 150857 | 150860 | ** |
| 150858 | 150861 | ** outB: Move the output of the selectB coroutine into the output |
| 150859 | 150862 | ** of the compound query. (Only generated for UNION and |
| 150860 | | -** UNION ALL. EXCEPT and INSERTSECT never output a row that |
| 150863 | +** UNION ALL. EXCEPT and INTERSECT never output a row that |
| 150861 | 150864 | ** appears only in B.) |
| 150862 | 150865 | ** |
| 150863 | 150866 | ** AltB: Called when there is data from both coroutines and A<B. |
| 150864 | 150867 | ** |
| 150865 | 150868 | ** AeqB: Called when there is data from both coroutines and A==B. |
| | @@ -150919,14 +150922,14 @@ |
| 150919 | 150922 | ** End: ... |
| 150920 | 150923 | ** |
| 150921 | 150924 | ** We call AltB, AeqB, AgtB, EofA, and EofB "subroutines" but they are not |
| 150922 | 150925 | ** actually called using Gosub and they do not Return. EofA and EofB loop |
| 150923 | 150926 | ** until all data is exhausted then jump to the "end" label. AltB, AeqB, |
| 150924 | | -** and AgtB jump to either L2 or to one of EofA or EofB. |
| 150927 | +** and AgtB jump to either Cmpr or to one of EofA or EofB. |
| 150925 | 150928 | */ |
| 150926 | 150929 | #ifndef SQLITE_OMIT_COMPOUND_SELECT |
| 150927 | | -static int multiSelectOrderBy( |
| 150930 | +static int multiSelectByMerge( |
| 150928 | 150931 | Parse *pParse, /* Parsing context */ |
| 150929 | 150932 | Select *p, /* The right-most of SELECTs to be coded */ |
| 150930 | 150933 | SelectDest *pDest /* What to do with query results */ |
| 150931 | 150934 | ){ |
| 150932 | 150935 | int i, j; /* Loop counters */ |
| | @@ -151019,11 +151022,11 @@ |
| 151019 | 151022 | assert( pItem!=0 ); |
| 151020 | 151023 | assert( pItem->u.x.iOrderByCol>0 ); |
| 151021 | 151024 | assert( pItem->u.x.iOrderByCol<=p->pEList->nExpr ); |
| 151022 | 151025 | aPermute[i] = pItem->u.x.iOrderByCol - 1; |
| 151023 | 151026 | } |
| 151024 | | - pKeyMerge = multiSelectOrderByKeyInfo(pParse, p, 1); |
| 151027 | + pKeyMerge = multiSelectByMergeKeyInfo(pParse, p, 1); |
| 151025 | 151028 | }else{ |
| 151026 | 151029 | pKeyMerge = 0; |
| 151027 | 151030 | } |
| 151028 | 151031 | |
| 151029 | 151032 | /* Allocate a range of temporary registers and the KeyInfo needed |
| | @@ -152131,11 +152134,11 @@ |
| 152131 | 152134 | pItem->fg.jointype |= (jointype & JT_LTORJ); |
| 152132 | 152135 | memset(&pSubSrc->a[i], 0, sizeof(pSubSrc->a[i])); |
| 152133 | 152136 | } |
| 152134 | 152137 | pSubitem->fg.jointype |= jointype; |
| 152135 | 152138 | |
| 152136 | | - /* Now begin substituting subquery result set expressions for |
| 152139 | + /* Begin substituting subquery result set expressions for |
| 152137 | 152140 | ** references to the iParent in the outer query. |
| 152138 | 152141 | ** |
| 152139 | 152142 | ** Example: |
| 152140 | 152143 | ** |
| 152141 | 152144 | ** SELECT a+5, b*10 FROM (SELECT x*3 AS a, y+10 AS b FROM t1) WHERE a>b; |
| | @@ -152143,21 +152146,21 @@ |
| 152143 | 152146 | ** \_____________________ outer query ______________________________/ |
| 152144 | 152147 | ** |
| 152145 | 152148 | ** We look at every expression in the outer query and every place we see |
| 152146 | 152149 | ** "a" we substitute "x*3" and every place we see "b" we substitute "y+10". |
| 152147 | 152150 | */ |
| 152148 | | - if( pSub->pOrderBy && (pParent->selFlags & SF_NoopOrderBy)==0 ){ |
| 152151 | + if( pSub->pOrderBy ){ |
| 152149 | 152152 | /* At this point, any non-zero iOrderByCol values indicate that the |
| 152150 | 152153 | ** ORDER BY column expression is identical to the iOrderByCol'th |
| 152151 | 152154 | ** expression returned by SELECT statement pSub. Since these values |
| 152152 | 152155 | ** do not necessarily correspond to columns in SELECT statement pParent, |
| 152153 | 152156 | ** zero them before transferring the ORDER BY clause. |
| 152154 | 152157 | ** |
| 152155 | 152158 | ** Not doing this may cause an error if a subsequent call to this |
| 152156 | | - ** function attempts to flatten a compound sub-query into pParent |
| 152157 | | - ** (the only way this can happen is if the compound sub-query is |
| 152158 | | - ** currently part of pSub->pSrc). See ticket [d11a6e908f]. */ |
| 152159 | + ** function attempts to flatten a compound sub-query into pParent. |
| 152160 | + ** See ticket [d11a6e908f]. |
| 152161 | + */ |
| 152159 | 152162 | ExprList *pOrderBy = pSub->pOrderBy; |
| 152160 | 152163 | for(i=0; i<pOrderBy->nExpr; i++){ |
| 152161 | 152164 | pOrderBy->a[i].u.x.iOrderByCol = 0; |
| 152162 | 152165 | } |
| 152163 | 152166 | assert( pParent->pOrderBy==0 ); |
| | @@ -153005,18 +153008,18 @@ |
| 153005 | 153008 | ** These are rewritten as a subquery: |
| 153006 | 153009 | ** |
| 153007 | 153010 | ** SELECT * FROM (SELECT ... FROM t1 EXCEPT SELECT ... FROM t2) |
| 153008 | 153011 | ** ORDER BY ... COLLATE ... |
| 153009 | 153012 | ** |
| 153010 | | -** This transformation is necessary because the multiSelectOrderBy() routine |
| 153013 | +** This transformation is necessary because the multiSelectByMerge() routine |
| 153011 | 153014 | ** above that generates the code for a compound SELECT with an ORDER BY clause |
| 153012 | 153015 | ** uses a merge algorithm that requires the same collating sequence on the |
| 153013 | 153016 | ** result columns as on the ORDER BY clause. See ticket |
| 153014 | 153017 | ** http://sqlite.org/src/info/6709574d2a |
| 153015 | 153018 | ** |
| 153016 | 153019 | ** This transformation is only needed for EXCEPT, INTERSECT, and UNION. |
| 153017 | | -** The UNION ALL operator works fine with multiSelectOrderBy() even when |
| 153020 | +** The UNION ALL operator works fine with multiSelectByMerge() even when |
| 153018 | 153021 | ** there are COLLATE terms in the ORDER BY. |
| 153019 | 153022 | */ |
| 153020 | 153023 | static int convertCompoundSelectToSubquery(Walker *pWalker, Select *p){ |
| 153021 | 153024 | int i; |
| 153022 | 153025 | Select *pNew; |
| | @@ -154862,11 +154865,10 @@ |
| 154862 | 154865 | pWhere->op = TK_INTEGER; |
| 154863 | 154866 | pWhere->u.iValue = 1; |
| 154864 | 154867 | ExprSetProperty(pWhere, EP_IntValue); |
| 154865 | 154868 | assert( p->pWhere!=0 ); |
| 154866 | 154869 | pSub->pSrc->a[0].fg.fromExists = 1; |
| 154867 | | - pSub->pSrc->a[0].fg.jointype |= JT_CROSS; |
| 154868 | 154870 | p->pSrc = sqlite3SrcListAppendList(pParse, p->pSrc, pSub->pSrc); |
| 154869 | 154871 | if( pSubWhere ){ |
| 154870 | 154872 | p->pWhere = sqlite3PExpr(pParse, TK_AND, p->pWhere, pSubWhere); |
| 154871 | 154873 | pSub->pWhere = 0; |
| 154872 | 154874 | } |
| | @@ -155111,12 +155113,11 @@ |
| 155111 | 155113 | assert( p->pOrderBy==0 || pDest->eDest!=SRT_DistFifo ); |
| 155112 | 155114 | assert( p->pOrderBy==0 || pDest->eDest!=SRT_Fifo ); |
| 155113 | 155115 | assert( p->pOrderBy==0 || pDest->eDest!=SRT_DistQueue ); |
| 155114 | 155116 | assert( p->pOrderBy==0 || pDest->eDest!=SRT_Queue ); |
| 155115 | 155117 | if( IgnorableDistinct(pDest) ){ |
| 155116 | | - assert(pDest->eDest==SRT_Exists || pDest->eDest==SRT_Union || |
| 155117 | | - pDest->eDest==SRT_Except || pDest->eDest==SRT_Discard || |
| 155118 | + assert(pDest->eDest==SRT_Exists || pDest->eDest==SRT_Discard || |
| 155118 | 155119 | pDest->eDest==SRT_DistQueue || pDest->eDest==SRT_DistFifo ); |
| 155119 | 155120 | /* All of these destinations are also able to ignore the ORDER BY clause */ |
| 155120 | 155121 | if( p->pOrderBy ){ |
| 155121 | 155122 | #if TREETRACE_ENABLED |
| 155122 | 155123 | TREETRACE(0x800,pParse,p, ("dropping superfluous ORDER BY:\n")); |
| | @@ -155128,11 +155129,10 @@ |
| 155128 | 155129 | p->pOrderBy); |
| 155129 | 155130 | testcase( pParse->earlyCleanup ); |
| 155130 | 155131 | p->pOrderBy = 0; |
| 155131 | 155132 | } |
| 155132 | 155133 | p->selFlags &= ~(u32)SF_Distinct; |
| 155133 | | - p->selFlags |= SF_NoopOrderBy; |
| 155134 | 155134 | } |
| 155135 | 155135 | sqlite3SelectPrep(pParse, p, 0); |
| 155136 | 155136 | if( pParse->nErr ){ |
| 155137 | 155137 | goto select_end; |
| 155138 | 155138 | } |
| | @@ -165904,20 +165904,26 @@ |
| 165904 | 165904 | u16 eOp = pOne->eOperator | pTwo->eOperator; |
| 165905 | 165905 | sqlite3 *db; /* Database connection (for malloc) */ |
| 165906 | 165906 | Expr *pNew; /* New virtual expression */ |
| 165907 | 165907 | int op; /* Operator for the combined expression */ |
| 165908 | 165908 | int idxNew; /* Index in pWC of the next virtual term */ |
| 165909 | + Expr *pA, *pB; /* Expressions associated with pOne and pTwo */ |
| 165909 | 165910 | |
| 165910 | 165911 | if( (pOne->wtFlags | pTwo->wtFlags) & TERM_VNULL ) return; |
| 165911 | 165912 | if( (pOne->eOperator & (WO_EQ|WO_LT|WO_LE|WO_GT|WO_GE))==0 ) return; |
| 165912 | 165913 | if( (pTwo->eOperator & (WO_EQ|WO_LT|WO_LE|WO_GT|WO_GE))==0 ) return; |
| 165913 | 165914 | if( (eOp & (WO_EQ|WO_LT|WO_LE))!=eOp |
| 165914 | 165915 | && (eOp & (WO_EQ|WO_GT|WO_GE))!=eOp ) return; |
| 165915 | | - assert( pOne->pExpr->pLeft!=0 && pOne->pExpr->pRight!=0 ); |
| 165916 | | - assert( pTwo->pExpr->pLeft!=0 && pTwo->pExpr->pRight!=0 ); |
| 165917 | | - if( sqlite3ExprCompare(0,pOne->pExpr->pLeft, pTwo->pExpr->pLeft, -1) ) return; |
| 165918 | | - if( sqlite3ExprCompare(0,pOne->pExpr->pRight, pTwo->pExpr->pRight,-1) )return; |
| 165916 | + pA = pOne->pExpr; |
| 165917 | + pB = pTwo->pExpr; |
| 165918 | + assert( pA->pLeft!=0 && pA->pRight!=0 ); |
| 165919 | + assert( pB->pLeft!=0 && pB->pRight!=0 ); |
| 165920 | + if( sqlite3ExprCompare(0,pA->pLeft, pB->pLeft, -1) ) return; |
| 165921 | + if( sqlite3ExprCompare(0,pA->pRight, pB->pRight,-1) ) return; |
| 165922 | + if( ExprHasProperty(pA,EP_Commuted)!=ExprHasProperty(pB,EP_Commuted) ){ |
| 165923 | + return; |
| 165924 | + } |
| 165919 | 165925 | /* If we reach this point, it means the two subterms can be combined */ |
| 165920 | 165926 | if( (eOp & (eOp-1))!=0 ){ |
| 165921 | 165927 | if( eOp & (WO_LT|WO_LE) ){ |
| 165922 | 165928 | eOp = WO_LE; |
| 165923 | 165929 | }else{ |
| | @@ -165924,11 +165930,11 @@ |
| 165924 | 165930 | assert( eOp & (WO_GT|WO_GE) ); |
| 165925 | 165931 | eOp = WO_GE; |
| 165926 | 165932 | } |
| 165927 | 165933 | } |
| 165928 | 165934 | db = pWC->pWInfo->pParse->db; |
| 165929 | | - pNew = sqlite3ExprDup(db, pOne->pExpr, 0); |
| 165935 | + pNew = sqlite3ExprDup(db, pA, 0); |
| 165930 | 165936 | if( pNew==0 ) return; |
| 165931 | 165937 | for(op=TK_EQ; eOp!=(WO_EQ<<(op-TK_EQ)); op++){ assert( op<TK_GE ); } |
| 165932 | 165938 | pNew->op = op; |
| 165933 | 165939 | idxNew = whereClauseInsert(pWC, pNew, TERM_VIRTUAL|TERM_DYNAMIC); |
| 165934 | 165940 | exprAnalyze(pSrc, pWC, idxNew); |
| | @@ -170766,10 +170772,11 @@ |
| 170766 | 170772 | |
| 170767 | 170773 | nOutUnadjusted = pNew->nOut; |
| 170768 | 170774 | pNew->rRun += nInMul + nIn; |
| 170769 | 170775 | pNew->nOut += nInMul + nIn; |
| 170770 | 170776 | whereLoopOutputAdjust(pBuilder->pWC, pNew, rSize); |
| 170777 | + if( pSrc->fg.fromExists ) pNew->nOut = 0; |
| 170771 | 170778 | rc = whereLoopInsert(pBuilder, pNew); |
| 170772 | 170779 | |
| 170773 | 170780 | if( pNew->wsFlags & WHERE_COLUMN_RANGE ){ |
| 170774 | 170781 | pNew->nOut = saved_nOut; |
| 170775 | 170782 | }else{ |
| | @@ -171362,10 +171369,12 @@ |
| 171362 | 171369 | ApplyCostMultiplier(pNew->rRun, pTab->costMult); |
| 171363 | 171370 | whereLoopOutputAdjust(pWC, pNew, rSize); |
| 171364 | 171371 | if( pSrc->fg.isSubquery ){ |
| 171365 | 171372 | if( pSrc->fg.viaCoroutine ) pNew->wsFlags |= WHERE_COROUTINE; |
| 171366 | 171373 | pNew->u.btree.pOrderBy = pSrc->u4.pSubq->pSelect->pOrderBy; |
| 171374 | + }else if( pSrc->fg.fromExists ){ |
| 171375 | + pNew->nOut = 0; |
| 171367 | 171376 | } |
| 171368 | 171377 | rc = whereLoopInsert(pBuilder, pNew); |
| 171369 | 171378 | pNew->nOut = rSize; |
| 171370 | 171379 | if( rc ) break; |
| 171371 | 171380 | }else{ |
| | @@ -171464,10 +171473,11 @@ |
| 171464 | 171473 | /* Do not do an SCAN of a index-on-expression in a RIGHT JOIN |
| 171465 | 171474 | ** because the cursor used to access the index might not be |
| 171466 | 171475 | ** positioned to the correct row during the right-join no-match |
| 171467 | 171476 | ** loop. */ |
| 171468 | 171477 | }else{ |
| 171478 | + if( pSrc->fg.fromExists ) pNew->nOut = 0; |
| 171469 | 171479 | rc = whereLoopInsert(pBuilder, pNew); |
| 171470 | 171480 | } |
| 171471 | 171481 | pNew->nOut = rSize; |
| 171472 | 171482 | if( rc ) break; |
| 171473 | 171483 | } |
| | @@ -172161,10 +172171,21 @@ |
| 172161 | 172171 | ** is itself on the left side of a RIGHT JOIN. |
| 172162 | 172172 | */ |
| 172163 | 172173 | if( pItem->fg.jointype & JT_LTORJ ) hasRightJoin = 1; |
| 172164 | 172174 | mPrereq |= mPrior; |
| 172165 | 172175 | bFirstPastRJ = (pItem->fg.jointype & JT_RIGHT)!=0; |
| 172176 | + }else if( pItem->fg.fromExists ){ |
| 172177 | + /* joins that result from the EXISTS-to-JOIN optimization should not |
| 172178 | + ** be moved to the left of any of their dependencies */ |
| 172179 | + WhereClause *pWC = &pWInfo->sWC; |
| 172180 | + WhereTerm *pTerm; |
| 172181 | + int i; |
| 172182 | + for(i=pWC->nBase, pTerm=pWC->a; i>0; i--, pTerm++){ |
| 172183 | + if( (pNew->maskSelf & pTerm->prereqAll)!=0 ){ |
| 172184 | + mPrereq |= (pTerm->prereqAll & (pNew->maskSelf-1)); |
| 172185 | + } |
| 172186 | + } |
| 172166 | 172187 | }else if( !hasRightJoin ){ |
| 172167 | 172188 | mPrereq = 0; |
| 172168 | 172189 | } |
| 172169 | 172190 | #ifndef SQLITE_OMIT_VIRTUALTABLE |
| 172170 | 172191 | if( IsVirtual(pItem->pSTab) ){ |
| | @@ -174713,26 +174734,31 @@ |
| 174713 | 174734 | VdbeCoverageIf(v, op==OP_SeekGT); |
| 174714 | 174735 | sqlite3VdbeAddOp2(v, OP_Goto, 1, pLevel->p2); |
| 174715 | 174736 | } |
| 174716 | 174737 | #endif /* SQLITE_DISABLE_SKIPAHEAD_DISTINCT */ |
| 174717 | 174738 | } |
| 174718 | | - if( pTabList->a[pLevel->iFrom].fg.fromExists && i==pWInfo->nLevel-1 ){ |
| 174719 | | - /* If the EXISTS-to-JOIN optimization was applied, then the EXISTS |
| 174720 | | - ** loop(s) will be the inner-most loops of the join. There might be |
| 174721 | | - ** multiple EXISTS loops, but they will all be nested, and the join |
| 174722 | | - ** order will not have been changed by the query planner. If the |
| 174723 | | - ** inner-most EXISTS loop sees a single successful row, it should |
| 174724 | | - ** break out of *all* EXISTS loops. But only the inner-most of the |
| 174725 | | - ** nested EXISTS loops should do this breakout. */ |
| 174739 | + if( pTabList->a[pLevel->iFrom].fg.fromExists |
| 174740 | + && (i==pWInfo->nLevel-1 |
| 174741 | + || pTabList->a[pWInfo->a[i+1].iFrom].fg.fromExists==0) |
| 174742 | + ){ |
| 174743 | + /* This is an EXISTS-to-JOIN optimization which is either the |
| 174744 | + ** inner-most loop, or the inner-most of a group of nested |
| 174745 | + ** EXISTS-to-JOIN optimization loops. If this loop sees a successful |
| 174746 | + ** row, it should break out of itself as well as other EXISTS-to-JOIN |
| 174747 | + ** loops in which is is directly nested. */ |
| 174726 | 174748 | int nOuter = 0; /* Nr of outer EXISTS that this one is nested within */ |
| 174727 | 174749 | while( nOuter<i ){ |
| 174728 | 174750 | if( !pTabList->a[pLevel[-nOuter-1].iFrom].fg.fromExists ) break; |
| 174729 | 174751 | nOuter++; |
| 174730 | 174752 | } |
| 174731 | 174753 | testcase( nOuter>0 ); |
| 174732 | 174754 | sqlite3VdbeAddOp2(v, OP_Goto, 0, pLevel[-nOuter].addrBrk); |
| 174733 | | - VdbeComment((v, "EXISTS break")); |
| 174755 | + if( nOuter ){ |
| 174756 | + VdbeComment((v, "EXISTS break %d..%d", i-nOuter, i)); |
| 174757 | + }else{ |
| 174758 | + VdbeComment((v, "EXISTS break %d", i)); |
| 174759 | + } |
| 174734 | 174760 | } |
| 174735 | 174761 | sqlite3VdbeResolveLabel(v, pLevel->addrCont); |
| 174736 | 174762 | if( pLevel->op!=OP_Noop ){ |
| 174737 | 174763 | sqlite3VdbeAddOp3(v, pLevel->op, pLevel->p1, pLevel->p2, pLevel->p3); |
| 174738 | 174764 | sqlite3VdbeChangeP5(v, pLevel->p5); |
| | @@ -189501,10 +189527,16 @@ |
| 189501 | 189527 | /* |
| 189502 | 189528 | ** Find existing client data. |
| 189503 | 189529 | */ |
| 189504 | 189530 | SQLITE_API void *sqlite3_get_clientdata(sqlite3 *db, const char *zName){ |
| 189505 | 189531 | DbClientData *p; |
| 189532 | +#ifdef SQLITE_ENABLE_API_ARMOR |
| 189533 | + if( !zName || !sqlite3SafetyCheckOk(db) ){ |
| 189534 | + (void)SQLITE_MISUSE_BKPT; |
| 189535 | + return 0; |
| 189536 | + } |
| 189537 | +#endif |
| 189506 | 189538 | sqlite3_mutex_enter(db->mutex); |
| 189507 | 189539 | for(p=db->pDbData; p; p=p->pNext){ |
| 189508 | 189540 | if( strcmp(p->zName, zName)==0 ){ |
| 189509 | 189541 | void *pResult = p->pData; |
| 189510 | 189542 | sqlite3_mutex_leave(db->mutex); |
| | @@ -211254,11 +211286,14 @@ |
| 211254 | 211286 | */ |
| 211255 | 211287 | #define JSON_JSON 0x01 /* Result is always JSON */ |
| 211256 | 211288 | #define JSON_SQL 0x02 /* Result is always SQL */ |
| 211257 | 211289 | #define JSON_ABPATH 0x03 /* Allow abbreviated JSON path specs */ |
| 211258 | 211290 | #define JSON_ISSET 0x04 /* json_set(), not json_insert() */ |
| 211259 | | -#define JSON_BLOB 0x08 /* Use the BLOB output format */ |
| 211291 | +#define JSON_AINS 0x08 /* json_array_insert(), not json_insert() */ |
| 211292 | +#define JSON_BLOB 0x10 /* Use the BLOB output format */ |
| 211293 | + |
| 211294 | +#define JSON_INSERT_TYPE(X) (((X)&0xC)>>2) |
| 211260 | 211295 | |
| 211261 | 211296 | |
| 211262 | 211297 | /* A parsed JSON value. Lifecycle: |
| 211263 | 211298 | ** |
| 211264 | 211299 | ** 1. JSON comes in and is parsed into a JSONB value in aBlob. The |
| | @@ -211300,10 +211335,11 @@ |
| 211300 | 211335 | /* Allowed values for JsonParse.eEdit */ |
| 211301 | 211336 | #define JEDIT_DEL 1 /* Delete if exists */ |
| 211302 | 211337 | #define JEDIT_REPL 2 /* Overwrite if exists */ |
| 211303 | 211338 | #define JEDIT_INS 3 /* Insert if not exists */ |
| 211304 | 211339 | #define JEDIT_SET 4 /* Insert or overwrite */ |
| 211340 | +#define JEDIT_AINS 5 /* array_insert() */ |
| 211305 | 211341 | |
| 211306 | 211342 | /* |
| 211307 | 211343 | ** Maximum nesting depth of JSON for this implementation. |
| 211308 | 211344 | ** |
| 211309 | 211345 | ** This limit is needed to avoid a stack overflow in the recursive |
| | @@ -213796,11 +213832,12 @@ |
| 213796 | 213832 | /* |
| 213797 | 213833 | ** Error returns from jsonLookupStep() |
| 213798 | 213834 | */ |
| 213799 | 213835 | #define JSON_LOOKUP_ERROR 0xffffffff |
| 213800 | 213836 | #define JSON_LOOKUP_NOTFOUND 0xfffffffe |
| 213801 | | -#define JSON_LOOKUP_PATHERROR 0xfffffffd |
| 213837 | +#define JSON_LOOKUP_NOTARRAY 0xfffffffd |
| 213838 | +#define JSON_LOOKUP_PATHERROR 0xfffffffc |
| 213802 | 213839 | #define JSON_LOOKUP_ISERROR(x) ((x)>=JSON_LOOKUP_PATHERROR) |
| 213803 | 213840 | |
| 213804 | 213841 | /* Forward declaration */ |
| 213805 | 213842 | static u32 jsonLookupStep(JsonParse*,u32,const char*,u32); |
| 213806 | 213843 | |
| | @@ -213825,11 +213862,11 @@ |
| 213825 | 213862 | ** using the substructure. |
| 213826 | 213863 | */ |
| 213827 | 213864 | static u32 jsonCreateEditSubstructure( |
| 213828 | 213865 | JsonParse *pParse, /* The original JSONB that is being edited */ |
| 213829 | 213866 | JsonParse *pIns, /* Populate this with the blob data to insert */ |
| 213830 | | - const char *zTail /* Tail of the path that determins substructure */ |
| 213867 | + const char *zTail /* Tail of the path that determines substructure */ |
| 213831 | 213868 | ){ |
| 213832 | 213869 | static const u8 emptyObject[] = { JSONB_ARRAY, JSONB_OBJECT }; |
| 213833 | 213870 | int rc; |
| 213834 | 213871 | memset(pIns, 0, sizeof(*pIns)); |
| 213835 | 213872 | pIns->db = pParse->db; |
| | @@ -213860,13 +213897,13 @@ |
| 213860 | 213897 | ** label, before returning. |
| 213861 | 213898 | ** |
| 213862 | 213899 | ** Return one of the JSON_LOOKUP error codes if problems are seen. |
| 213863 | 213900 | ** |
| 213864 | 213901 | ** This routine will also modify the blob. If pParse->eEdit is one of |
| 213865 | | -** JEDIT_DEL, JEDIT_REPL, JEDIT_INS, or JEDIT_SET, then changes might be |
| 213866 | | -** made to the selected value. If an edit is performed, then the return |
| 213867 | | -** value does not necessarily point to the select element. If an edit |
| 213902 | +** JEDIT_DEL, JEDIT_REPL, JEDIT_INS, JEDIT_SET, or JEDIT_AINS, then changes |
| 213903 | +** might be made to the selected value. If an edit is performed, then the |
| 213904 | +** return value does not necessarily point to the select element. If an edit |
| 213868 | 213905 | ** is performed, the return value is only useful for detecting error |
| 213869 | 213906 | ** conditions. |
| 213870 | 213907 | */ |
| 213871 | 213908 | static u32 jsonLookupStep( |
| 213872 | 213909 | JsonParse *pParse, /* The JSON to search */ |
| | @@ -213888,10 +213925,17 @@ |
| 213888 | 213925 | iRoot = iLabel; |
| 213889 | 213926 | } |
| 213890 | 213927 | jsonBlobEdit(pParse, iRoot, sz, 0, 0); |
| 213891 | 213928 | }else if( pParse->eEdit==JEDIT_INS ){ |
| 213892 | 213929 | /* Already exists, so json_insert() is a no-op */ |
| 213930 | + }else if( pParse->eEdit==JEDIT_AINS ){ |
| 213931 | + /* json_array_insert() */ |
| 213932 | + if( zPath[-1]!=']' ){ |
| 213933 | + return JSON_LOOKUP_NOTARRAY; |
| 213934 | + }else{ |
| 213935 | + jsonBlobEdit(pParse, iRoot, 0, pParse->aIns, pParse->nIns); |
| 213936 | + } |
| 213893 | 213937 | }else{ |
| 213894 | 213938 | /* json_set() or json_replace() */ |
| 213895 | 213939 | jsonBlobEdit(pParse, iRoot, sz, pParse->aIns, pParse->nIns); |
| 213896 | 213940 | } |
| 213897 | 213941 | } |
| | @@ -213959,10 +214003,14 @@ |
| 213959 | 214003 | u32 nIns; /* Total bytes to insert (label+value) */ |
| 213960 | 214004 | JsonParse v; /* BLOB encoding of the value to be inserted */ |
| 213961 | 214005 | JsonParse ix; /* Header of the label to be inserted */ |
| 213962 | 214006 | testcase( pParse->eEdit==JEDIT_INS ); |
| 213963 | 214007 | testcase( pParse->eEdit==JEDIT_SET ); |
| 214008 | + testcase( pParse->eEdit==JEDIT_AINS ); |
| 214009 | + if( pParse->eEdit==JEDIT_AINS && sqlite3_strglob("*]",&zPath[i])!=0 ){ |
| 214010 | + return JSON_LOOKUP_NOTARRAY; |
| 214011 | + } |
| 213964 | 214012 | memset(&ix, 0, sizeof(ix)); |
| 213965 | 214013 | ix.db = pParse->db; |
| 213966 | 214014 | jsonBlobAppendNode(&ix, rawKey?JSONB_TEXTRAW:JSONB_TEXT5, nKey, 0); |
| 213967 | 214015 | pParse->oom |= ix.oom; |
| 213968 | 214016 | rc = jsonCreateEditSubstructure(pParse, &v, &zPath[i]); |
| | @@ -214034,10 +214082,11 @@ |
| 214034 | 214082 | if( j>iEnd ) return JSON_LOOKUP_ERROR; |
| 214035 | 214083 | if( k>0 ) return JSON_LOOKUP_NOTFOUND; |
| 214036 | 214084 | if( pParse->eEdit>=JEDIT_INS ){ |
| 214037 | 214085 | JsonParse v; |
| 214038 | 214086 | testcase( pParse->eEdit==JEDIT_INS ); |
| 214087 | + testcase( pParse->eEdit==JEDIT_AINS ); |
| 214039 | 214088 | testcase( pParse->eEdit==JEDIT_SET ); |
| 214040 | 214089 | rc = jsonCreateEditSubstructure(pParse, &v, &zPath[i+1]); |
| 214041 | 214090 | if( !JSON_LOOKUP_ISERROR(rc) |
| 214042 | 214091 | && jsonBlobMakeEditable(pParse, v.nBlob) |
| 214043 | 214092 | ){ |
| | @@ -214358,13 +214407,19 @@ |
| 214358 | 214407 | ** If ctx is not NULL then push the error message into ctx and return NULL. |
| 214359 | 214408 | ** If ctx is NULL, then return the text of the error message. |
| 214360 | 214409 | */ |
| 214361 | 214410 | static char *jsonBadPathError( |
| 214362 | 214411 | sqlite3_context *ctx, /* The function call containing the error */ |
| 214363 | | - const char *zPath /* The path with the problem */ |
| 214412 | + const char *zPath, /* The path with the problem */ |
| 214413 | + int rc /* Maybe JSON_LOOKUP_NOTARRAY */ |
| 214364 | 214414 | ){ |
| 214365 | | - char *zMsg = sqlite3_mprintf("bad JSON path: %Q", zPath); |
| 214415 | + char *zMsg; |
| 214416 | + if( rc==(int)JSON_LOOKUP_NOTARRAY ){ |
| 214417 | + zMsg = sqlite3_mprintf("not an array element: %Q", zPath); |
| 214418 | + }else{ |
| 214419 | + zMsg = sqlite3_mprintf("bad JSON path: %Q", zPath); |
| 214420 | + } |
| 214366 | 214421 | if( ctx==0 ) return zMsg; |
| 214367 | 214422 | if( zMsg ){ |
| 214368 | 214423 | sqlite3_result_error(ctx, zMsg, -1); |
| 214369 | 214424 | sqlite3_free(zMsg); |
| 214370 | 214425 | }else{ |
| | @@ -214377,17 +214432,17 @@ |
| 214377 | 214432 | ** arguments come in pairs where each pair contains a JSON path and |
| 214378 | 214433 | ** content to insert or set at that patch. Do the updates |
| 214379 | 214434 | ** and return the result. |
| 214380 | 214435 | ** |
| 214381 | 214436 | ** The specific operation is determined by eEdit, which can be one |
| 214382 | | -** of JEDIT_INS, JEDIT_REPL, or JEDIT_SET. |
| 214437 | +** of JEDIT_INS, JEDIT_REPL, JEDIT_SET, or JEDIT_AINS. |
| 214383 | 214438 | */ |
| 214384 | 214439 | static void jsonInsertIntoBlob( |
| 214385 | 214440 | sqlite3_context *ctx, |
| 214386 | 214441 | int argc, |
| 214387 | 214442 | sqlite3_value **argv, |
| 214388 | | - int eEdit /* JEDIT_INS, JEDIT_REPL, or JEDIT_SET */ |
| 214443 | + int eEdit /* JEDIT_INS, JEDIT_REPL, JEDIT_SET, JEDIT_AINS */ |
| 214389 | 214444 | ){ |
| 214390 | 214445 | int i; |
| 214391 | 214446 | u32 rc = 0; |
| 214392 | 214447 | const char *zPath = 0; |
| 214393 | 214448 | int flgs; |
| | @@ -214435,11 +214490,11 @@ |
| 214435 | 214490 | jsonInsertIntoBlob_patherror: |
| 214436 | 214491 | jsonParseFree(p); |
| 214437 | 214492 | if( rc==JSON_LOOKUP_ERROR ){ |
| 214438 | 214493 | sqlite3_result_error(ctx, "malformed JSON", -1); |
| 214439 | 214494 | }else{ |
| 214440 | | - jsonBadPathError(ctx, zPath); |
| 214495 | + jsonBadPathError(ctx, zPath, rc); |
| 214441 | 214496 | } |
| 214442 | 214497 | return; |
| 214443 | 214498 | } |
| 214444 | 214499 | |
| 214445 | 214500 | /* |
| | @@ -214877,11 +214932,11 @@ |
| 214877 | 214932 | i = jsonLookupStep(p, 0, zPath[0]=='$' ? zPath+1 : "@", 0); |
| 214878 | 214933 | if( JSON_LOOKUP_ISERROR(i) ){ |
| 214879 | 214934 | if( i==JSON_LOOKUP_NOTFOUND ){ |
| 214880 | 214935 | /* no-op */ |
| 214881 | 214936 | }else if( i==JSON_LOOKUP_PATHERROR ){ |
| 214882 | | - jsonBadPathError(ctx, zPath); |
| 214937 | + jsonBadPathError(ctx, zPath, 0); |
| 214883 | 214938 | }else{ |
| 214884 | 214939 | sqlite3_result_error(ctx, "malformed JSON", -1); |
| 214885 | 214940 | } |
| 214886 | 214941 | eErr = 1; |
| 214887 | 214942 | i = 0; |
| | @@ -214982,11 +215037,11 @@ |
| 214982 | 215037 | } |
| 214983 | 215038 | jsonStringTerminate(&jx); |
| 214984 | 215039 | j = jsonLookupStep(p, 0, jx.zBuf, 0); |
| 214985 | 215040 | jsonStringReset(&jx); |
| 214986 | 215041 | }else{ |
| 214987 | | - jsonBadPathError(ctx, zPath); |
| 215042 | + jsonBadPathError(ctx, zPath, 0); |
| 214988 | 215043 | goto json_extract_error; |
| 214989 | 215044 | } |
| 214990 | 215045 | if( j<p->nBlob ){ |
| 214991 | 215046 | if( argc==2 ){ |
| 214992 | 215047 | if( flags & JSON_JSON ){ |
| | @@ -215017,11 +215072,11 @@ |
| 215017 | 215072 | } |
| 215018 | 215073 | }else if( j==JSON_LOOKUP_ERROR ){ |
| 215019 | 215074 | sqlite3_result_error(ctx, "malformed JSON", -1); |
| 215020 | 215075 | goto json_extract_error; |
| 215021 | 215076 | }else{ |
| 215022 | | - jsonBadPathError(ctx, zPath); |
| 215077 | + jsonBadPathError(ctx, zPath, 0); |
| 215023 | 215078 | goto json_extract_error; |
| 215024 | 215079 | } |
| 215025 | 215080 | } |
| 215026 | 215081 | if( argc>2 ){ |
| 215027 | 215082 | jsonAppendChar(&jx, ']'); |
| | @@ -215346,11 +215401,11 @@ |
| 215346 | 215401 | rc = jsonLookupStep(p, 0, zPath+1, 0); |
| 215347 | 215402 | if( JSON_LOOKUP_ISERROR(rc) ){ |
| 215348 | 215403 | if( rc==JSON_LOOKUP_NOTFOUND ){ |
| 215349 | 215404 | continue; /* No-op */ |
| 215350 | 215405 | }else if( rc==JSON_LOOKUP_PATHERROR ){ |
| 215351 | | - jsonBadPathError(ctx, zPath); |
| 215406 | + jsonBadPathError(ctx, zPath, rc); |
| 215352 | 215407 | }else{ |
| 215353 | 215408 | sqlite3_result_error(ctx, "malformed JSON", -1); |
| 215354 | 215409 | } |
| 215355 | 215410 | goto json_remove_done; |
| 215356 | 215411 | } |
| | @@ -215358,11 +215413,11 @@ |
| 215358 | 215413 | jsonReturnParse(ctx, p); |
| 215359 | 215414 | jsonParseFree(p); |
| 215360 | 215415 | return; |
| 215361 | 215416 | |
| 215362 | 215417 | json_remove_patherror: |
| 215363 | | - jsonBadPathError(ctx, zPath); |
| 215418 | + jsonBadPathError(ctx, zPath, 0); |
| 215364 | 215419 | |
| 215365 | 215420 | json_remove_done: |
| 215366 | 215421 | jsonParseFree(p); |
| 215367 | 215422 | return; |
| 215368 | 215423 | } |
| | @@ -215402,20 +215457,22 @@ |
| 215402 | 215457 | static void jsonSetFunc( |
| 215403 | 215458 | sqlite3_context *ctx, |
| 215404 | 215459 | int argc, |
| 215405 | 215460 | sqlite3_value **argv |
| 215406 | 215461 | ){ |
| 215407 | | - |
| 215408 | 215462 | int flags = SQLITE_PTR_TO_INT(sqlite3_user_data(ctx)); |
| 215409 | | - int bIsSet = (flags&JSON_ISSET)!=0; |
| 215463 | + int eInsType = JSON_INSERT_TYPE(flags); |
| 215464 | + static const char *azInsType[] = { "insert", "set", "array_insert" }; |
| 215465 | + static const u8 aEditType[] = { JEDIT_INS, JEDIT_SET, JEDIT_AINS }; |
| 215410 | 215466 | |
| 215411 | 215467 | if( argc<1 ) return; |
| 215468 | + assert( eInsType>=0 && eInsType<=2 ); |
| 215412 | 215469 | if( (argc&1)==0 ) { |
| 215413 | | - jsonWrongNumArgs(ctx, bIsSet ? "set" : "insert"); |
| 215470 | + jsonWrongNumArgs(ctx, azInsType[eInsType]); |
| 215414 | 215471 | return; |
| 215415 | 215472 | } |
| 215416 | | - jsonInsertIntoBlob(ctx, argc, argv, bIsSet ? JEDIT_SET : JEDIT_INS); |
| 215473 | + jsonInsertIntoBlob(ctx, argc, argv, aEditType[eInsType]); |
| 215417 | 215474 | } |
| 215418 | 215475 | |
| 215419 | 215476 | /* |
| 215420 | 215477 | ** json_type(JSON) |
| 215421 | 215478 | ** json_type(JSON, PATH) |
| | @@ -215436,19 +215493,19 @@ |
| 215436 | 215493 | if( p==0 ) return; |
| 215437 | 215494 | if( argc==2 ){ |
| 215438 | 215495 | zPath = (const char*)sqlite3_value_text(argv[1]); |
| 215439 | 215496 | if( zPath==0 ) goto json_type_done; |
| 215440 | 215497 | if( zPath[0]!='$' ){ |
| 215441 | | - jsonBadPathError(ctx, zPath); |
| 215498 | + jsonBadPathError(ctx, zPath, 0); |
| 215442 | 215499 | goto json_type_done; |
| 215443 | 215500 | } |
| 215444 | 215501 | i = jsonLookupStep(p, 0, zPath+1, 0); |
| 215445 | 215502 | if( JSON_LOOKUP_ISERROR(i) ){ |
| 215446 | 215503 | if( i==JSON_LOOKUP_NOTFOUND ){ |
| 215447 | 215504 | /* no-op */ |
| 215448 | 215505 | }else if( i==JSON_LOOKUP_PATHERROR ){ |
| 215449 | | - jsonBadPathError(ctx, zPath); |
| 215506 | + jsonBadPathError(ctx, zPath, 0); |
| 215450 | 215507 | }else{ |
| 215451 | 215508 | sqlite3_result_error(ctx, "malformed JSON", -1); |
| 215452 | 215509 | } |
| 215453 | 215510 | goto json_type_done; |
| 215454 | 215511 | } |
| | @@ -215700,16 +215757,15 @@ |
| 215700 | 215757 | jsonAppendSqlValue(pStr, argv[0]); |
| 215701 | 215758 | } |
| 215702 | 215759 | } |
| 215703 | 215760 | static void jsonArrayCompute(sqlite3_context *ctx, int isFinal){ |
| 215704 | 215761 | JsonString *pStr; |
| 215762 | + int flags = SQLITE_PTR_TO_INT(sqlite3_user_data(ctx)); |
| 215705 | 215763 | pStr = (JsonString*)sqlite3_aggregate_context(ctx, 0); |
| 215706 | 215764 | if( pStr ){ |
| 215707 | | - int flags; |
| 215708 | 215765 | pStr->pCtx = ctx; |
| 215709 | 215766 | jsonAppendChar(pStr, ']'); |
| 215710 | | - flags = SQLITE_PTR_TO_INT(sqlite3_user_data(ctx)); |
| 215711 | 215767 | if( pStr->eErr ){ |
| 215712 | 215768 | jsonReturnString(pStr, 0, 0); |
| 215713 | 215769 | return; |
| 215714 | 215770 | }else if( flags & JSON_BLOB ){ |
| 215715 | 215771 | jsonReturnStringAsBlob(pStr); |
| | @@ -215726,10 +215782,13 @@ |
| 215726 | 215782 | pStr->bStatic = 1; |
| 215727 | 215783 | }else{ |
| 215728 | 215784 | sqlite3_result_text(ctx, pStr->zBuf, (int)pStr->nUsed, SQLITE_TRANSIENT); |
| 215729 | 215785 | jsonStringTrimOneChar(pStr); |
| 215730 | 215786 | } |
| 215787 | + }else if( flags & JSON_BLOB ){ |
| 215788 | + static const u8 emptyArray = 0x0b; |
| 215789 | + sqlite3_result_blob(ctx, &emptyArray, 1, SQLITE_STATIC); |
| 215731 | 215790 | }else{ |
| 215732 | 215791 | sqlite3_result_text(ctx, "[]", 2, SQLITE_STATIC); |
| 215733 | 215792 | } |
| 215734 | 215793 | sqlite3_result_subtype(ctx, JSON_SUBTYPE); |
| 215735 | 215794 | } |
| | @@ -215822,16 +215881,15 @@ |
| 215822 | 215881 | } |
| 215823 | 215882 | } |
| 215824 | 215883 | } |
| 215825 | 215884 | static void jsonObjectCompute(sqlite3_context *ctx, int isFinal){ |
| 215826 | 215885 | JsonString *pStr; |
| 215886 | + int flags = SQLITE_PTR_TO_INT(sqlite3_user_data(ctx)); |
| 215827 | 215887 | pStr = (JsonString*)sqlite3_aggregate_context(ctx, 0); |
| 215828 | 215888 | if( pStr ){ |
| 215829 | | - int flags; |
| 215830 | 215889 | jsonAppendChar(pStr, '}'); |
| 215831 | 215890 | pStr->pCtx = ctx; |
| 215832 | | - flags = SQLITE_PTR_TO_INT(sqlite3_user_data(ctx)); |
| 215833 | 215891 | if( pStr->eErr ){ |
| 215834 | 215892 | jsonReturnString(pStr, 0, 0); |
| 215835 | 215893 | return; |
| 215836 | 215894 | }else if( flags & JSON_BLOB ){ |
| 215837 | 215895 | jsonReturnStringAsBlob(pStr); |
| | @@ -215848,10 +215906,13 @@ |
| 215848 | 215906 | pStr->bStatic = 1; |
| 215849 | 215907 | }else{ |
| 215850 | 215908 | sqlite3_result_text(ctx, pStr->zBuf, (int)pStr->nUsed, SQLITE_TRANSIENT); |
| 215851 | 215909 | jsonStringTrimOneChar(pStr); |
| 215852 | 215910 | } |
| 215911 | + }else if( flags & JSON_BLOB ){ |
| 215912 | + static const unsigned char emptyObject = 0x0c; |
| 215913 | + sqlite3_result_blob(ctx, &emptyObject, 1, SQLITE_STATIC); |
| 215853 | 215914 | }else{ |
| 215854 | 215915 | sqlite3_result_text(ctx, "{}", 2, SQLITE_STATIC); |
| 215855 | 215916 | } |
| 215856 | 215917 | sqlite3_result_subtype(ctx, JSON_SUBTYPE); |
| 215857 | 215918 | } |
| | @@ -216348,11 +216409,11 @@ |
| 216348 | 216409 | if( idxNum==3 ){ |
| 216349 | 216410 | zRoot = (const char*)sqlite3_value_text(argv[1]); |
| 216350 | 216411 | if( zRoot==0 ) return SQLITE_OK; |
| 216351 | 216412 | if( zRoot[0]!='$' ){ |
| 216352 | 216413 | sqlite3_free(cur->pVtab->zErrMsg); |
| 216353 | | - cur->pVtab->zErrMsg = jsonBadPathError(0, zRoot); |
| 216414 | + cur->pVtab->zErrMsg = jsonBadPathError(0, zRoot, 0); |
| 216354 | 216415 | jsonEachCursorReset(p); |
| 216355 | 216416 | return cur->pVtab->zErrMsg ? SQLITE_ERROR : SQLITE_NOMEM; |
| 216356 | 216417 | } |
| 216357 | 216418 | p->nRoot = sqlite3Strlen30(zRoot); |
| 216358 | 216419 | if( zRoot[1]==0 ){ |
| | @@ -216366,11 +216427,11 @@ |
| 216366 | 216427 | p->eType = 0; |
| 216367 | 216428 | p->iEnd = 0; |
| 216368 | 216429 | return SQLITE_OK; |
| 216369 | 216430 | } |
| 216370 | 216431 | sqlite3_free(cur->pVtab->zErrMsg); |
| 216371 | | - cur->pVtab->zErrMsg = jsonBadPathError(0, zRoot); |
| 216432 | + cur->pVtab->zErrMsg = jsonBadPathError(0, zRoot, 0); |
| 216372 | 216433 | jsonEachCursorReset(p); |
| 216373 | 216434 | return cur->pVtab->zErrMsg ? SQLITE_ERROR : SQLITE_NOMEM; |
| 216374 | 216435 | } |
| 216375 | 216436 | if( p->sParse.iLabel ){ |
| 216376 | 216437 | p->i = p->sParse.iLabel; |
| | @@ -216456,10 +216517,12 @@ |
| 216456 | 216517 | /* | | | | | | */ |
| 216457 | 216518 | JFUNCTION(json, 1,1,1, 0,0,0, jsonRemoveFunc), |
| 216458 | 216519 | JFUNCTION(jsonb, 1,1,0, 0,1,0, jsonRemoveFunc), |
| 216459 | 216520 | JFUNCTION(json_array, -1,0,1, 1,0,0, jsonArrayFunc), |
| 216460 | 216521 | JFUNCTION(jsonb_array, -1,0,1, 1,1,0, jsonArrayFunc), |
| 216522 | + JFUNCTION(json_array_insert, -1,1,1, 1,0,JSON_AINS, jsonSetFunc), |
| 216523 | + JFUNCTION(jsonb_array_insert,-1,1,0, 1,1,JSON_AINS, jsonSetFunc), |
| 216461 | 216524 | JFUNCTION(json_array_length, 1,1,0, 0,0,0, jsonArrayLengthFunc), |
| 216462 | 216525 | JFUNCTION(json_array_length, 2,1,0, 0,0,0, jsonArrayLengthFunc), |
| 216463 | 216526 | JFUNCTION(json_error_position,1,1,0, 0,0,0, jsonErrorFunc), |
| 216464 | 216527 | JFUNCTION(json_extract, -1,1,1, 0,0,0, jsonExtractFunc), |
| 216465 | 216528 | JFUNCTION(jsonb_extract, -1,1,0, 0,1,0, jsonExtractFunc), |
| | @@ -232389,31 +232452,31 @@ |
| 232389 | 232452 | for(i=0; i<pTab->nCol; i++){ |
| 232390 | 232453 | int eType = *a; |
| 232391 | 232454 | int isPK = pTab->abPK[i]; |
| 232392 | 232455 | if( bPkOnly && isPK==0 ) continue; |
| 232393 | 232456 | |
| 232394 | | - /* It is not possible for eType to be SQLITE_NULL here. The session |
| 232395 | | - ** module does not record changes for rows with NULL values stored in |
| 232396 | | - ** primary key columns. */ |
| 232397 | 232457 | assert( eType==SQLITE_INTEGER || eType==SQLITE_FLOAT |
| 232398 | 232458 | || eType==SQLITE_TEXT || eType==SQLITE_BLOB |
| 232399 | 232459 | || eType==SQLITE_NULL || eType==0 |
| 232400 | 232460 | ); |
| 232401 | | - assert( !isPK || (eType!=0 && eType!=SQLITE_NULL) ); |
| 232402 | 232461 | |
| 232403 | 232462 | if( isPK ){ |
| 232404 | 232463 | a++; |
| 232405 | 232464 | h = sessionHashAppendType(h, eType); |
| 232406 | 232465 | if( eType==SQLITE_INTEGER || eType==SQLITE_FLOAT ){ |
| 232407 | 232466 | h = sessionHashAppendI64(h, sessionGetI64(a)); |
| 232408 | 232467 | a += 8; |
| 232409 | | - }else{ |
| 232468 | + }else if( eType==SQLITE_TEXT || eType==SQLITE_BLOB ){ |
| 232410 | 232469 | int n; |
| 232411 | 232470 | a += sessionVarintGet(a, &n); |
| 232412 | 232471 | h = sessionHashAppendBlob(h, n, a); |
| 232413 | 232472 | a += n; |
| 232414 | 232473 | } |
| 232474 | + /* It should not be possible for eType to be SQLITE_NULL or 0x00 here, |
| 232475 | + ** as the session module does not record changes for rows with NULL |
| 232476 | + ** values stored in primary key columns. But a corrupt changesets |
| 232477 | + ** may contain such a value. */ |
| 232415 | 232478 | }else{ |
| 232416 | 232479 | a += sessionSerialLen(a); |
| 232417 | 232480 | } |
| 232418 | 232481 | } |
| 232419 | 232482 | return (h % nBucket); |
| | @@ -234818,14 +234881,17 @@ |
| 234818 | 234881 | *pnChangeset = 0; |
| 234819 | 234882 | *ppChangeset = 0; |
| 234820 | 234883 | } |
| 234821 | 234884 | |
| 234822 | 234885 | if( pSession->rc ) return pSession->rc; |
| 234823 | | - rc = sqlite3_exec(pSession->db, "SAVEPOINT changeset", 0, 0, 0); |
| 234824 | | - if( rc!=SQLITE_OK ) return rc; |
| 234825 | 234886 | |
| 234826 | 234887 | sqlite3_mutex_enter(sqlite3_db_mutex(db)); |
| 234888 | + rc = sqlite3_exec(pSession->db, "SAVEPOINT changeset", 0, 0, 0); |
| 234889 | + if( rc!=SQLITE_OK ){ |
| 234890 | + sqlite3_mutex_leave(sqlite3_db_mutex(db)); |
| 234891 | + return rc; |
| 234892 | + } |
| 234827 | 234893 | |
| 234828 | 234894 | for(pTab=pSession->pTable; rc==SQLITE_OK && pTab; pTab=pTab->pNext){ |
| 234829 | 234895 | if( pTab->nEntry ){ |
| 234830 | 234896 | const char *zName = pTab->zName; |
| 234831 | 234897 | int i; /* Used to iterate through hash buckets */ |
| | @@ -235377,12 +235443,19 @@ |
| 235377 | 235443 | |
| 235378 | 235444 | while( rc==SQLITE_OK ){ |
| 235379 | 235445 | while( (pIn->iNext + nRead)<pIn->nData && pIn->aData[pIn->iNext + nRead] ){ |
| 235380 | 235446 | nRead++; |
| 235381 | 235447 | } |
| 235448 | + |
| 235449 | + /* Break out of the loop if if the nul-terminator byte has been found. |
| 235450 | + ** Otherwise, read some more input data and keep seeking. If there is |
| 235451 | + ** no more input data, consider the changeset corrupt. */ |
| 235382 | 235452 | if( (pIn->iNext + nRead)<pIn->nData ) break; |
| 235383 | 235453 | rc = sessionInputBuffer(pIn, nRead + 100); |
| 235454 | + if( rc==SQLITE_OK && (pIn->iNext + nRead)>=pIn->nData ){ |
| 235455 | + rc = SQLITE_CORRUPT_BKPT; |
| 235456 | + } |
| 235384 | 235457 | } |
| 235385 | 235458 | *pnByte = nRead+1; |
| 235386 | 235459 | return rc; |
| 235387 | 235460 | } |
| 235388 | 235461 | |
| | @@ -253281,11 +253354,11 @@ |
| 253281 | 253354 | ){ |
| 253282 | 253355 | const int bDetailNone = (p->pConfig->eDetail==FTS5_DETAIL_NONE); |
| 253283 | 253356 | int iSegid = pSeg->pSeg->iSegid; |
| 253284 | 253357 | u8 *aPg = pSeg->pLeaf->p; |
| 253285 | 253358 | int nPg = pSeg->pLeaf->nn; |
| 253286 | | - int iPgIdx = pSeg->pLeaf->szLeaf; |
| 253359 | + int iPgIdx = pSeg->pLeaf->szLeaf; /* Offset of page footer */ |
| 253287 | 253360 | |
| 253288 | 253361 | u64 iDelta = 0; |
| 253289 | 253362 | int iNextOff = 0; |
| 253290 | 253363 | int iOff = 0; |
| 253291 | 253364 | int nIdx = 0; |
| | @@ -253360,11 +253433,11 @@ |
| 253360 | 253433 | iStart = iSOP + (nPos/2); |
| 253361 | 253434 | iSOP = iStart + fts5GetVarint(&aPg[iStart], &iDelta); |
| 253362 | 253435 | iSOP += fts5GetVarint32(&aPg[iSOP], nPos); |
| 253363 | 253436 | } |
| 253364 | 253437 | assert_nc( iSOP==pSeg->iLeafOffset ); |
| 253365 | | - iNextOff = pSeg->iLeafOffset + pSeg->nPos; |
| 253438 | + iNextOff = iSOP + pSeg->nPos; |
| 253366 | 253439 | } |
| 253367 | 253440 | } |
| 253368 | 253441 | |
| 253369 | 253442 | iOff = iStart; |
| 253370 | 253443 | |
| | @@ -253440,35 +253513,35 @@ |
| 253440 | 253513 | if( iNextOff!=iPgIdx ){ |
| 253441 | 253514 | /* This is the only position-list associated with the term, and there |
| 253442 | 253515 | ** is another term following it on this page. So the subsequent term |
| 253443 | 253516 | ** needs to be moved to replace the term associated with the entry |
| 253444 | 253517 | ** being removed. */ |
| 253445 | | - int nPrefix = 0; |
| 253446 | | - int nSuffix = 0; |
| 253447 | | - int nPrefix2 = 0; |
| 253448 | | - int nSuffix2 = 0; |
| 253518 | + u64 nPrefix = 0; |
| 253519 | + u64 nSuffix = 0; |
| 253520 | + u64 nPrefix2 = 0; |
| 253521 | + u64 nSuffix2 = 0; |
| 253449 | 253522 | |
| 253450 | 253523 | iDelKeyOff = iNextOff; |
| 253451 | | - iNextOff += fts5GetVarint32(&aPg[iNextOff], nPrefix2); |
| 253452 | | - iNextOff += fts5GetVarint32(&aPg[iNextOff], nSuffix2); |
| 253524 | + iNextOff += fts5GetVarint(&aPg[iNextOff], &nPrefix2); |
| 253525 | + iNextOff += fts5GetVarint(&aPg[iNextOff], &nSuffix2); |
| 253453 | 253526 | |
| 253454 | 253527 | if( iKey!=1 ){ |
| 253455 | | - iKeyOff += fts5GetVarint32(&aPg[iKeyOff], nPrefix); |
| 253528 | + iKeyOff += fts5GetVarint(&aPg[iKeyOff], &nPrefix); |
| 253456 | 253529 | } |
| 253457 | | - iKeyOff += fts5GetVarint32(&aPg[iKeyOff], nSuffix); |
| 253530 | + iKeyOff += fts5GetVarint(&aPg[iKeyOff], &nSuffix); |
| 253458 | 253531 | |
| 253459 | 253532 | nPrefix = MIN(nPrefix, nPrefix2); |
| 253460 | 253533 | nSuffix = (nPrefix2 + nSuffix2) - nPrefix; |
| 253461 | 253534 | |
| 253462 | | - if( (iKeyOff+nSuffix)>iPgIdx || (iNextOff+nSuffix2)>iPgIdx ){ |
| 253535 | + if( (iKeyOff+nSuffix)>(u64)iPgIdx || (iNextOff+nSuffix2)>(u64)iPgIdx ){ |
| 253463 | 253536 | FTS5_CORRUPT_IDX(p); |
| 253464 | 253537 | }else{ |
| 253465 | 253538 | if( iKey!=1 ){ |
| 253466 | 253539 | iOff += sqlite3Fts5PutVarint(&aPg[iOff], nPrefix); |
| 253467 | 253540 | } |
| 253468 | 253541 | iOff += sqlite3Fts5PutVarint(&aPg[iOff], nSuffix); |
| 253469 | | - if( nPrefix2>pSeg->term.n ){ |
| 253542 | + if( nPrefix2>(u64)pSeg->term.n ){ |
| 253470 | 253543 | FTS5_CORRUPT_IDX(p); |
| 253471 | 253544 | }else if( nPrefix2>nPrefix ){ |
| 253472 | 253545 | memcpy(&aPg[iOff], &pSeg->term.p[nPrefix], nPrefix2-nPrefix); |
| 253473 | 253546 | iOff += (nPrefix2-nPrefix); |
| 253474 | 253547 | } |
| | @@ -253495,11 +253568,11 @@ |
| 253495 | 253568 | Fts5Data *pTerm = fts5DataRead(p, iId); |
| 253496 | 253569 | if( pTerm && pTerm->szLeaf==pSeg->iTermLeafOffset ){ |
| 253497 | 253570 | u8 *aTermIdx = &pTerm->p[pTerm->szLeaf]; |
| 253498 | 253571 | int nTermIdx = pTerm->nn - pTerm->szLeaf; |
| 253499 | 253572 | int iTermIdx = 0; |
| 253500 | | - int iTermOff = 0; |
| 253573 | + i64 iTermOff = 0; |
| 253501 | 253574 | |
| 253502 | 253575 | while( 1 ){ |
| 253503 | 253576 | u32 iVal = 0; |
| 253504 | 253577 | int nByte = fts5GetVarint32(&aTermIdx[iTermIdx], iVal); |
| 253505 | 253578 | iTermOff += iVal; |
| | @@ -253506,16 +253579,19 @@ |
| 253506 | 253579 | if( (iTermIdx+nByte)>=nTermIdx ) break; |
| 253507 | 253580 | iTermIdx += nByte; |
| 253508 | 253581 | } |
| 253509 | 253582 | nTermIdx = iTermIdx; |
| 253510 | 253583 | |
| 253511 | | - memmove(&pTerm->p[iTermOff], &pTerm->p[pTerm->szLeaf], nTermIdx); |
| 253512 | | - fts5PutU16(&pTerm->p[2], iTermOff); |
| 253513 | | - |
| 253514 | | - fts5DataWrite(p, iId, pTerm->p, iTermOff+nTermIdx); |
| 253515 | | - if( nTermIdx==0 ){ |
| 253516 | | - fts5SecureDeleteIdxEntry(p, iSegid, pSeg->iTermLeafPgno); |
| 253584 | + if( iTermOff>pTerm->szLeaf ){ |
| 253585 | + FTS5_CORRUPT_IDX(p); |
| 253586 | + }else{ |
| 253587 | + memmove(&pTerm->p[iTermOff], &pTerm->p[pTerm->szLeaf], nTermIdx); |
| 253588 | + fts5PutU16(&pTerm->p[2], iTermOff); |
| 253589 | + fts5DataWrite(p, iId, pTerm->p, iTermOff+nTermIdx); |
| 253590 | + if( nTermIdx==0 ){ |
| 253591 | + fts5SecureDeleteIdxEntry(p, iSegid, pSeg->iTermLeafPgno); |
| 253592 | + } |
| 253517 | 253593 | } |
| 253518 | 253594 | } |
| 253519 | 253595 | fts5DataRelease(pTerm); |
| 253520 | 253596 | } |
| 253521 | 253597 | } |
| | @@ -253534,11 +253610,13 @@ |
| 253534 | 253610 | int nShift = iNextOff - iOff; /* Distance to move them */ |
| 253535 | 253611 | |
| 253536 | 253612 | int iPrevKeyOut = 0; |
| 253537 | 253613 | int iKeyIn = 0; |
| 253538 | 253614 | |
| 253539 | | - memmove(&aPg[iOff], &aPg[iNextOff], nMove); |
| 253615 | + if( nMove>0 ){ |
| 253616 | + memmove(&aPg[iOff], &aPg[iNextOff], nMove); |
| 253617 | + } |
| 253540 | 253618 | iPgIdx -= nShift; |
| 253541 | 253619 | nPg = iPgIdx; |
| 253542 | 253620 | fts5PutU16(&aPg[2], iPgIdx); |
| 253543 | 253621 | |
| 253544 | 253622 | for(iIdx=0; iIdx<nIdx; /* no-op */){ |
| | @@ -261180,11 +261258,11 @@ |
| 261180 | 261258 | int nArg, /* Number of args */ |
| 261181 | 261259 | sqlite3_value **apUnused /* Function arguments */ |
| 261182 | 261260 | ){ |
| 261183 | 261261 | assert( nArg==0 ); |
| 261184 | 261262 | UNUSED_PARAM2(nArg, apUnused); |
| 261185 | | - sqlite3_result_text(pCtx, "fts5: 2026-01-09 00:41:35 9adab8b2bef4130abd358d53384cb5f4dd691b808336bb7102793b0165b1c516", -1, SQLITE_TRANSIENT); |
| 261263 | + sqlite3_result_text(pCtx, "fts5: 2026-01-26 10:53:24 4733d351ec2376291f093ba8d2ba71d82c6f100c68dc860eee0532986c154e71", -1, SQLITE_TRANSIENT); |
| 261186 | 261264 | } |
| 261187 | 261265 | |
| 261188 | 261266 | /* |
| 261189 | 261267 | ** Implementation of fts5_locale(LOCALE, TEXT) function. |
| 261190 | 261268 | ** |
| 261191 | 261269 | |