SQLite

Check-in [e487d3b3c0]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:Ensure that the query flattener does not change an ON clause term to a WHERE clause term.
Downloads: Tarball | ZIP archive
Timelines: family | ancestors | descendants | both | branch-3.47
Files: files | file ages | folders
SHA3-256: e487d3b3c03ebcf06f8071f5c6a04faae15605200361e831df7bb2361e33efc3
User & Date: drh 2024-12-02 19:32:07.485
Context
2024-12-07
14:51
On x64 hardware, round-trip uint64_t→double→uint64_t conversions fail for values greater than UINT64_MAX-2047. This caused the SQLite text-to-float converter routine to give incorrect results for values between '1.8446744073709550592eNNN' and '1.8446744073709551609eNNN' for any exponent NNN. Fixed by this check-in. (check-in: 17537a98cb user: drh tags: branch-3.47)
2024-12-02
19:32
Ensure that the query flattener does not change an ON clause term to a WHERE clause term. (check-in: e487d3b3c0 user: drh tags: branch-3.47)
17:21
Ensure that the query flattener does not change an ON clause term to a WHERE clause term. [forum:/forumpost/3f676b1196|Forum post 3f676b1196]. Follow-up to [f1eae192315335d7]. (check-in: bdd408a255 user: dan tags: trunk)
16:38
Add the SVG version of the SQLite logo. (check-in: a2061fe09f user: drh tags: branch-3.47)
Changes
Unified Diff Ignore Whitespace Patch
Changes to src/select.c.
3907
3908
3909
3910
3911
3912
3913




















3914
3915
3916
3917
3918
3919
3920
3921
3922
3923
3924
3925
3926
3927
3928
3929
3930
3931
3932
3933
3934
3935
3936
3937
3938
3939
3940
3941
3942
3943
3944
3945
3946
        if( db->mallocFailed ){
          sqlite3ExprDelete(db, pNew);
          return pExpr;
        }
        if( pSubst->isOuterJoin ){
          ExprSetProperty(pNew, EP_CanBeNull);
        }




















        if( ExprHasProperty(pExpr,EP_OuterON|EP_InnerON) ){
          sqlite3SetJoinExpr(pNew, pExpr->w.iJoin,
                             pExpr->flags & (EP_OuterON|EP_InnerON));
        }
        sqlite3ExprDelete(db, pExpr);
        pExpr = pNew;
        if( pExpr->op==TK_TRUEFALSE ){
          pExpr->u.iValue = sqlite3ExprTruthValue(pExpr);
          pExpr->op = TK_INTEGER;
          ExprSetProperty(pExpr, EP_IntValue);
        }

        /* Ensure that the expression now has an implicit collation sequence,
        ** just as it did when it was a column of a view or sub-query. */
        {
          CollSeq *pNat = sqlite3ExprCollSeq(pSubst->pParse, pExpr);
          CollSeq *pColl = sqlite3ExprCollSeq(pSubst->pParse,
                pSubst->pCList->a[iColumn].pExpr
          );
          if( pNat!=pColl || (pExpr->op!=TK_COLUMN && pExpr->op!=TK_COLLATE) ){
            pExpr = sqlite3ExprAddCollateString(pSubst->pParse, pExpr,
                (pColl ? pColl->zName : "BINARY")
            );
          }
        }
        ExprClearProperty(pExpr, EP_Collate);
      }
    }
  }else{
    if( pExpr->op==TK_IF_NULL_ROW && pExpr->iTable==pSubst->iTable ){
      pExpr->iTable = pSubst->iNewTable;
    }
    pExpr->pLeft = substExpr(pSubst, pExpr->pLeft);







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>






<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<
<







3907
3908
3909
3910
3911
3912
3913
3914
3915
3916
3917
3918
3919
3920
3921
3922
3923
3924
3925
3926
3927
3928
3929
3930
3931
3932
3933
3934
3935
3936
3937
3938
3939




















3940
3941
3942
3943
3944
3945
3946
        if( db->mallocFailed ){
          sqlite3ExprDelete(db, pNew);
          return pExpr;
        }
        if( pSubst->isOuterJoin ){
          ExprSetProperty(pNew, EP_CanBeNull);
        }
        if( pNew->op==TK_TRUEFALSE ){
          pNew->u.iValue = sqlite3ExprTruthValue(pNew);
          pNew->op = TK_INTEGER;
          ExprSetProperty(pNew, EP_IntValue);
        }

        /* Ensure that the expression now has an implicit collation sequence,
        ** just as it did when it was a column of a view or sub-query. */
        {
          CollSeq *pNat = sqlite3ExprCollSeq(pSubst->pParse, pNew);
          CollSeq *pColl = sqlite3ExprCollSeq(pSubst->pParse,
                pSubst->pCList->a[iColumn].pExpr
          );
          if( pNat!=pColl || (pNew->op!=TK_COLUMN && pNew->op!=TK_COLLATE) ){
            pNew = sqlite3ExprAddCollateString(pSubst->pParse, pNew,
                (pColl ? pColl->zName : "BINARY")
            );
          }
        }
        ExprClearProperty(pNew, EP_Collate);
        if( ExprHasProperty(pExpr,EP_OuterON|EP_InnerON) ){
          sqlite3SetJoinExpr(pNew, pExpr->w.iJoin,
                             pExpr->flags & (EP_OuterON|EP_InnerON));
        }
        sqlite3ExprDelete(db, pExpr);
        pExpr = pNew;




















      }
    }
  }else{
    if( pExpr->op==TK_IF_NULL_ROW && pExpr->iTable==pSubst->iTable ){
      pExpr->iTable = pSubst->iNewTable;
    }
    pExpr->pLeft = substExpr(pSubst, pExpr->pLeft);
Changes to test/pushdown.test.
320
321
322
323
324
325
326































327
328
  |     |     `--CREATE BLOOM FILTER
  |     `--UNION ALL
  |        |--SEARCH t02 USING INDEX t02x (w=? AND x=? AND y>? AND y<?)
  |        `--REUSE LIST SUBQUERY xxxxxx
  |--SEARCH t0
  `--REUSE LIST SUBQUERY xxxxxx
}
































