4 ** The author disclaims copyright to this source code. In place of
5 ** a legal notice, here is a blessing:
7 ** May you do good and not evil.
8 ** May you find forgiveness for yourself and forgive others.
9 ** May you share freely, never taking more than you give.
11 ******************************************************************************
13 ** This file contains code that modified the OS layer in order to simulate
14 ** different device types (by overriding the return values of the
15 ** xDeviceCharacteristics() and xSectorSize() methods).
17 #if SQLITE_TEST /* This file is used for testing only */
20 #include "sqliteInt.h"
23 ** Maximum pathname length supported by the devsym backend.
25 #define DEVSYM_MAX_PATHNAME 512
28 ** Name used to identify this VFS.
30 #define DEVSYM_VFS_NAME "devsym"
32 typedef struct devsym_file devsym_file
;
39 ** Method declarations for devsym_file.
41 static int devsymClose(sqlite3_file
*);
42 static int devsymRead(sqlite3_file
*, void*, int iAmt
, sqlite3_int64 iOfst
);
43 static int devsymWrite(sqlite3_file
*,const void*,int iAmt
, sqlite3_int64 iOfst
);
44 static int devsymTruncate(sqlite3_file
*, sqlite3_int64 size
);
45 static int devsymSync(sqlite3_file
*, int flags
);
46 static int devsymFileSize(sqlite3_file
*, sqlite3_int64
*pSize
);
47 static int devsymLock(sqlite3_file
*, int);
48 static int devsymUnlock(sqlite3_file
*, int);
49 static int devsymCheckReservedLock(sqlite3_file
*, int *);
50 static int devsymFileControl(sqlite3_file
*, int op
, void *pArg
);
51 static int devsymSectorSize(sqlite3_file
*);
52 static int devsymDeviceCharacteristics(sqlite3_file
*);
53 static int devsymShmLock(sqlite3_file
*,int,int,int);
54 static int devsymShmMap(sqlite3_file
*,int,int,int, void volatile **);
55 static void devsymShmBarrier(sqlite3_file
*);
56 static int devsymShmUnmap(sqlite3_file
*,int);
59 ** Method declarations for devsym_vfs.
61 static int devsymOpen(sqlite3_vfs
*, const char *, sqlite3_file
*, int , int *);
62 static int devsymDelete(sqlite3_vfs
*, const char *zName
, int syncDir
);
63 static int devsymAccess(sqlite3_vfs
*, const char *zName
, int flags
, int *);
64 static int devsymFullPathname(sqlite3_vfs
*, const char *zName
, int, char *zOut
);
65 #ifndef SQLITE_OMIT_LOAD_EXTENSION
66 static void *devsymDlOpen(sqlite3_vfs
*, const char *zFilename
);
67 static void devsymDlError(sqlite3_vfs
*, int nByte
, char *zErrMsg
);
68 static void (*devsymDlSym(sqlite3_vfs
*,void*, const char *zSymbol
))(void);
69 static void devsymDlClose(sqlite3_vfs
*, void*);
70 #endif /* SQLITE_OMIT_LOAD_EXTENSION */
71 static int devsymRandomness(sqlite3_vfs
*, int nByte
, char *zOut
);
72 static int devsymSleep(sqlite3_vfs
*, int microseconds
);
73 static int devsymCurrentTime(sqlite3_vfs
*, double*);
75 static sqlite3_vfs devsym_vfs
= {
77 sizeof(devsym_file
), /* szOsFile */
78 DEVSYM_MAX_PATHNAME
, /* mxPathname */
80 DEVSYM_VFS_NAME
, /* zName */
82 devsymOpen
, /* xOpen */
83 devsymDelete
, /* xDelete */
84 devsymAccess
, /* xAccess */
85 devsymFullPathname
, /* xFullPathname */
86 #ifndef SQLITE_OMIT_LOAD_EXTENSION
87 devsymDlOpen
, /* xDlOpen */
88 devsymDlError
, /* xDlError */
89 devsymDlSym
, /* xDlSym */
90 devsymDlClose
, /* xDlClose */
96 #endif /* SQLITE_OMIT_LOAD_EXTENSION */
97 devsymRandomness
, /* xRandomness */
98 devsymSleep
, /* xSleep */
99 devsymCurrentTime
, /* xCurrentTime */
100 0, /* xGetLastError */
101 0 /* xCurrentTimeInt64 */
104 static sqlite3_io_methods devsym_io_methods
= {
106 devsymClose
, /* xClose */
107 devsymRead
, /* xRead */
108 devsymWrite
, /* xWrite */
109 devsymTruncate
, /* xTruncate */
110 devsymSync
, /* xSync */
111 devsymFileSize
, /* xFileSize */
112 devsymLock
, /* xLock */
113 devsymUnlock
, /* xUnlock */
114 devsymCheckReservedLock
, /* xCheckReservedLock */
115 devsymFileControl
, /* xFileControl */
116 devsymSectorSize
, /* xSectorSize */
117 devsymDeviceCharacteristics
, /* xDeviceCharacteristics */
118 devsymShmMap
, /* xShmMap */
119 devsymShmLock
, /* xShmLock */
120 devsymShmBarrier
, /* xShmBarrier */
121 devsymShmUnmap
/* xShmUnmap */
124 struct DevsymGlobal
{
129 struct DevsymGlobal g
= {0, 0, 512};
132 ** Close an devsym-file.
134 static int devsymClose(sqlite3_file
*pFile
){
135 devsym_file
*p
= (devsym_file
*)pFile
;
136 return sqlite3OsClose(p
->pReal
);
140 ** Read data from an devsym-file.
142 static int devsymRead(
148 devsym_file
*p
= (devsym_file
*)pFile
;
149 return sqlite3OsRead(p
->pReal
, zBuf
, iAmt
, iOfst
);
153 ** Write data to an devsym-file.
155 static int devsymWrite(
161 devsym_file
*p
= (devsym_file
*)pFile
;
162 return sqlite3OsWrite(p
->pReal
, zBuf
, iAmt
, iOfst
);
166 ** Truncate an devsym-file.
168 static int devsymTruncate(sqlite3_file
*pFile
, sqlite_int64 size
){
169 devsym_file
*p
= (devsym_file
*)pFile
;
170 return sqlite3OsTruncate(p
->pReal
, size
);
174 ** Sync an devsym-file.
176 static int devsymSync(sqlite3_file
*pFile
, int flags
){
177 devsym_file
*p
= (devsym_file
*)pFile
;
178 return sqlite3OsSync(p
->pReal
, flags
);
182 ** Return the current file-size of an devsym-file.
184 static int devsymFileSize(sqlite3_file
*pFile
, sqlite_int64
*pSize
){
185 devsym_file
*p
= (devsym_file
*)pFile
;
186 return sqlite3OsFileSize(p
->pReal
, pSize
);
190 ** Lock an devsym-file.
192 static int devsymLock(sqlite3_file
*pFile
, int eLock
){
193 devsym_file
*p
= (devsym_file
*)pFile
;
194 return sqlite3OsLock(p
->pReal
, eLock
);
198 ** Unlock an devsym-file.
200 static int devsymUnlock(sqlite3_file
*pFile
, int eLock
){
201 devsym_file
*p
= (devsym_file
*)pFile
;
202 return sqlite3OsUnlock(p
->pReal
, eLock
);
206 ** Check if another file-handle holds a RESERVED lock on an devsym-file.
208 static int devsymCheckReservedLock(sqlite3_file
*pFile
, int *pResOut
){
209 devsym_file
*p
= (devsym_file
*)pFile
;
210 return sqlite3OsCheckReservedLock(p
->pReal
, pResOut
);
214 ** File control method. For custom operations on an devsym-file.
216 static int devsymFileControl(sqlite3_file
*pFile
, int op
, void *pArg
){
217 devsym_file
*p
= (devsym_file
*)pFile
;
218 return sqlite3OsFileControl(p
->pReal
, op
, pArg
);
222 ** Return the sector-size in bytes for an devsym-file.
224 static int devsymSectorSize(sqlite3_file
*pFile
){
225 return g
.iSectorSize
;
229 ** Return the device characteristic flags supported by an devsym-file.
231 static int devsymDeviceCharacteristics(sqlite3_file
*pFile
){
232 return g
.iDeviceChar
;
236 ** Shared-memory methods are all pass-thrus.
238 static int devsymShmLock(sqlite3_file
*pFile
, int ofst
, int n
, int flags
){
239 devsym_file
*p
= (devsym_file
*)pFile
;
240 return sqlite3OsShmLock(p
->pReal
, ofst
, n
, flags
);
242 static int devsymShmMap(
249 devsym_file
*p
= (devsym_file
*)pFile
;
250 return sqlite3OsShmMap(p
->pReal
, iRegion
, szRegion
, isWrite
, pp
);
252 static void devsymShmBarrier(sqlite3_file
*pFile
){
253 devsym_file
*p
= (devsym_file
*)pFile
;
254 sqlite3OsShmBarrier(p
->pReal
);
256 static int devsymShmUnmap(sqlite3_file
*pFile
, int delFlag
){
257 devsym_file
*p
= (devsym_file
*)pFile
;
258 return sqlite3OsShmUnmap(p
->pReal
, delFlag
);
264 ** Open an devsym file handle.
266 static int devsymOpen(
274 devsym_file
*p
= (devsym_file
*)pFile
;
275 p
->pReal
= (sqlite3_file
*)&p
[1];
276 rc
= sqlite3OsOpen(g
.pVfs
, zName
, p
->pReal
, flags
, pOutFlags
);
277 if( p
->pReal
->pMethods
){
278 pFile
->pMethods
= &devsym_io_methods
;
284 ** Delete the file located at zPath. If the dirSync argument is true,
285 ** ensure the file-system modifications are synced to disk before
288 static int devsymDelete(sqlite3_vfs
*pVfs
, const char *zPath
, int dirSync
){
289 return sqlite3OsDelete(g
.pVfs
, zPath
, dirSync
);
293 ** Test for access permissions. Return true if the requested permission
294 ** is available, or false otherwise.
296 static int devsymAccess(
302 return sqlite3OsAccess(g
.pVfs
, zPath
, flags
, pResOut
);
306 ** Populate buffer zOut with the full canonical pathname corresponding
307 ** to the pathname in zPath. zOut is guaranteed to point to a buffer
308 ** of at least (DEVSYM_MAX_PATHNAME+1) bytes.
310 static int devsymFullPathname(
316 return sqlite3OsFullPathname(g
.pVfs
, zPath
, nOut
, zOut
);
319 #ifndef SQLITE_OMIT_LOAD_EXTENSION
321 ** Open the dynamic library located at zPath and return a handle.
323 static void *devsymDlOpen(sqlite3_vfs
*pVfs
, const char *zPath
){
324 return sqlite3OsDlOpen(g
.pVfs
, zPath
);
328 ** Populate the buffer zErrMsg (size nByte bytes) with a human readable
329 ** utf-8 string describing the most recent error encountered associated
330 ** with dynamic libraries.
332 static void devsymDlError(sqlite3_vfs
*pVfs
, int nByte
, char *zErrMsg
){
333 sqlite3OsDlError(g
.pVfs
, nByte
, zErrMsg
);
337 ** Return a pointer to the symbol zSymbol in the dynamic library pHandle.
339 static void (*devsymDlSym(sqlite3_vfs
*pVfs
, void *p
, const char *zSym
))(void){
340 return sqlite3OsDlSym(g
.pVfs
, p
, zSym
);
344 ** Close the dynamic library handle pHandle.
346 static void devsymDlClose(sqlite3_vfs
*pVfs
, void *pHandle
){
347 sqlite3OsDlClose(g
.pVfs
, pHandle
);
349 #endif /* SQLITE_OMIT_LOAD_EXTENSION */
352 ** Populate the buffer pointed to by zBufOut with nByte bytes of
355 static int devsymRandomness(sqlite3_vfs
*pVfs
, int nByte
, char *zBufOut
){
356 return sqlite3OsRandomness(g
.pVfs
, nByte
, zBufOut
);
360 ** Sleep for nMicro microseconds. Return the number of microseconds
363 static int devsymSleep(sqlite3_vfs
*pVfs
, int nMicro
){
364 return sqlite3OsSleep(g
.pVfs
, nMicro
);
368 ** Return the current time as a Julian Day number in *pTimeOut.
370 static int devsymCurrentTime(sqlite3_vfs
*pVfs
, double *pTimeOut
){
371 return g
.pVfs
->xCurrentTime(g
.pVfs
, pTimeOut
);
376 ** This procedure registers the devsym vfs with SQLite. If the argument is
377 ** true, the devsym vfs becomes the new default vfs. It is the only publicly
378 ** available function in this file.
380 void devsym_register(int iDeviceChar
, int iSectorSize
){
382 g
.pVfs
= sqlite3_vfs_find(0);
383 devsym_vfs
.szOsFile
+= g
.pVfs
->szOsFile
;
384 sqlite3_vfs_register(&devsym_vfs
, 0);
386 if( iDeviceChar
>=0 ){
387 g
.iDeviceChar
= iDeviceChar
;
391 if( iSectorSize
>=0 ){
392 g
.iSectorSize
= iSectorSize
;