aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authordrh <drh@noemail.net>2017-10-12 19:50:28 +0000
committerdrh <drh@noemail.net>2017-10-12 19:50:28 +0000
commit277ee81babd94ce08cda6c57596759dec457f35b (patch)
treec56ee5f7b1d6d5b0667f38b5f4302d694f7fdd4a /src
parentf02f8a710279125b2ca1cd3367a77d05cf6ca47f (diff)
downloadsqlite-277ee81babd94ce08cda6c57596759dec457f35b.tar.gz
sqlite-277ee81babd94ce08cda6c57596759dec457f35b.zip
Create the new ext/repair folder and move checkfreelist.c there. Remove
checkfreelist.c from the command-line shell (undoing check-in [48418f2e]). FossilOrigin-Name: dfdebd12bfc80b91d234ab328cb6106d5d37ccb79b58e36e556c1a8af640a4ab
Diffstat (limited to 'src')
-rw-r--r--src/shell.c302
-rw-r--r--src/shell.c.in2
2 files changed, 0 insertions, 304 deletions
diff --git a/src/shell.c b/src/shell.c
index 6c14db9fd..2b77d482e 100644
--- a/src/shell.c
+++ b/src/shell.c
@@ -2156,307 +2156,6 @@ int sqlite3_completion_init(
}
/************************* End ../ext/misc/completion.c ********************/
-/************************* Begin ../ext/misc/checkfreelist.c ******************/
-/*
-** 2017 October 11
-**
-** The author disclaims copyright to this source code. In place of
-** 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.
-**
-*************************************************************************
-**
-** This module exports a single C function:
-**
-** int sqlite3_check_freelist(sqlite3 *db, const char *zDb);
-**
-** This function checks the free-list in database zDb (one of "main",
-** "temp", etc.) and reports any errors by invoking the sqlite3_log()
-** function. It returns SQLITE_OK if successful, or an SQLite error
-** code otherwise. It is not an error if the free-list is corrupted but
-** no IO or OOM errors occur.
-**
-** If this file is compiled and loaded as an SQLite loadable extension,
-** it adds an SQL function "checkfreelist" to the database handle, to
-** be invoked as follows:
-**
-** SELECT checkfreelist(<database-name>);
-**
-** This function performs the same checks as sqlite3_check_freelist(),
-** except that it returns all error messages as a single text value,
-** separated by newline characters. If the freelist is not corrupted
-** in any way, an empty string is returned.
-**
-** To compile this module for use as an SQLite loadable extension:
-**
-** gcc -Os -fPIC -shared checkfreelist.c -o checkfreelist.so
-*/
-
-SQLITE_EXTENSION_INIT1
-
-#ifndef SQLITE_AMALGAMATION
-# include <string.h>
-# include <stdio.h>
-# include <stdlib.h>
-# include <assert.h>
-# define ALWAYS(X) 1
-# define NEVER(X) 0
- typedef unsigned char u8;
- typedef unsigned short u16;
- typedef unsigned int u32;
-#define get4byte(x) ( \
- ((u32)((x)[0])<<24) + \
- ((u32)((x)[1])<<16) + \
- ((u32)((x)[2])<<8) + \
- ((u32)((x)[3])) \
-)
-#endif
-
-/*
-** Execute a single PRAGMA statement and return the integer value returned
-** via output parameter (*pnOut).
-**
-** The SQL statement passed as the third argument should be a printf-style
-** format string containing a single "%s" which will be replace by the
-** value passed as the second argument. e.g.
-**
-** sqlGetInteger(db, "main", "PRAGMA %s.page_count", pnOut)
-**
-** executes "PRAGMA main.page_count" and stores the results in (*pnOut).
-*/
-static int sqlGetInteger(
- sqlite3 *db, /* Database handle */
- const char *zDb, /* Database name ("main", "temp" etc.) */
- const char *zFmt, /* SQL statement format */
- u32 *pnOut /* OUT: Integer value */
-){
- int rc, rc2;
- char *zSql;
- sqlite3_stmt *pStmt = 0;
- int bOk = 0;
-
- zSql = sqlite3_mprintf(zFmt, zDb);
- if( zSql==0 ){
- rc = SQLITE_NOMEM;
- }else{
- rc = sqlite3_prepare_v2(db, zSql, -1, &pStmt, 0);
- sqlite3_free(zSql);
- }
-
- if( rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pStmt) ){
- *pnOut = (u32)sqlite3_column_int(pStmt, 0);
- bOk = 1;
- }
-
- rc2 = sqlite3_finalize(pStmt);
- if( rc==SQLITE_OK ) rc = rc2;
- if( rc==SQLITE_OK && bOk==0 ) rc = SQLITE_ERROR;
- return rc;
-}
-
-/*
-** Argument zFmt must be a printf-style format string and must be
-** followed by its required arguments. If argument pzOut is NULL,
-** then the results of printf()ing the format string are passed to
-** sqlite3_log(). Otherwise, they are appended to the string
-** at (*pzOut).
-*/
-static int checkFreelistError(char **pzOut, const char *zFmt, ...){
- int rc = SQLITE_OK;
- char *zErr = 0;
- va_list ap;
-
- va_start(ap, zFmt);
- zErr = sqlite3_vmprintf(zFmt, ap);
- if( zErr==0 ){
- rc = SQLITE_NOMEM;
- }else{
- if( pzOut ){
- *pzOut = sqlite3_mprintf("%s%z%s", *pzOut?"\n":"", *pzOut, zErr);
- if( *pzOut==0 ) rc = SQLITE_NOMEM;
- }else{
- sqlite3_log(SQLITE_ERROR, "checkfreelist: %s", zErr);
- }
- sqlite3_free(zErr);
- }
- va_end(ap);
- return rc;
-}
-
-static int checkFreelist(
- sqlite3 *db,
- const char *zDb,
- char **pzOut
-){
- /* This query returns one row for each page on the free list. Each row has
- ** two columns - the page number and page content. */
- const char *zTrunk =
- "WITH freelist_trunk(i, d, n) AS ("
- "SELECT 1, NULL, sqlite_readint32(data, 32) "
- "FROM sqlite_dbpage(:1) WHERE pgno=1 "
- "UNION ALL "
- "SELECT n, data, sqlite_readint32(data) "
- "FROM freelist_trunk, sqlite_dbpage(:1) WHERE pgno=n "
- ")"
- "SELECT i, d FROM freelist_trunk WHERE i!=1;";
-
- int rc, rc2; /* Return code */
- sqlite3_stmt *pTrunk = 0; /* Compilation of zTrunk */
- u32 nPage = 0; /* Number of pages in db */
- u32 nExpected = 0; /* Expected number of free pages */
- u32 nFree = 0; /* Number of pages on free list */
-
- if( zDb==0 ) zDb = "main";
-
- if( (rc = sqlGetInteger(db, zDb, "PRAGMA %s.page_count", &nPage))
- || (rc = sqlGetInteger(db, zDb, "PRAGMA %s.freelist_count", &nExpected))
- ){
- return rc;
- }
-
- rc = sqlite3_prepare_v2(db, zTrunk, -1, &pTrunk, 0);
- if( rc!=SQLITE_OK ) return rc;
- sqlite3_bind_text(pTrunk, 1, zDb, -1, SQLITE_STATIC);
- while( rc==SQLITE_OK && sqlite3_step(pTrunk)==SQLITE_ROW ){
- u32 i;
- u32 iTrunk = (u32)sqlite3_column_int(pTrunk, 0);
- const u8 *aData = (const u8*)sqlite3_column_blob(pTrunk, 1);
- int nData = sqlite3_column_bytes(pTrunk, 1);
- u32 iNext = get4byte(&aData[0]);
- u32 nLeaf = get4byte(&aData[4]);
-
- if( nLeaf>((nData/4)-2-6) ){
- rc = checkFreelistError(pzOut,
- "leaf count out of range (%d) on trunk page %d",
- (int)nLeaf, (int)iTrunk
- );
- nLeaf = (nData/4) - 2 - 6;
- }
-
- nFree += 1+nLeaf;
- if( iNext>nPage ){
- rc = checkFreelistError(pzOut,
- "trunk page %d is out of range", (int)iNext
- );
- }
-
- for(i=0; rc==SQLITE_OK && i<nLeaf; i++){
- u32 iLeaf = get4byte(&aData[8 + 4*i]);
- if( iLeaf==0 || iLeaf>nPage ){
- rc = checkFreelistError(pzOut,
- "leaf page %d is out of range (child %d of trunk page %d)",
- (int)iLeaf, (int)i, (int)iTrunk
- );
- }
- }
- }
-
- if( rc==SQLITE_OK && nFree!=nExpected ){
- rc = checkFreelistError(pzOut,
- "free-list count mismatch: actual=%d header=%d",
- (int)nFree, (int)nExpected
- );
- }
-
- rc2 = sqlite3_finalize(pTrunk);
- if( rc==SQLITE_OK ) rc = rc2;
- return rc;
-}
-
-int sqlite3_check_freelist(sqlite3 *db, const char *zDb){
- return checkFreelist(db, zDb, 0);
-}
-
-static void checkfreelist_function(
- sqlite3_context *pCtx,
- int nArg,
- sqlite3_value **apArg
-){
- const char *zDb;
- int rc;
- char *zOut = 0;
- sqlite3 *db = sqlite3_context_db_handle(pCtx);
-
- assert( nArg==1 );
- zDb = (const char*)sqlite3_value_text(apArg[0]);
- rc = checkFreelist(db, zDb, &zOut);
- if( rc==SQLITE_OK ){
- sqlite3_result_text(pCtx, zOut?zOut:"ok", -1, SQLITE_TRANSIENT);
- }else{
- sqlite3_result_error_code(pCtx, rc);
- }
-
- sqlite3_free(zOut);
-}
-
-/*
-** An SQL function invoked as follows:
-**
-** sqlite_readint32(BLOB) -- Decode 32-bit integer from start of blob
-*/
-static void readint_function(
- sqlite3_context *pCtx,
- int nArg,
- sqlite3_value **apArg
-){
- const u8 *zBlob;
- int nBlob;
- int iOff = 0;
- u32 iRet = 0;
-
- if( nArg!=1 && nArg!=2 ){
- sqlite3_result_error(
- pCtx, "wrong number of arguments to function sqlite_readint32()", -1
- );
- return;
- }
- if( nArg==2 ){
- iOff = sqlite3_value_int(apArg[1]);
- }
-
- zBlob = sqlite3_value_blob(apArg[0]);
- nBlob = sqlite3_value_bytes(apArg[0]);
-
- if( nBlob>=(iOff+4) ){
- iRet = get4byte(&zBlob[iOff]);
- }
-
- sqlite3_result_int64(pCtx, (sqlite3_int64)iRet);
-}
-
-/*
-** Register the SQL functions.
-*/
-static int cflRegister(sqlite3 *db){
- int rc = sqlite3_create_function(
- db, "sqlite_readint32", -1, SQLITE_UTF8, 0, readint_function, 0, 0
- );
- if( rc!=SQLITE_OK ) return rc;
- rc = sqlite3_create_function(
- db, "checkfreelist", 1, SQLITE_UTF8, 0, checkfreelist_function, 0, 0
- );
- return rc;
-}
-
-/*
-** Extension load function.
-*/
-#ifdef _WIN32
-
-#endif
-int sqlite3_checkfreelist_init(
- sqlite3 *db,
- char **pzErrMsg,
- const sqlite3_api_routines *pApi
-){
- SQLITE_EXTENSION_INIT2(pApi);
- return cflRegister(db);
-}
-
-/************************* End ../ext/misc/checkfreelist.c ********************/
#if defined(SQLITE_ENABLE_SESSION)
/*
@@ -4547,7 +4246,6 @@ static void open_db(ShellState *p, int keepAlive){
sqlite3_fileio_init(p->db, 0, 0);
sqlite3_shathree_init(p->db, 0, 0);
sqlite3_completion_init(p->db, 0, 0);
- sqlite3_checkfreelist_init(p->db, 0, 0);
sqlite3_create_function(p->db, "shell_add_schema", 2, SQLITE_UTF8, 0,
shellAddSchemaName, 0, 0);
}
diff --git a/src/shell.c.in b/src/shell.c.in
index de170887f..54a61b945 100644
--- a/src/shell.c.in
+++ b/src/shell.c.in
@@ -796,7 +796,6 @@ static void shellAddSchemaName(
INCLUDE ../ext/misc/shathree.c
INCLUDE ../ext/misc/fileio.c
INCLUDE ../ext/misc/completion.c
-INCLUDE ../ext/misc/checkfreelist.c
#if defined(SQLITE_ENABLE_SESSION)
/*
@@ -2887,7 +2886,6 @@ static void open_db(ShellState *p, int keepAlive){
sqlite3_fileio_init(p->db, 0, 0);
sqlite3_shathree_init(p->db, 0, 0);
sqlite3_completion_init(p->db, 0, 0);
- sqlite3_checkfreelist_init(p->db, 0, 0);
sqlite3_create_function(p->db, "shell_add_schema", 2, SQLITE_UTF8, 0,
shellAddSchemaName, 0, 0);
}