finish_test







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>


320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
  |     |     `--CREATE BLOOM FILTER
  |     `--UNION ALL
  |        |--SEARCH t02 USING INDEX t02x (w=? AND x=? AND y>? AND y<?)
  |        `--REUSE LIST SUBQUERY xxxxxx
  |--SEARCH t0
  `--REUSE LIST SUBQUERY xxxxxx
}

#-------------------------------------------------------------------------
reset_db
do_execsql_test 7.0 {
  CREATE  TABLE  t0_1(a INT , b INT, c INT);
  CREATE  TABLE  t0_2(a INT , b INT, c INT);

  INSERT INTO t0_1 (a, b, c) VALUES (1, 0, 1);
  INSERT INTO t0_2 (a, b, c) VALUES (1, 0, 1);

  CREATE  TABLE  empty1(x);
  CREATE  TABLE  empty2(y);
}

do_execsql_test 7.1 {
  SELECT t0_2.c
    FROM (SELECT '0000' AS c0 FROM empty2 RIGHT JOIN t0_1 ON 1) AS v0 
    LEFT JOIN empty1 ON v0.c0, t0_2 
    RIGHT JOIN (
           SELECT 5678 AS col0 FROM (SELECT 0)
    ) AS sub1 ON 1;
} {1}

do_execsql_test 7.2 {
  SELECT t0_2.c
    FROM (SELECT '0000' AS c0 FROM empty2 RIGHT JOIN t0_1 ON 1) AS v0 
    LEFT JOIN empty1 ON v0.c0, t0_2 
    RIGHT JOIN (
           SELECT 5678 AS col0 FROM (SELECT 0)
    ) AS sub1 ON 1 WHERE +t0_2.c;
} {1}

finish_test