Many hyperlinks are disabled.
Use anonymous login
to enable hyperlinks.
Overview
Comment: | Do not allow the pagesize of :memory: databases to be changed. Silently ignore PRAGMA page_size=N requests for :memory: databases. Ticket #1144 and #1252. (CVS 2466) |
---|---|
Downloads: | Tarball | ZIP archive | SQL archive |
Timelines: | family | ancestors | descendants | both | trunk |
Files: | files | file ages | folders |
SHA1: |
f29a1d882623d8ff14f35a302aef63a1 |
User & Date: | drh 2005-05-20 20:01:56 |
Context
2005-05-20
| ||
20:11 | Reorder structure fields to reduce code footprint. Ticket #1253. Need to do more of this. (CVS 2467) check-in: 27025613 user: drh tags: trunk | |
20:01 | Do not allow the pagesize of :memory: databases to be changed. Silently ignore PRAGMA page_size=N requests for :memory: databases. Ticket #1144 and #1252. (CVS 2466) check-in: f29a1d88 user: drh tags: trunk | |
19:36 | Comment changes in vdbeapi.c (CVS 2465) check-in: ab7805fb user: drh tags: trunk | |
Changes
Changes to src/btree.c.
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
....
1358
1359
1360
1361
1362
1363
1364
1365
1366
1367
1368
1369
1370
1371
1372
1373
|
** a legal notice, here is a blessing: ** ** May you do good and not evil. ** May you find forgiveness for yourself and forgive others. ** May you share freely, never taking more than you give. ** ************************************************************************* ** $Id: btree.c,v 1.259 2005/05/05 18:14:14 drh Exp $ ** ** This file implements a external (disk-based) database using BTrees. ** For a detailed discussion of BTrees, refer to ** ** Donald E. Knuth, THE ART OF COMPUTER PROGRAMMING, Volume 3: ** "Sorting And Searching", pages 473-480. Addison-Wesley ** Publishing Company, Reading, Massachusetts. ................................................................................ } if( nReserve<0 ){ nReserve = pBt->pageSize - pBt->usableSize; } if( pageSize>=512 && pageSize<=SQLITE_MAX_PAGE_SIZE && ((pageSize-1)&pageSize)==0 ){ assert( (pageSize & 7)==0 ); pBt->pageSize = pageSize; sqlite3pager_set_pagesize(pBt->pPager, pageSize); } pBt->usableSize = pBt->pageSize - nReserve; return SQLITE_OK; } /* ** Return the currently defined page size |
|
<
|
|
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
....
1358
1359
1360
1361
1362
1363
1364
1365
1366
1367
1368
1369
1370
1371
1372
|
** a legal notice, here is a blessing: ** ** May you do good and not evil. ** May you find forgiveness for yourself and forgive others. ** May you share freely, never taking more than you give. ** ************************************************************************* ** $Id: btree.c,v 1.260 2005/05/20 20:01:56 drh Exp $ ** ** This file implements a external (disk-based) database using BTrees. ** For a detailed discussion of BTrees, refer to ** ** Donald E. Knuth, THE ART OF COMPUTER PROGRAMMING, Volume 3: ** "Sorting And Searching", pages 473-480. Addison-Wesley ** Publishing Company, Reading, Massachusetts. ................................................................................ } if( nReserve<0 ){ nReserve = pBt->pageSize - pBt->usableSize; } if( pageSize>=512 && pageSize<=SQLITE_MAX_PAGE_SIZE && ((pageSize-1)&pageSize)==0 ){ assert( (pageSize & 7)==0 ); pBt->pageSize = sqlite3pager_set_pagesize(pBt->pPager, pageSize); } pBt->usableSize = pBt->pageSize - nReserve; return SQLITE_OK; } /* ** Return the currently defined page size |
Changes to src/pager.c.
14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 ... 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 ... 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 ... 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 .... 1656 1657 1658 1659 1660 1661 1662 1663 1664 1665 1666 1667 1668 1669 1670 .... 1712 1713 1714 1715 1716 1717 1718 1719 1720 1721 1722 1723 1724 1725 1726 1727 1728 1729 1730 1731 1732 1733 .... 2372 2373 2374 2375 2376 2377 2378 2379 2380 2381 2382 2383 2384 2385 2386 |
** The pager is used to access a database disk file. It implements ** atomic commit and rollback through the use of a journal file that ** is separate from the database file. The pager also implements file ** locking to prevent two processes from writing the same database ** file simultaneously, or one process from reading the database while ** another is writing. ** ** @(#) $Id: pager.c,v 1.202 2005/04/28 17:18:48 drh Exp $ */ #ifndef SQLITE_OMIT_DISKIO #include "sqliteInt.h" #include "os.h" #include "pager.h" #include <assert.h> #include <string.h> ................................................................................ u8 needSync; /* Sync journal before writing this page */ u8 alwaysRollback; /* Disable dont_rollback() for this page */ short int nRef; /* Number of users of this page */ PgHdr *pDirty; /* Dirty pages sorted by PgHdr.pgno */ #ifdef SQLITE_CHECK_PAGES u32 pageHash; #endif /* pPager->psAligned bytes of page data follow this header */ /* Pager.nExtra bytes of local data follow the page data */ }; /* ** For an in-memory only database, some extra information is recorded about ** each page so that changes can be rolled back. (Journal files are not ** used for in-memory databases.) The following information is added to ................................................................................ /* ** Convert a pointer to a PgHdr into a pointer to its data ** and back again. */ #define PGHDR_TO_DATA(P) ((void*)(&(P)[1])) #define DATA_TO_PGHDR(D) (&((PgHdr*)(D))[-1]) #define PGHDR_TO_EXTRA(G,P) ((void*)&((char*)(&(G)[1]))[(P)->psAligned]) #define PGHDR_TO_HIST(P,PGR) \ ((PgHistory*)&((char*)(&(P)[1]))[(PGR)->psAligned+(PGR)->nExtra]) /* ** How big to make the hash table used for locating in-memory pages ** by page number. This macro looks a little silly, but is evaluated ** at compile-time, not run-time (at least for gcc this is true). */ #define N_PG_HASH (\ ................................................................................ int nRec; /* Number of pages written to the journal */ u32 cksumInit; /* Quasi-random value added to every checksum */ int stmtNRec; /* Number of records in stmt subjournal */ int nExtra; /* Add this many bytes to each in-memory page */ void (*xDestructor)(void*,int); /* Call this routine when freeing pages */ void (*xReiniter)(void*,int); /* Call this routine when reloading pages */ int pageSize; /* Number of bytes in a page */ int psAligned; /* pageSize rounded up to a multiple of 8 */ int nPage; /* Total number of in-memory pages */ int nMaxPage; /* High water mark of nPage */ int nRef; /* Number of in-memory pages with PgHdr.nRef>0 */ int mxPage; /* Maximum number of pages to hold in cache */ int nHit, nMiss, nOvfl; /* Cache hits, missing, and LRU overflows */ int nRead,nWrite; /* Database pages read/written */ void (*xCodec)(void*,void*,Pgno,int); /* Routine for en/decoding data */ ................................................................................ pPager->useJournal = useJournal && !memDb; pPager->noReadlock = noReadlock && readOnly; pPager->stmtOpen = 0; pPager->stmtInUse = 0; pPager->nRef = 0; pPager->dbSize = memDb-1; pPager->pageSize = SQLITE_DEFAULT_PAGE_SIZE; pPager->psAligned = FORCE_ALIGNMENT(pPager->pageSize); pPager->stmtSize = 0; pPager->stmtJSize = 0; pPager->nPage = 0; pPager->nMaxPage = 0; pPager->mxPage = 100; pPager->state = PAGER_UNLOCK; pPager->errMask = 0; ................................................................................ ** page data. */ void sqlite3pager_set_reiniter(Pager *pPager, void (*xReinit)(void*,int)){ pPager->xReiniter = xReinit; } /* ** Set the page size. ** ** The page size must only be changed when the cache is empty. */ void sqlite3pager_set_pagesize(Pager *pPager, int pageSize){ assert( pageSize>=512 && pageSize<=SQLITE_MAX_PAGE_SIZE ); pPager->pageSize = pageSize; pPager->psAligned = FORCE_ALIGNMENT(pageSize); } /* ** Read the first N bytes from the beginning of the file into memory ** that pDest points to. No error checking is done. */ void sqlite3pager_read_fileheader(Pager *pPager, int N, unsigned char *pDest){ ................................................................................ } if( pPg==0 ){ /* The requested page is not in the page cache. */ int h; pPager->nMiss++; if( pPager->nPage<pPager->mxPage || pPager->pFirst==0 || MEMDB ){ /* Create a new page */ pPg = sqliteMallocRaw( sizeof(*pPg) + pPager->psAligned + sizeof(u32) + pPager->nExtra + MEMDB*sizeof(PgHistory) ); if( pPg==0 ){ pPager->errMask |= PAGER_ERR_MEM; return SQLITE_NOMEM; } memset(pPg, 0, sizeof(*pPg)); |
| | | | < < | | | | > | < > > | |
14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 ... 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 ... 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 ... 246 247 248 249 250 251 252 253 254 255 256 257 258 259 .... 1655 1656 1657 1658 1659 1660 1661 1662 1663 1664 1665 1666 1667 1668 .... 1710 1711 1712 1713 1714 1715 1716 1717 1718 1719 1720 1721 1722 1723 1724 1725 1726 1727 1728 1729 1730 1731 1732 1733 .... 2372 2373 2374 2375 2376 2377 2378 2379 2380 2381 2382 2383 2384 2385 2386 |
** The pager is used to access a database disk file. It implements ** atomic commit and rollback through the use of a journal file that ** is separate from the database file. The pager also implements file ** locking to prevent two processes from writing the same database ** file simultaneously, or one process from reading the database while ** another is writing. ** ** @(#) $Id: pager.c,v 1.203 2005/05/20 20:01:56 drh Exp $ */ #ifndef SQLITE_OMIT_DISKIO #include "sqliteInt.h" #include "os.h" #include "pager.h" #include <assert.h> #include <string.h> ................................................................................ u8 needSync; /* Sync journal before writing this page */ u8 alwaysRollback; /* Disable dont_rollback() for this page */ short int nRef; /* Number of users of this page */ PgHdr *pDirty; /* Dirty pages sorted by PgHdr.pgno */ #ifdef SQLITE_CHECK_PAGES u32 pageHash; #endif /* pPager->pageSize bytes of page data follow this header */ /* Pager.nExtra bytes of local data follow the page data */ }; /* ** For an in-memory only database, some extra information is recorded about ** each page so that changes can be rolled back. (Journal files are not ** used for in-memory databases.) The following information is added to ................................................................................ /* ** Convert a pointer to a PgHdr into a pointer to its data ** and back again. */ #define PGHDR_TO_DATA(P) ((void*)(&(P)[1])) #define DATA_TO_PGHDR(D) (&((PgHdr*)(D))[-1]) #define PGHDR_TO_EXTRA(G,P) ((void*)&((char*)(&(G)[1]))[(P)->pageSize]) #define PGHDR_TO_HIST(P,PGR) \ ((PgHistory*)&((char*)(&(P)[1]))[(PGR)->pageSize+(PGR)->nExtra]) /* ** How big to make the hash table used for locating in-memory pages ** by page number. This macro looks a little silly, but is evaluated ** at compile-time, not run-time (at least for gcc this is true). */ #define N_PG_HASH (\ ................................................................................ int nRec; /* Number of pages written to the journal */ u32 cksumInit; /* Quasi-random value added to every checksum */ int stmtNRec; /* Number of records in stmt subjournal */ int nExtra; /* Add this many bytes to each in-memory page */ void (*xDestructor)(void*,int); /* Call this routine when freeing pages */ void (*xReiniter)(void*,int); /* Call this routine when reloading pages */ int pageSize; /* Number of bytes in a page */ int nPage; /* Total number of in-memory pages */ int nMaxPage; /* High water mark of nPage */ int nRef; /* Number of in-memory pages with PgHdr.nRef>0 */ int mxPage; /* Maximum number of pages to hold in cache */ int nHit, nMiss, nOvfl; /* Cache hits, missing, and LRU overflows */ int nRead,nWrite; /* Database pages read/written */ void (*xCodec)(void*,void*,Pgno,int); /* Routine for en/decoding data */ ................................................................................ pPager->useJournal = useJournal && !memDb; pPager->noReadlock = noReadlock && readOnly; pPager->stmtOpen = 0; pPager->stmtInUse = 0; pPager->nRef = 0; pPager->dbSize = memDb-1; pPager->pageSize = SQLITE_DEFAULT_PAGE_SIZE; pPager->stmtSize = 0; pPager->stmtJSize = 0; pPager->nPage = 0; pPager->nMaxPage = 0; pPager->mxPage = 100; pPager->state = PAGER_UNLOCK; pPager->errMask = 0; ................................................................................ ** page data. */ void sqlite3pager_set_reiniter(Pager *pPager, void (*xReinit)(void*,int)){ pPager->xReiniter = xReinit; } /* ** Set the page size. Return the new size. If the suggest new page ** size is inappropriate, then an alternative page size is selected ** and returned. */ int sqlite3pager_set_pagesize(Pager *pPager, int pageSize){ assert( pageSize>=512 && pageSize<=SQLITE_MAX_PAGE_SIZE ); if( !pPager->memDb ){ pPager->pageSize = pageSize; } return pPager->pageSize; } /* ** Read the first N bytes from the beginning of the file into memory ** that pDest points to. No error checking is done. */ void sqlite3pager_read_fileheader(Pager *pPager, int N, unsigned char *pDest){ ................................................................................ } if( pPg==0 ){ /* The requested page is not in the page cache. */ int h; pPager->nMiss++; if( pPager->nPage<pPager->mxPage || pPager->pFirst==0 || MEMDB ){ /* Create a new page */ pPg = sqliteMallocRaw( sizeof(*pPg) + pPager->pageSize + sizeof(u32) + pPager->nExtra + MEMDB*sizeof(PgHistory) ); if( pPg==0 ){ pPager->errMask |= PAGER_ERR_MEM; return SQLITE_NOMEM; } memset(pPg, 0, sizeof(*pPg)); |
Changes to src/pager.h.
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
..
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
|
** May you share freely, never taking more than you give. ** ************************************************************************* ** This header file defines the interface that the sqlite page cache ** subsystem. The page cache subsystem reads and writes a file a page ** at a time and provides a journal for rollback. ** ** @(#) $Id: pager.h,v 1.43 2005/03/31 21:02:46 drh Exp $ */ /* ** The default size of a database page. */ #ifndef SQLITE_DEFAULT_PAGE_SIZE # define SQLITE_DEFAULT_PAGE_SIZE 1024 ................................................................................ ** routines: */ int sqlite3pager_open(Pager **ppPager, const char *zFilename, int nExtra, int flags); void sqlite3pager_set_busyhandler(Pager*, BusyHandler *pBusyHandler); void sqlite3pager_set_destructor(Pager*, void(*)(void*,int)); void sqlite3pager_set_reiniter(Pager*, void(*)(void*,int)); void sqlite3pager_set_pagesize(Pager*, int); void sqlite3pager_read_fileheader(Pager*, int, unsigned char*); void sqlite3pager_set_cachesize(Pager*, int); int sqlite3pager_close(Pager *pPager); int sqlite3pager_get(Pager *pPager, Pgno pgno, void **ppPage); void *sqlite3pager_lookup(Pager *pPager, Pgno pgno); int sqlite3pager_ref(void*); int sqlite3pager_unref(void*); |
|
|
|
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
..
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
|
** May you share freely, never taking more than you give. ** ************************************************************************* ** This header file defines the interface that the sqlite page cache ** subsystem. The page cache subsystem reads and writes a file a page ** at a time and provides a journal for rollback. ** ** @(#) $Id: pager.h,v 1.44 2005/05/20 20:01:56 drh Exp $ */ /* ** The default size of a database page. */ #ifndef SQLITE_DEFAULT_PAGE_SIZE # define SQLITE_DEFAULT_PAGE_SIZE 1024 ................................................................................ ** routines: */ int sqlite3pager_open(Pager **ppPager, const char *zFilename, int nExtra, int flags); void sqlite3pager_set_busyhandler(Pager*, BusyHandler *pBusyHandler); void sqlite3pager_set_destructor(Pager*, void(*)(void*,int)); void sqlite3pager_set_reiniter(Pager*, void(*)(void*,int)); int sqlite3pager_set_pagesize(Pager*, int); void sqlite3pager_read_fileheader(Pager*, int, unsigned char*); void sqlite3pager_set_cachesize(Pager*, int); int sqlite3pager_close(Pager *pPager); int sqlite3pager_get(Pager *pPager, Pgno pgno, void **ppPage); void *sqlite3pager_lookup(Pager *pPager, Pgno pgno); int sqlite3pager_ref(void*); int sqlite3pager_unref(void*); |
Changes to test/pagesize.test.
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
..
71
72
73
74
75
76
77
78
79
80
81
82
83
84
|
# May you find forgiveness for yourself and forgive others. # May you share freely, never taking more than you give. # #*********************************************************************** # This file implements regression tests for SQLite library. # This file implements tests for the page_size PRAGMA. # # $Id: pagesize.test,v 1.9 2004/11/23 10:52:51 danielk1977 Exp $ set testdir [file dirname $argv0] source $testdir/tester.tcl # This test script depends entirely on "PRAGMA page_size". So if this # pragma is not available, omit the whole file. ................................................................................ execsql { PRAGMA page_size=1234; PRAGMA page_size } } 8192 foreach PGSZ {512 2048 4096 8192} { do_test pagesize-2.$PGSZ.1 { db close file delete -force test.db sqlite3 db test.db execsql "PRAGMA page_size=$PGSZ" execsql { CREATE TABLE t1(x); |
|
>
>
>
>
>
>
|
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
..
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
|
# May you find forgiveness for yourself and forgive others. # May you share freely, never taking more than you give. # #*********************************************************************** # This file implements regression tests for SQLite library. # This file implements tests for the page_size PRAGMA. # # $Id: pagesize.test,v 1.10 2005/05/20 20:01:56 drh Exp $ set testdir [file dirname $argv0] source $testdir/tester.tcl # This test script depends entirely on "PRAGMA page_size". So if this # pragma is not available, omit the whole file. ................................................................................ execsql { PRAGMA page_size=1234; PRAGMA page_size } } 8192 foreach PGSZ {512 2048 4096 8192} { do_test pagesize-2.$PGSZ.0 { db close sqlite3 db :memory: execsql "PRAGMA page_size=$PGSZ;" execsql {PRAGMA page_size} } 1024 do_test pagesize-2.$PGSZ.1 { db close file delete -force test.db sqlite3 db test.db execsql "PRAGMA page_size=$PGSZ" execsql { CREATE TABLE t1(x); |