From ce9ef1d43f0e46f004e70c348fe150e4b775503a Mon Sep 17 00:00:00 2001 From: drh <> Date: Mon, 22 Jul 2024 16:59:35 +0000 Subject: [PATCH] Only allow variables in LIMIT clauses if the LIMIT is within a LATERAL subquery and the variable resolves to another FROM clause term to the left of the subquery. We cannot allow variables from outer contexts because the LIMIT value is computed before the cursors in the outer context have been initialized. FossilOrigin-Name: 0a2531c3a3750fd22360595274eb97fa66d17a90502180b7b11adc5b136da5ed --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/resolve.c | 13 +++++++++++-- 3 files changed, 18 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index 83921a10fc..079f71874b 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Allow\sLIMIT\sexpressions\sto\sappear\sin\sany\souter\scontext. -D 2024-07-22T16:15:25.528 +C Only\sallow\svariables\sin\sLIMIT\sclauses\sif\sthe\sLIMIT\sis\swithin\sa\sLATERAL\ssubquery\nand\sthe\svariable\sresolves\sto\sanother\sFROM\sclause\sterm\sto\sthe\sleft\sof\sthe\nsubquery.\s\sWe\scannot\sallow\svariables\sfrom\souter\scontexts\sbecause\sthe\sLIMIT\nvalue\sis\scomputed\sbefore\sthe\scursors\sin\sthe\souter\scontext\shave\sbeen\sinitialized. +D 2024-07-22T16:59:35.769 F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1 F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea F LICENSE.md df5091916dbb40e6e9686186587125e1b2ff51f022cc334e886c19a0e9982724 @@ -753,7 +753,7 @@ F src/pragma.h e690a356c18e98414d2e870ea791c1be1545a714ba623719deb63f7f226d8bb7 F src/prepare.c d99931f45416652895e502328ca49fe782cfc4e1ebdcda13b3736d991ebf42ce F src/printf.c 8b250972305e14b365561be5117ed0fd364e4fd58968776df1ce64c6280b90f9 F src/random.c 606b00941a1d7dd09c381d3279a058d771f406c5213c9932bbd93d5587be4b9c -F src/resolve.c faf549360137f79582853f0e631e586e1d8e50b01c81b4e8e3413f6a6629955e +F src/resolve.c 8dc8832973fd9f695e85042577d4e21f5b91c4f4576d311d418ad11387fd75ed F src/rowset.c 8432130e6c344b3401a8874c3cb49fefe6873fec593294de077afea2dce5ec97 F src/select.c 1f5f1663fe84ee1963a55aef8871f1e7740a8030db517dcbfa16e27c6187fe74 F src/shell.c.in b7d435c137eb323981adff814f172dbaabb9ba504fef17cb11d4681c1633ee13 @@ -2196,8 +2196,8 @@ F vsixtest/vsixtest.tcl 6a9a6ab600c25a91a7acc6293828957a386a8a93 F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0 -P 10347821376db1d33895fa794ac093ec6c2cc28daebe9adfd2578cbd1b3ce386 -R 4c95a122c5976ab28e0a9c267f355dab +P c9d3427de5b55303279449023b7d7957821bfe97089547dcafcfb913806745ed +R 41a4aad165dcb3790b8abe2f6b5c4bd9 U drh -Z 86e33b4ab8ddc73e7f8283d820eff8d6 +Z 133ddb98c99accb293096ad5d3d47230 # Remove this line to create a well-formed Fossil manifest. diff --git a/manifest.uuid b/manifest.uuid index 81d835c70f..bab32365d4 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -c9d3427de5b55303279449023b7d7957821bfe97089547dcafcfb913806745ed +0a2531c3a3750fd22360595274eb97fa66d17a90502180b7b11adc5b136da5ed diff --git a/src/resolve.c b/src/resolve.c index 87432bc392..a4a52e140b 100644 --- a/src/resolve.c +++ b/src/resolve.c @@ -1868,8 +1868,7 @@ static int resolveSelectStep(Walker *pWalker, Select *p){ memset(&sNC, 0, sizeof(sNC)); sNC.pParse = pParse; sNC.pWinSelect = p; - sNC.pNext = pOuterNC; - if( sqlite3ResolveExprNames(&sNC, p->pLimit) ){ + if( p->pLimit!=0 && sqlite3ResolveExprNames(&sNC, p->pLimit) ){ return WRC_Abort; } @@ -1902,9 +1901,19 @@ static int resolveSelectStep(Walker *pWalker, Select *p){ if( pItem->zName ) pParse->zAuthContext = pItem->zName; if( pItem->fg.isLateral ){ assert( i>0 ); /* Because p->pSub->a[0] is never marked LATERAL */ + assert( pItem->pSelect!=0 ); assert( pItem->pSelect->selFlags & SF_Lateral ); p->pSrc->nSrc = i; sNC.pSrcList = p->pSrc; + if( pItem->pSelect->pLimit ){ + /* If a LIMIT/OFFSET clause exists on a LATERAL subquery, allow + ** variables from other FROM clause terms to the left of the + ** subquery to be used in the LIMIT/OFFSET clause. */ + sNC.pNext = 0; + if( sqlite3ResolveExprNames(&sNC, pItem->pSelect->pLimit) ){ + return WRC_Abort; + } + } sNC.pNext = pOuterNC; pSubNC = &sNC; }else{ -- 2.47.3