d0a537100c
test_delete.c. Accidentally removed by the previous commit. FossilOrigin-Name: 59c70108fd179932ccdd860f93e1cd68b77476d3b1af1af00cf6e378c9984862
157 lines
4.5 KiB
C
157 lines
4.5 KiB
C
/*
|
|
** 2016 September 10
|
|
**
|
|
** 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 file contains test code to delete an SQLite database and all
|
|
** of its associated files. Associated files include:
|
|
**
|
|
** * The journal file.
|
|
** * The wal file.
|
|
** * The SQLITE_ENABLE_8_3_NAMES version of the db, journal or wal files.
|
|
** * Files created by the test_multiplex.c module to extend any of the
|
|
** above.
|
|
*/
|
|
|
|
#ifndef SQLITE_OS_WIN
|
|
# include <unistd.h>
|
|
# include <errno.h>
|
|
#endif
|
|
#include <string.h>
|
|
#include <assert.h>
|
|
#include "sqlite3.h"
|
|
|
|
/* The following #defines are copied from test_multiplex.c */
|
|
#ifndef MX_CHUNK_NUMBER
|
|
# define MX_CHUNK_NUMBER 299
|
|
#endif
|
|
#ifndef SQLITE_MULTIPLEX_JOURNAL_8_3_OFFSET
|
|
# define SQLITE_MULTIPLEX_JOURNAL_8_3_OFFSET 400
|
|
#endif
|
|
#ifndef SQLITE_MULTIPLEX_WAL_8_3_OFFSET
|
|
# define SQLITE_MULTIPLEX_WAL_8_3_OFFSET 700
|
|
#endif
|
|
|
|
/*
|
|
** This routine is a copy of (most of) the code from SQLite function
|
|
** sqlite3FileSuffix3(). It modifies the filename in buffer z in the
|
|
** same way as SQLite does when in 8.3 filenames mode.
|
|
*/
|
|
static void sqlite3Delete83Name(char *z){
|
|
int i, sz;
|
|
sz = (int)strlen(z);
|
|
for(i=sz-1; i>0 && z[i]!='/' && z[i]!='.'; i--){}
|
|
if( z[i]=='.' && (sz>i+4) ) memmove(&z[i+1], &z[sz-3], 4);
|
|
}
|
|
|
|
/*
|
|
** zFile is a filename. Assuming no error occurs, if this file exists,
|
|
** set *pbExists to true and unlink it. Or, if the file does not exist,
|
|
** set *pbExists to false before returning.
|
|
**
|
|
** If an error occurs, non-zero is returned. Or, if no error occurs, zero.
|
|
*/
|
|
static int sqlite3DeleteUnlinkIfExists(
|
|
sqlite3_vfs *pVfs,
|
|
const char *zFile,
|
|
int *pbExists
|
|
){
|
|
int rc = SQLITE_ERROR;
|
|
#if SQLITE_OS_WIN
|
|
if( pVfs ){
|
|
if( pbExists ) *pbExists = 1;
|
|
rc = pVfs->xDelete(pVfs, zFile, 0);
|
|
if( rc==SQLITE_IOERR_DELETE_NOENT ){
|
|
if( pbExists ) *pbExists = 0;
|
|
rc = SQLITE_OK;
|
|
}
|
|
}
|
|
#else
|
|
assert( pVfs==0 );
|
|
rc = access(zFile, F_OK);
|
|
if( rc ){
|
|
if( errno==ENOENT ){
|
|
if( pbExists ) *pbExists = 0;
|
|
rc = SQLITE_OK;
|
|
}
|
|
}else{
|
|
if( pbExists ) *pbExists = 1;
|
|
rc = unlink(zFile);
|
|
}
|
|
#endif
|
|
return rc;
|
|
}
|
|
|
|
/*
|
|
** Delete the database file identified by the string argument passed to this
|
|
** function. The string must contain a filename, not an SQLite URI.
|
|
*/
|
|
SQLITE_API int sqlite3_delete_database(
|
|
const char *zFile /* File to delete */
|
|
){
|
|
char *zBuf; /* Buffer to sprintf() filenames to */
|
|
int nBuf; /* Size of buffer in bytes */
|
|
int rc = 0; /* System error code */
|
|
int i; /* Iterate through azFmt[] and aMFile[] */
|
|
|
|
const char *azFmt[] = { "%s", "%s-journal", "%s-wal", "%s-shm" };
|
|
|
|
struct MFile {
|
|
const char *zFmt;
|
|
int iOffset;
|
|
int b83;
|
|
} aMFile[] = {
|
|
{ "%s%03d", 0, 0 },
|
|
{ "%s-journal%03d", 0, 0 },
|
|
{ "%s-wal%03d", 0, 0 },
|
|
{ "%s%03d", 0, 1 },
|
|
{ "%s-journal%03d", SQLITE_MULTIPLEX_JOURNAL_8_3_OFFSET, 1 },
|
|
{ "%s-wal%03d", SQLITE_MULTIPLEX_WAL_8_3_OFFSET, 1 },
|
|
};
|
|
|
|
#ifdef SQLITE_OS_WIN
|
|
sqlite3_vfs *pVfs = sqlite3_vfs_find("win32");
|
|
#else
|
|
sqlite3_vfs *pVfs = 0;
|
|
#endif
|
|
|
|
/* Allocate a buffer large enough for any of the files that need to be
|
|
** deleted. */
|
|
nBuf = (int)strlen(zFile) + 100;
|
|
zBuf = (char*)sqlite3_malloc(nBuf);
|
|
if( zBuf==0 ) return SQLITE_NOMEM;
|
|
|
|
/* Delete both the regular and 8.3 filenames versions of the database,
|
|
** journal, wal and shm files. */
|
|
for(i=0; rc==0 && i<sizeof(azFmt)/sizeof(azFmt[0]); i++){
|
|
sqlite3_snprintf(nBuf, zBuf, azFmt[i], zFile);
|
|
rc = sqlite3DeleteUnlinkIfExists(pVfs, zBuf, 0);
|
|
if( rc==0 && i!=0 ){
|
|
sqlite3Delete83Name(zBuf);
|
|
rc = sqlite3DeleteUnlinkIfExists(pVfs, zBuf, 0);
|
|
}
|
|
}
|
|
|
|
/* Delete any multiplexor files */
|
|
for(i=0; rc==0 && i<sizeof(aMFile)/sizeof(aMFile[0]); i++){
|
|
struct MFile *p = &aMFile[i];
|
|
int iChunk;
|
|
for(iChunk=1; iChunk<=MX_CHUNK_NUMBER; iChunk++){
|
|
int bExists;
|
|
sqlite3_snprintf(nBuf, zBuf, p->zFmt, zFile, iChunk+p->iOffset);
|
|
if( p->b83 ) sqlite3Delete83Name(zBuf);
|
|
rc = sqlite3DeleteUnlinkIfExists(pVfs, zBuf, &bExists);
|
|
if( bExists==0 || rc!=0 ) break;
|
|
}
|
|
}
|
|
|
|
sqlite3_free(zBuf);
|
|
return (rc ? SQLITE_ERROR : SQLITE_OK);
|
|
}
|