/ Hex Artifact Content
Login

Artifact a6223d9d938aba83f20611a2c01680d8043cd2f7:


0000: 2f 2a 0a 2a 2a 20 32 30 30 34 20 4d 61 79 20 32  /*.** 2004 May 2
0010: 32 0a 2a 2a 0a 2a 2a 20 54 68 65 20 61 75 74 68  2.**.** The auth
0020: 6f 72 20 64 69 73 63 6c 61 69 6d 73 20 63 6f 70  or disclaims cop
0030: 79 72 69 67 68 74 20 74 6f 20 74 68 69 73 20 73  yright to this s
0040: 6f 75 72 63 65 20 63 6f 64 65 2e 20 20 49 6e 20  ource code.  In 
0050: 70 6c 61 63 65 20 6f 66 0a 2a 2a 20 61 20 6c 65  place of.** a le
0060: 67 61 6c 20 6e 6f 74 69 63 65 2c 20 68 65 72 65  gal notice, here
0070: 20 69 73 20 61 20 62 6c 65 73 73 69 6e 67 3a 0a   is a blessing:.
0080: 2a 2a 0a 2a 2a 20 20 20 20 4d 61 79 20 79 6f 75  **.**    May you
0090: 20 64 6f 20 67 6f 6f 64 20 61 6e 64 20 6e 6f 74   do good and not
00a0: 20 65 76 69 6c 2e 0a 2a 2a 20 20 20 20 4d 61 79   evil..**    May
00b0: 20 79 6f 75 20 66 69 6e 64 20 66 6f 72 67 69 76   you find forgiv
00c0: 65 6e 65 73 73 20 66 6f 72 20 79 6f 75 72 73 65  eness for yourse
00d0: 6c 66 20 61 6e 64 20 66 6f 72 67 69 76 65 20 6f  lf and forgive o
00e0: 74 68 65 72 73 2e 0a 2a 2a 20 20 20 20 4d 61 79  thers..**    May
00f0: 20 79 6f 75 20 73 68 61 72 65 20 66 72 65 65 6c   you share freel
0100: 79 2c 20 6e 65 76 65 72 20 74 61 6b 69 6e 67 20  y, never taking 
0110: 6d 6f 72 65 20 74 68 61 6e 20 79 6f 75 20 67 69  more than you gi
0120: 76 65 2e 0a 2a 2a 0a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ve..**.*********
0130: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0140: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0150: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0160: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0170: 2a 2a 2a 2a 2a 0a 2a 2a 0a 2a 2a 20 54 68 69 73  *****.**.** This
0180: 20 66 69 6c 65 20 63 6f 6e 74 61 69 6e 73 20 63   file contains c
0190: 6f 64 65 20 74 68 61 74 20 6d 6f 64 69 66 69 65  ode that modifie
01a0: 64 20 74 68 65 20 4f 53 20 6c 61 79 65 72 20 69  d the OS layer i
01b0: 6e 20 6f 72 64 65 72 20 74 6f 20 73 69 6d 75 6c  n order to simul
01c0: 61 74 65 0a 2a 2a 20 74 68 65 20 65 66 66 65 63  ate.** the effec
01d0: 74 20 6f 6e 20 74 68 65 20 64 61 74 61 62 61 73  t on the databas
01e0: 65 20 66 69 6c 65 20 6f 66 20 61 6e 20 4f 53 20  e file of an OS 
01f0: 63 72 61 73 68 20 6f 72 20 70 6f 77 65 72 20 66  crash or power f
0200: 61 69 6c 75 72 65 2e 20 20 54 68 69 73 0a 2a 2a  ailure.  This.**
0210: 20 69 73 20 75 73 65 64 20 74 6f 20 74 65 73 74   is used to test
0220: 20 74 68 65 20 61 62 69 6c 69 74 79 20 6f 66 20   the ability of 
0230: 53 51 4c 69 74 65 20 74 6f 20 72 65 63 6f 76 65  SQLite to recove
0240: 72 20 66 72 6f 6d 20 74 68 6f 73 65 20 73 69 74  r from those sit
0250: 75 61 74 69 6f 6e 73 2e 0a 2a 2f 0a 23 69 66 20  uations..*/.#if 
0260: 53 51 4c 49 54 45 5f 54 45 53 54 20 20 20 20 20  SQLITE_TEST     
0270: 20 20 20 20 20 2f 2a 20 54 68 69 73 20 66 69 6c       /* This fil
0280: 65 20 69 73 20 75 73 65 64 20 66 6f 72 20 74 65  e is used for te
0290: 73 74 69 6e 67 20 6f 6e 6c 79 20 2a 2f 0a 23 69  sting only */.#i
02a0: 6e 63 6c 75 64 65 20 22 73 71 6c 69 74 65 49 6e  nclude "sqliteIn
02b0: 74 2e 68 22 0a 23 69 6e 63 6c 75 64 65 20 22 74  t.h".#include "t
02c0: 63 6c 2e 68 22 0a 0a 23 69 66 6e 64 65 66 20 53  cl.h"..#ifndef S
02d0: 51 4c 49 54 45 5f 4f 4d 49 54 5f 44 49 53 4b 49  QLITE_OMIT_DISKI
02e0: 4f 20 20 2f 2a 20 54 68 69 73 20 66 69 6c 65 20  O  /* This file 
02f0: 69 73 20 61 20 6e 6f 2d 6f 70 20 69 66 20 64 69  is a no-op if di
0300: 73 6b 20 49 2f 4f 20 69 73 20 64 69 73 61 62 6c  sk I/O is disabl
0310: 65 64 20 2a 2f 0a 0a 2f 2a 20 23 64 65 66 69 6e  ed */../* #defin
0320: 65 20 54 52 41 43 45 5f 43 52 41 53 48 54 45 53  e TRACE_CRASHTES
0330: 54 20 2a 2f 0a 0a 74 79 70 65 64 65 66 20 73 74  T */..typedef st
0340: 72 75 63 74 20 43 72 61 73 68 46 69 6c 65 20 43  ruct CrashFile C
0350: 72 61 73 68 46 69 6c 65 3b 0a 74 79 70 65 64 65  rashFile;.typede
0360: 66 20 73 74 72 75 63 74 20 43 72 61 73 68 47 6c  f struct CrashGl
0370: 6f 62 61 6c 20 43 72 61 73 68 47 6c 6f 62 61 6c  obal CrashGlobal
0380: 3b 0a 74 79 70 65 64 65 66 20 73 74 72 75 63 74  ;.typedef struct
0390: 20 57 72 69 74 65 42 75 66 66 65 72 20 57 72 69   WriteBuffer Wri
03a0: 74 65 42 75 66 66 65 72 3b 0a 0a 2f 2a 0a 2a 2a  teBuffer;../*.**
03b0: 20 4d 65 74 68 6f 64 3a 0a 2a 2a 0a 2a 2a 20 20   Method:.**.**  
03c0: 20 54 68 69 73 20 6c 61 79 65 72 20 69 73 20 69   This layer is i
03d0: 6d 70 6c 65 6d 65 6e 74 65 64 20 61 73 20 61 20  mplemented as a 
03e0: 77 72 61 70 70 65 72 20 61 72 6f 75 6e 64 20 74  wrapper around t
03f0: 68 65 20 22 72 65 61 6c 22 20 0a 2a 2a 20 20 20  he "real" .**   
0400: 73 71 6c 69 74 65 33 5f 66 69 6c 65 20 6f 62 6a  sqlite3_file obj
0410: 65 63 74 20 66 6f 72 20 74 68 65 20 68 6f 73 74  ect for the host
0420: 20 73 79 73 74 65 6d 2e 20 45 61 63 68 20 74 69   system. Each ti
0430: 6d 65 20 64 61 74 61 20 69 73 20 0a 2a 2a 20 20  me data is .**  
0440: 20 77 72 69 74 74 65 6e 20 74 6f 20 74 68 65 20   written to the 
0450: 66 69 6c 65 20 6f 62 6a 65 63 74 2c 20 69 6e 73  file object, ins
0460: 74 65 61 64 20 6f 66 20 62 65 69 6e 67 20 77 72  tead of being wr
0470: 69 74 74 65 6e 20 74 6f 20 74 68 65 0a 2a 2a 20  itten to the.** 
0480: 20 20 75 6e 64 65 72 6c 79 69 6e 67 20 66 69 6c    underlying fil
0490: 65 2c 20 74 68 65 20 77 72 69 74 65 20 6f 70 65  e, the write ope
04a0: 72 61 74 69 6f 6e 20 69 73 20 73 74 6f 72 65 64  ration is stored
04b0: 20 69 6e 20 61 6e 20 69 6e 2d 6d 65 6d 6f 72 79   in an in-memory
04c0: 20 0a 2a 2a 20 20 20 73 74 72 75 63 74 75 72 65   .**   structure
04d0: 20 28 74 79 70 65 20 57 72 69 74 65 42 75 66 66   (type WriteBuff
04e0: 65 72 29 2e 20 54 68 69 73 20 73 74 72 75 63 74  er). This struct
04f0: 75 72 65 20 69 73 20 70 6c 61 63 65 64 20 61 74  ure is placed at
0500: 20 74 68 65 0a 2a 2a 20 20 20 65 6e 64 20 6f 66   the.**   end of
0510: 20 61 20 67 6c 6f 62 61 6c 20 6f 72 64 65 72 65   a global ordere
0520: 64 20 6c 69 73 74 20 28 74 68 65 20 77 72 69 74  d list (the writ
0530: 65 2d 6c 69 73 74 29 2e 0a 2a 2a 0a 2a 2a 20 20  e-list)..**.**  
0540: 20 57 68 65 6e 20 64 61 74 61 20 69 73 20 72 65   When data is re
0550: 61 64 20 66 72 6f 6d 20 61 20 66 69 6c 65 20 6f  ad from a file o
0560: 62 6a 65 63 74 2c 20 74 68 65 20 72 65 71 75 65  bject, the reque
0570: 73 74 65 64 20 72 65 67 69 6f 6e 20 69 73 0a 2a  sted region is.*
0580: 2a 20 20 20 66 69 72 73 74 20 72 65 74 72 69 65  *   first retrie
0590: 76 65 64 20 66 72 6f 6d 20 74 68 65 20 72 65 61  ved from the rea
05a0: 6c 20 66 69 6c 65 2e 20 54 68 65 20 77 72 69 74  l file. The writ
05b0: 65 2d 6c 69 73 74 20 69 73 20 74 68 65 6e 20 0a  e-list is then .
05c0: 2a 2a 20 20 20 74 72 61 76 65 72 73 65 64 20 61  **   traversed a
05d0: 6e 64 20 64 61 74 61 20 63 6f 70 69 65 64 20 66  nd data copied f
05e0: 72 6f 6d 20 61 6e 79 20 6f 76 65 72 6c 61 70 70  rom any overlapp
05f0: 69 6e 67 20 57 72 69 74 65 42 75 66 66 65 72 20  ing WriteBuffer 
0600: 0a 2a 2a 20 20 20 73 74 72 75 63 74 75 72 65 73  .**   structures
0610: 20 74 6f 20 74 68 65 20 6f 75 74 70 75 74 20 62   to the output b
0620: 75 66 66 65 72 2e 20 69 2e 65 2e 20 61 20 72 65  uffer. i.e. a re
0630: 61 64 28 29 20 6f 70 65 72 61 74 69 6f 6e 20 66  ad() operation f
0640: 6f 6c 6c 6f 77 69 6e 67 0a 2a 2a 20 20 20 6f 6e  ollowing.**   on
0650: 65 20 6f 72 20 6d 6f 72 65 20 77 72 69 74 65 28  e or more write(
0660: 29 20 6f 70 65 72 61 74 69 6f 6e 73 20 77 6f 72  ) operations wor
0670: 6b 73 20 61 73 20 65 78 70 65 63 74 65 64 2c 20  ks as expected, 
0680: 65 76 65 6e 20 69 66 20 6e 6f 0a 2a 2a 20 20 20  even if no.**   
0690: 64 61 74 61 20 68 61 73 20 61 63 74 75 61 6c 6c  data has actuall
06a0: 79 20 62 65 65 6e 20 77 72 69 74 74 65 6e 20 6f  y been written o
06b0: 75 74 20 74 6f 20 74 68 65 20 72 65 61 6c 20 66  ut to the real f
06c0: 69 6c 65 2e 0a 2a 2a 0a 2a 2a 20 20 20 57 68 65  ile..**.**   Whe
06d0: 6e 20 61 20 66 73 79 6e 63 28 29 20 6f 70 65 72  n a fsync() oper
06e0: 61 74 69 6f 6e 20 69 73 20 70 65 72 66 6f 72 6d  ation is perform
06f0: 65 64 2c 20 61 6e 20 6f 70 65 72 61 74 69 6e 67  ed, an operating
0700: 20 73 79 73 74 65 6d 20 63 72 61 73 68 20 0a 2a   system crash .*
0710: 2a 20 20 20 6d 61 79 20 62 65 20 73 69 6d 75 6c  *   may be simul
0720: 61 74 65 64 2c 20 69 6e 20 77 68 69 63 68 20 63  ated, in which c
0730: 61 73 65 20 65 78 69 74 28 2d 31 29 20 69 73 20  ase exit(-1) is 
0740: 63 61 6c 6c 65 64 20 28 74 68 65 20 63 61 6c 6c  called (the call
0750: 20 74 6f 20 0a 2a 2a 20 20 20 78 53 79 6e 63 28   to .**   xSync(
0760: 29 20 6e 65 76 65 72 20 72 65 74 75 72 6e 73 29  ) never returns)
0770: 2e 20 57 68 65 74 68 65 72 20 6f 72 20 6e 6f 74  . Whether or not
0780: 20 61 20 63 72 61 73 68 20 69 73 20 73 69 6d 75   a crash is simu
0790: 6c 61 74 65 64 2c 0a 2a 2a 20 20 20 74 68 65 20  lated,.**   the 
07a0: 64 61 74 61 20 61 73 73 6f 63 69 61 74 65 64 20  data associated 
07b0: 77 69 74 68 20 61 20 73 75 62 73 65 74 20 6f 66  with a subset of
07c0: 20 74 68 65 20 57 72 69 74 65 42 75 66 66 65 72   the WriteBuffer
07d0: 20 73 74 72 75 63 74 75 72 65 73 20 0a 2a 2a 20   structures .** 
07e0: 20 20 73 74 6f 72 65 64 20 69 6e 20 74 68 65 20    stored in the 
07f0: 77 72 69 74 65 2d 6c 69 73 74 20 69 73 20 77 72  write-list is wr
0800: 69 74 74 65 6e 20 74 6f 20 74 68 65 20 72 65 61  itten to the rea
0810: 6c 20 75 6e 64 65 72 6c 79 69 6e 67 20 66 69 6c  l underlying fil
0820: 65 73 20 0a 2a 2a 20 20 20 61 6e 64 20 74 68 65  es .**   and the
0830: 20 65 6e 74 72 69 65 73 20 72 65 6d 6f 76 65 64   entries removed
0840: 20 66 72 6f 6d 20 74 68 65 20 77 72 69 74 65 2d   from the write-
0850: 6c 69 73 74 2e 20 49 66 20 61 20 63 72 61 73 68  list. If a crash
0860: 20 69 73 20 73 69 6d 75 6c 61 74 65 64 2c 0a 2a   is simulated,.*
0870: 2a 20 20 20 61 20 73 75 62 73 65 74 20 6f 66 20  *   a subset of 
0880: 74 68 65 20 62 75 66 66 65 72 73 20 6d 61 79 20  the buffers may 
0890: 62 65 20 63 6f 72 72 75 70 74 65 64 20 62 65 66  be corrupted bef
08a0: 6f 72 65 20 74 68 65 20 64 61 74 61 20 69 73 20  ore the data is 
08b0: 77 72 69 74 74 65 6e 2e 0a 2a 2a 0a 2a 2a 20 20  written..**.**  
08c0: 20 54 68 65 20 65 78 61 63 74 20 73 75 62 73 65   The exact subse
08d0: 74 20 6f 66 20 74 68 65 20 77 72 69 74 65 2d 6c  t of the write-l
08e0: 69 73 74 20 77 72 69 74 74 65 6e 20 61 6e 64 2f  ist written and/
08f0: 6f 72 20 63 6f 72 72 75 70 74 65 64 20 69 73 0a  or corrupted is.
0900: 2a 2a 20 20 20 64 65 74 65 72 6d 69 6e 65 64 20  **   determined 
0910: 62 79 20 74 68 65 20 73 69 6d 75 6c 61 74 65 64  by the simulated
0920: 20 64 65 76 69 63 65 20 63 68 61 72 61 63 74 65   device characte
0930: 72 69 73 74 69 63 73 20 61 6e 64 20 73 65 63 74  ristics and sect
0940: 6f 72 2d 73 69 7a 65 2e 0a 2a 2a 0a 2a 2a 20 22  or-size..**.** "
0950: 4e 6f 72 6d 61 6c 22 20 6d 6f 64 65 3a 0a 2a 2a  Normal" mode:.**
0960: 0a 2a 2a 20 20 20 4e 6f 72 6d 61 6c 20 6d 6f 64  .**   Normal mod
0970: 65 20 69 73 20 75 73 65 64 20 77 68 65 6e 20 74  e is used when t
0980: 68 65 20 73 69 6d 75 6c 61 74 65 64 20 64 65 76  he simulated dev
0990: 69 63 65 20 68 61 73 20 6e 6f 6e 65 20 6f 66 20  ice has none of 
09a0: 74 68 65 0a 2a 2a 20 20 20 53 51 4c 49 54 45 5f  the.**   SQLITE_
09b0: 49 4f 43 41 50 5f 58 58 58 20 66 6c 61 67 73 20  IOCAP_XXX flags 
09c0: 73 65 74 2e 0a 2a 2a 0a 2a 2a 20 20 20 49 6e 20  set..**.**   In 
09d0: 6e 6f 72 6d 61 6c 20 6d 6f 64 65 2c 20 69 66 20  normal mode, if 
09e0: 74 68 65 20 66 73 79 6e 63 28 29 20 69 73 20 6e  the fsync() is n
09f0: 6f 74 20 61 20 73 69 6d 75 6c 61 74 65 64 20 63  ot a simulated c
0a00: 72 61 73 68 2c 20 74 68 65 20 0a 2a 2a 20 20 20  rash, the .**   
0a10: 77 72 69 74 65 2d 6c 69 73 74 20 69 73 20 74 72  write-list is tr
0a20: 61 76 65 72 73 65 64 20 66 72 6f 6d 20 62 65 67  aversed from beg
0a30: 69 6e 6e 69 6e 67 20 74 6f 20 65 6e 64 2e 20 45  inning to end. E
0a40: 61 63 68 20 57 72 69 74 65 42 75 66 66 65 72 0a  ach WriteBuffer.
0a50: 2a 2a 20 20 20 73 74 72 75 63 74 75 72 65 20 61  **   structure a
0a60: 73 73 6f 63 69 61 74 65 64 20 77 69 74 68 20 74  ssociated with t
0a70: 68 65 20 66 69 6c 65 20 68 61 6e 64 6c 65 20 75  he file handle u
0a80: 73 65 64 20 74 6f 20 63 61 6c 6c 20 78 53 79 6e  sed to call xSyn
0a90: 63 28 29 0a 2a 2a 20 20 20 69 73 20 77 72 69 74  c().**   is writ
0aa0: 74 65 6e 20 74 6f 20 74 68 65 20 72 65 61 6c 20  ten to the real 
0ab0: 66 69 6c 65 20 61 6e 64 20 72 65 6d 6f 76 65 64  file and removed
0ac0: 20 66 72 6f 6d 20 74 68 65 20 77 72 69 74 65 2d   from the write-
0ad0: 6c 69 73 74 2e 0a 2a 2a 0a 2a 2a 20 20 20 49 66  list..**.**   If
0ae0: 20 61 20 63 72 61 73 68 20 69 73 20 73 69 6d 75   a crash is simu
0af0: 6c 61 74 65 64 2c 20 6f 6e 65 20 6f 66 20 74 68  lated, one of th
0b00: 65 20 66 6f 6c 6c 6f 77 69 6e 67 20 74 61 6b 65  e following take
0b10: 73 20 70 6c 61 63 65 20 66 6f 72 20 0a 2a 2a 20  s place for .** 
0b20: 20 20 65 61 63 68 20 57 72 69 74 65 42 75 66 66    each WriteBuff
0b30: 65 72 20 69 6e 20 74 68 65 20 77 72 69 74 65 2d  er in the write-
0b40: 6c 69 73 74 2c 20 72 65 67 61 72 64 6c 65 73 73  list, regardless
0b50: 20 6f 66 20 77 68 69 63 68 20 0a 2a 2a 20 20 20   of which .**   
0b60: 66 69 6c 65 2d 68 61 6e 64 6c 65 20 69 74 20 69  file-handle it i
0b70: 73 20 61 73 73 6f 63 69 61 74 65 64 20 77 69 74  s associated wit
0b80: 68 3a 0a 2a 2a 0a 2a 2a 20 20 20 20 20 31 2e 20  h:.**.**     1. 
0b90: 54 68 65 20 62 75 66 66 65 72 20 69 73 20 63 6f  The buffer is co
0ba0: 72 72 65 63 74 6c 79 20 77 72 69 74 74 65 6e 20  rrectly written 
0bb0: 74 6f 20 74 68 65 20 66 69 6c 65 2c 20 6a 75 73  to the file, jus
0bc0: 74 20 61 73 20 69 66 0a 2a 2a 20 20 20 20 20 20  t as if.**      
0bd0: 20 20 61 20 63 72 61 73 68 20 77 65 72 65 20 6e    a crash were n
0be0: 6f 74 20 62 65 69 6e 67 20 73 69 6d 75 6c 61 74  ot being simulat
0bf0: 65 64 2e 0a 2a 2a 0a 2a 2a 20 20 20 20 20 32 2e  ed..**.**     2.
0c00: 20 4e 6f 74 68 69 6e 67 20 69 73 20 64 6f 6e 65   Nothing is done
0c10: 2e 0a 2a 2a 0a 2a 2a 20 20 20 20 20 33 2e 20 47  ..**.**     3. G
0c20: 61 72 62 61 67 65 20 64 61 74 61 20 69 73 20 77  arbage data is w
0c30: 72 69 74 74 65 6e 20 74 6f 20 61 6c 6c 20 73 65  ritten to all se
0c40: 63 74 6f 72 73 20 6f 66 20 74 68 65 20 66 69 6c  ctors of the fil
0c50: 65 20 74 68 61 74 20 0a 2a 2a 20 20 20 20 20 20  e that .**      
0c60: 20 20 6f 76 65 72 6c 61 70 20 74 68 65 20 72 65    overlap the re
0c70: 67 69 6f 6e 20 73 70 65 63 69 66 69 65 64 20 62  gion specified b
0c80: 79 20 74 68 65 20 57 72 69 74 65 42 75 66 66 65  y the WriteBuffe
0c90: 72 2e 20 4f 72 20 67 61 72 62 61 67 65 0a 2a 2a  r. Or garbage.**
0ca0: 20 20 20 20 20 20 20 20 64 61 74 61 20 69 73 20          data is 
0cb0: 77 72 69 74 74 65 6e 20 74 6f 20 73 6f 6d 65 20  written to some 
0cc0: 63 6f 6e 74 69 67 75 6f 75 73 20 73 65 63 74 69  contiguous secti
0cd0: 6f 6e 20 77 69 74 68 69 6e 20 74 68 65 20 0a 2a  on within the .*
0ce0: 2a 20 20 20 20 20 20 20 20 6f 76 65 72 6c 61 70  *        overlap
0cf0: 70 65 64 20 73 65 63 74 6f 72 73 2e 0a 2a 2a 0a  ped sectors..**.
0d00: 2a 2a 20 44 65 76 69 63 65 20 43 68 61 72 61 63  ** Device Charac
0d10: 74 65 72 69 73 74 69 63 20 66 6c 61 67 20 68 61  teristic flag ha
0d20: 6e 64 6c 69 6e 67 3a 0a 2a 2a 0a 2a 2a 20 20 20  ndling:.**.**   
0d30: 49 66 20 74 68 65 20 49 4f 43 41 50 5f 41 54 4f  If the IOCAP_ATO
0d40: 4d 49 43 20 66 6c 61 67 20 69 73 20 73 65 74 2c  MIC flag is set,
0d50: 20 74 68 65 6e 20 6f 70 74 69 6f 6e 20 28 33 29   then option (3)
0d60: 20 61 62 6f 76 65 20 69 73 20 0a 2a 2a 20 20 20   above is .**   
0d70: 6e 65 76 65 72 20 73 65 6c 65 63 74 65 64 2e 0a  never selected..
0d80: 2a 2a 0a 2a 2a 20 20 20 49 66 20 74 68 65 20 49  **.**   If the I
0d90: 4f 43 41 50 5f 41 54 4f 4d 49 43 35 31 32 20 66  OCAP_ATOMIC512 f
0da0: 6c 61 67 20 69 73 20 73 65 74 2c 20 61 6e 64 20  lag is set, and 
0db0: 74 68 65 20 57 72 69 74 65 42 75 66 66 65 72 20  the WriteBuffer 
0dc0: 72 65 70 72 65 73 65 6e 74 73 0a 2a 2a 20 20 20  represents.**   
0dd0: 61 6e 20 61 6c 69 67 6e 65 64 20 77 72 69 74 65  an aligned write
0de0: 28 29 20 6f 66 20 61 6e 20 69 6e 74 65 67 65 72  () of an integer
0df0: 20 6e 75 6d 62 65 72 20 6f 66 20 35 31 32 20 62   number of 512 b
0e00: 79 74 65 20 72 65 67 69 6f 6e 73 2c 20 74 68 65  yte regions, the
0e10: 6e 0a 2a 2a 20 20 20 6f 70 74 69 6f 6e 20 28 33  n.**   option (3
0e20: 29 20 61 62 6f 76 65 20 69 73 20 6e 65 76 65 72  ) above is never
0e30: 20 73 65 6c 65 63 74 65 64 2e 20 49 6e 73 74 65   selected. Inste
0e40: 61 64 2c 20 65 61 63 68 20 35 31 32 20 62 79 74  ad, each 512 byt
0e50: 65 20 72 65 67 69 6f 6e 0a 2a 2a 20 20 20 69 73  e region.**   is
0e60: 20 65 69 74 68 65 72 20 63 6f 72 72 65 63 74 6c   either correctl
0e70: 79 20 77 72 69 74 74 65 6e 20 6f 72 20 6c 65 66  y written or lef
0e80: 74 20 63 6f 6d 70 6c 65 74 65 6c 79 20 75 6e 74  t completely unt
0e90: 6f 75 63 68 65 64 2e 20 53 69 6d 69 6c 61 72 0a  ouched. Similar.
0ea0: 2a 2a 20 20 20 6c 6f 67 69 63 20 67 6f 76 65 72  **   logic gover
0eb0: 6e 73 20 74 68 65 20 62 65 68 61 76 69 6f 75 72  ns the behaviour
0ec0: 20 69 66 20 61 6e 79 20 6f 66 20 74 68 65 20 6f   if any of the o
0ed0: 74 68 65 72 20 41 54 4f 4d 49 43 58 58 58 20 66  ther ATOMICXXX f
0ee0: 6c 61 67 73 0a 2a 2a 20 20 20 69 73 20 73 65 74  lags.**   is set
0ef0: 2e 0a 2a 2a 0a 2a 2a 20 20 20 49 66 20 65 69 74  ..**.**   If eit
0f00: 68 65 72 20 74 68 65 20 49 4f 43 41 50 5f 53 41  her the IOCAP_SA
0f10: 46 45 41 50 50 45 4e 44 20 6f 72 20 49 4f 43 41  FEAPPEND or IOCA
0f20: 50 5f 53 45 51 55 45 4e 54 49 41 4c 20 66 6c 61  P_SEQUENTIAL fla
0f30: 67 73 20 61 72 65 20 73 65 74 0a 2a 2a 20 20 20  gs are set.**   
0f40: 61 6e 64 20 61 20 63 72 61 73 68 20 69 73 20 62  and a crash is b
0f50: 65 69 6e 67 20 73 69 6d 75 6c 61 74 65 64 2c 20  eing simulated, 
0f60: 74 68 65 6e 20 61 6e 20 65 6e 74 72 79 20 6f 66  then an entry of
0f70: 20 74 68 65 20 77 72 69 74 65 2d 6c 69 73 74 20   the write-list 
0f80: 69 73 0a 2a 2a 20 20 20 73 65 6c 65 63 74 65 64  is.**   selected
0f90: 20 61 74 20 72 61 6e 64 6f 6d 2e 20 45 76 65 72   at random. Ever
0fa0: 79 74 68 69 6e 67 20 69 6e 20 74 68 65 20 6c 69  ything in the li
0fb0: 73 74 20 61 66 74 65 72 20 74 68 65 20 73 65 6c  st after the sel
0fc0: 65 63 74 65 64 20 65 6e 74 72 79 20 0a 2a 2a 20  ected entry .** 
0fd0: 20 20 69 73 20 64 69 73 63 61 72 64 65 64 20 62    is discarded b
0fe0: 65 66 6f 72 65 20 70 72 6f 63 65 73 73 69 6e 67  efore processing
0ff0: 20 62 65 67 69 6e 73 2e 0a 2a 2a 0a 2a 2a 20 20   begins..**.**  
1000: 20 49 66 20 49 4f 43 41 50 5f 53 45 51 55 45 4e   If IOCAP_SEQUEN
1010: 54 49 41 4c 20 69 73 20 73 65 74 20 61 6e 64 20  TIAL is set and 
1020: 61 20 63 72 61 73 68 20 69 73 20 62 65 69 6e 67  a crash is being
1030: 20 73 69 6d 75 6c 61 74 65 64 2c 20 6f 70 74 69   simulated, opti
1040: 6f 6e 20 0a 2a 2a 20 20 20 28 31 29 20 69 73 20  on .**   (1) is 
1050: 73 65 6c 65 63 74 65 64 20 66 6f 72 20 61 6c 6c  selected for all
1060: 20 77 72 69 74 65 2d 6c 69 73 74 20 65 6e 74 72   write-list entr
1070: 69 65 73 20 65 78 63 65 70 74 20 74 68 65 20 6c  ies except the l
1080: 61 73 74 2e 20 49 66 20 61 20 0a 2a 2a 20 20 20  ast. If a .**   
1090: 63 72 61 73 68 20 69 73 20 6e 6f 74 20 62 65 69  crash is not bei
10a0: 6e 67 20 73 69 6d 75 6c 61 74 65 64 2c 20 74 68  ng simulated, th
10b0: 65 6e 20 61 6c 6c 20 65 6e 74 72 69 65 73 20 69  en all entries i
10c0: 6e 20 74 68 65 20 77 72 69 74 65 2d 6c 69 73 74  n the write-list
10d0: 0a 2a 2a 20 20 20 74 68 61 74 20 6f 63 63 75 72  .**   that occur
10e0: 20 62 65 66 6f 72 65 20 61 74 20 6c 65 61 73 74   before at least
10f0: 20 6f 6e 65 20 77 72 69 74 65 28 29 20 6f 6e 20   one write() on 
1100: 74 68 65 20 66 69 6c 65 2d 68 61 6e 64 6c 65 20  the file-handle 
1110: 73 70 65 63 69 66 69 65 64 0a 2a 2a 20 20 20 61  specified.**   a
1120: 73 20 70 61 72 74 20 6f 66 20 74 68 65 20 78 53  s part of the xS
1130: 79 6e 63 28 29 20 61 72 65 20 77 72 69 74 74 65  ync() are writte
1140: 6e 20 74 6f 20 74 68 65 69 72 20 61 73 73 6f 63  n to their assoc
1150: 69 61 74 65 64 20 72 65 61 6c 20 66 69 6c 65 73  iated real files
1160: 2e 0a 2a 2a 0a 2a 2a 20 20 20 49 66 20 49 4f 43  ..**.**   If IOC
1170: 41 50 5f 53 41 46 45 41 50 50 45 4e 44 20 69 73  AP_SAFEAPPEND is
1180: 20 73 65 74 20 61 6e 64 20 74 68 65 20 66 69 72   set and the fir
1190: 73 74 20 62 79 74 65 20 77 72 69 74 74 65 6e 20  st byte written 
11a0: 62 79 20 74 68 65 20 77 72 69 74 65 28 29 0a 2a  by the write().*
11b0: 2a 20 20 20 6f 70 65 72 61 74 69 6f 6e 20 69 73  *   operation is
11c0: 20 6f 6e 65 20 62 79 74 65 20 70 61 73 74 20 74   one byte past t
11d0: 68 65 20 63 75 72 72 65 6e 74 20 65 6e 64 20 6f  he current end o
11e0: 66 20 74 68 65 20 66 69 6c 65 2c 20 74 68 65 6e  f the file, then
11f0: 20 6f 70 74 69 6f 6e 0a 2a 2a 20 20 20 28 31 29   option.**   (1)
1200: 20 69 73 20 61 6c 77 61 79 73 20 73 65 6c 65 63   is always selec
1210: 74 65 64 2e 0a 2a 2f 0a 0a 2f 2a 0a 2a 2a 20 45  ted..*/../*.** E
1220: 61 63 68 20 77 72 69 74 65 20 6f 70 65 72 61 74  ach write operat
1230: 69 6f 6e 20 69 6e 20 74 68 65 20 77 72 69 74 65  ion in the write
1240: 2d 6c 69 73 74 20 69 73 20 72 65 70 72 65 73 65  -list is represe
1250: 6e 74 65 64 20 62 79 20 61 6e 20 69 6e 73 74 61  nted by an insta
1260: 6e 63 65 0a 2a 2a 20 6f 66 20 74 68 65 20 66 6f  nce.** of the fo
1270: 6c 6c 6f 77 69 6e 67 20 73 74 72 75 63 74 75 72  llowing structur
1280: 65 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 7a 42 75 66  e..**.** If zBuf
1290: 20 69 73 20 30 2c 20 74 68 65 6e 20 74 68 69 73   is 0, then this
12a0: 20 73 74 72 75 63 74 75 72 65 20 72 65 70 72 65   structure repre
12b0: 73 65 6e 74 73 20 61 20 63 61 6c 6c 20 74 6f 20  sents a call to 
12c0: 78 54 72 75 6e 63 61 74 65 28 29 2c 20 0a 2a 2a  xTruncate(), .**
12d0: 20 6e 6f 74 20 78 57 72 69 74 65 28 29 2e 20 49   not xWrite(). I
12e0: 6e 20 74 68 61 74 20 63 61 73 65 2c 20 69 4f 66  n that case, iOf
12f0: 66 73 65 74 20 69 73 20 74 68 65 20 73 69 7a 65  fset is the size
1300: 20 74 68 61 74 20 74 68 65 20 66 69 6c 65 20 69   that the file i
1310: 73 0a 2a 2a 20 74 72 75 6e 63 61 74 65 64 20 74  s.** truncated t
1320: 6f 2e 0a 2a 2f 0a 73 74 72 75 63 74 20 57 72 69  o..*/.struct Wri
1330: 74 65 42 75 66 66 65 72 20 7b 0a 20 20 69 36 34  teBuffer {.  i64
1340: 20 69 4f 66 66 73 65 74 3b 20 20 20 20 20 20 20   iOffset;       
1350: 20 20 20 20 20 20 20 20 20 20 2f 2a 20 42 79 74            /* Byt
1360: 65 20 6f 66 66 73 65 74 20 6f 66 20 74 68 65 20  e offset of the 
1370: 73 74 61 72 74 20 6f 66 20 74 68 69 73 20 77 72  start of this wr
1380: 69 74 65 28 29 20 2a 2f 0a 20 20 69 6e 74 20 6e  ite() */.  int n
1390: 42 75 66 3b 20 20 20 20 20 20 20 20 20 20 20 20  Buf;            
13a0: 20 20 20 20 20 20 20 20 2f 2a 20 4e 75 6d 62 65          /* Numbe
13b0: 72 20 6f 66 20 62 79 74 65 73 20 77 72 69 74 74  r of bytes writt
13c0: 65 6e 20 2a 2f 0a 20 20 75 38 20 2a 7a 42 75 66  en */.  u8 *zBuf
13d0: 3b 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20  ;               
13e0: 20 20 20 20 20 2f 2a 20 50 6f 69 6e 74 65 72 20       /* Pointer 
13f0: 74 6f 20 63 6f 70 79 20 6f 66 20 77 72 69 74 74  to copy of writt
1400: 65 6e 20 64 61 74 61 20 2a 2f 0a 20 20 43 72 61  en data */.  Cra
1410: 73 68 46 69 6c 65 20 2a 70 46 69 6c 65 3b 20 20  shFile *pFile;  
1420: 20 20 20 20 20 20 20 20 20 20 2f 2a 20 46 69 6c            /* Fil
1430: 65 20 74 68 69 73 20 77 72 69 74 65 28 29 20 61  e this write() a
1440: 70 70 6c 69 65 73 20 74 6f 20 2a 2f 0a 0a 20 20  pplies to */..  
1450: 57 72 69 74 65 42 75 66 66 65 72 20 2a 70 4e 65  WriteBuffer *pNe
1460: 78 74 3b 20 20 20 20 20 20 20 20 20 20 2f 2a 20  xt;          /* 
1470: 4e 65 78 74 20 69 6e 20 43 72 61 73 68 47 6c 6f  Next in CrashGlo
1480: 62 61 6c 2e 70 57 72 69 74 65 4c 69 73 74 20 2a  bal.pWriteList *
1490: 2f 0a 7d 3b 0a 0a 73 74 72 75 63 74 20 43 72 61  /.};..struct Cra
14a0: 73 68 46 69 6c 65 20 7b 0a 20 20 63 6f 6e 73 74  shFile {.  const
14b0: 20 73 71 6c 69 74 65 33 5f 69 6f 5f 6d 65 74 68   sqlite3_io_meth
14c0: 6f 64 73 20 2a 70 4d 65 74 68 6f 64 3b 20 20 20  ods *pMethod;   
14d0: 2f 2a 20 4d 75 73 74 20 62 65 20 66 69 72 73 74  /* Must be first
14e0: 20 2a 2f 0a 20 20 73 71 6c 69 74 65 33 5f 66 69   */.  sqlite3_fi
14f0: 6c 65 20 2a 70 52 65 61 6c 46 69 6c 65 3b 20 20  le *pRealFile;  
1500: 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 55 6e             /* Un
1510: 64 65 72 6c 79 69 6e 67 20 22 72 65 61 6c 22 20  derlying "real" 
1520: 66 69 6c 65 20 68 61 6e 64 6c 65 20 2a 2f 0a 20  file handle */. 
1530: 20 63 68 61 72 20 2a 7a 4e 61 6d 65 3b 0a 0a 20   char *zName;.. 
1540: 20 2f 2a 20 43 61 63 68 65 20 6f 66 20 74 68 65   /* Cache of the
1550: 20 65 6e 74 69 72 65 20 66 69 6c 65 2e 20 54 68   entire file. Th
1560: 69 73 20 69 73 20 75 73 65 64 20 74 6f 20 73 70  is is used to sp
1570: 65 65 64 20 75 70 20 4f 73 52 65 61 64 28 29 20  eed up OsRead() 
1580: 61 6e 64 20 0a 20 20 2a 2a 20 4f 73 46 69 6c 65  and .  ** OsFile
1590: 53 69 7a 65 28 29 20 63 61 6c 6c 73 2e 20 41 6c  Size() calls. Al
15a0: 74 68 6f 75 67 68 20 62 6f 74 68 20 63 6f 75 6c  though both coul
15b0: 64 20 62 65 20 64 6f 6e 65 20 62 79 20 74 72 61  d be done by tra
15c0: 76 65 72 73 69 6e 67 20 74 68 65 0a 20 20 2a 2a  versing the.  **
15d0: 20 77 72 69 74 65 2d 6c 69 73 74 2c 20 69 6e 20   write-list, in 
15e0: 70 72 61 63 74 69 63 65 20 74 68 69 73 20 69 73  practice this is
15f0: 20 69 6d 70 72 61 63 74 69 63 61 6c 6c 79 20 73   impractically s
1600: 6c 6f 77 2e 0a 20 20 2a 2f 0a 20 20 69 6e 74 20  low..  */.  int 
1610: 69 53 69 7a 65 3b 20 20 20 20 20 20 20 20 20 20  iSize;          
1620: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1630: 20 2f 2a 20 53 69 7a 65 20 6f 66 20 66 69 6c 65   /* Size of file
1640: 20 69 6e 20 62 79 74 65 73 20 2a 2f 0a 20 20 69   in bytes */.  i
1650: 6e 74 20 6e 44 61 74 61 3b 20 20 20 20 20 20 20  nt nData;       
1660: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
1670: 20 20 20 20 2f 2a 20 53 69 7a 65 20 6f 66 20 62      /* Size of b
1680: 75 66 66 65 72 20 61 6c 6c 6f 63 61 74 65 64 20  uffer allocated 
1690: 61 74 20 7a 44 61 74 61 20 2a 2f 0a 20 20 75 38  at zData */.  u8
16a0: 20 2a 7a 44 61 74 61 3b 20 20 20 20 20 20 20 20   *zData;        
16b0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
16c0: 20 20 20 2f 2a 20 42 75 66 66 65 72 20 63 6f 6e     /* Buffer con
16d0: 74 61 69 6e 69 6e 67 20 66 69 6c 65 20 63 6f 6e  taining file con
16e0: 74 65 6e 74 73 20 2a 2f 0a 7d 3b 0a 0a 73 74 72  tents */.};..str
16f0: 75 63 74 20 43 72 61 73 68 47 6c 6f 62 61 6c 20  uct CrashGlobal 
1700: 7b 0a 20 20 57 72 69 74 65 42 75 66 66 65 72 20  {.  WriteBuffer 
1710: 2a 70 57 72 69 74 65 4c 69 73 74 3b 20 20 20 20  *pWriteList;    
1720: 20 2f 2a 20 48 65 61 64 20 6f 66 20 77 72 69 74   /* Head of writ
1730: 65 2d 6c 69 73 74 20 2a 2f 0a 20 20 57 72 69 74  e-list */.  Writ
1740: 65 42 75 66 66 65 72 20 2a 70 57 72 69 74 65 4c  eBuffer *pWriteL
1750: 69 73 74 45 6e 64 3b 20 20 2f 2a 20 45 6e 64 20  istEnd;  /* End 
1760: 6f 66 20 77 72 69 74 65 2d 6c 69 73 74 20 2a 2f  of write-list */
1770: 0a 0a 20 20 69 6e 74 20 69 53 65 63 74 6f 72 53  ..  int iSectorS
1780: 69 7a 65 3b 20 20 20 20 20 20 20 20 20 20 20 20  ize;            
1790: 20 2f 2a 20 56 61 6c 75 65 20 6f 66 20 73 69 6d   /* Value of sim
17a0: 75 6c 61 74 65 64 20 73 65 63 74 6f 72 20 73 69  ulated sector si
17b0: 7a 65 20 2a 2f 0a 20 20 69 6e 74 20 69 44 65 76  ze */.  int iDev
17c0: 69 63 65 43 68 61 72 61 63 74 65 72 69 73 74 69  iceCharacteristi
17d0: 63 73 3b 20 20 2f 2a 20 56 61 6c 75 65 20 6f 66  cs;  /* Value of
17e0: 20 73 69 6d 75 6c 61 74 65 64 20 64 65 76 69 63   simulated devic
17f0: 65 20 63 68 61 72 61 63 74 65 72 69 73 74 69 63  e characteristic
1800: 73 20 2a 2f 0a 0a 20 20 69 6e 74 20 69 43 72 61  s */..  int iCra
1810: 73 68 3b 20 20 20 20 20 20 20 20 20 20 20 20 20  sh;             
1820: 20 20 20 20 20 2f 2a 20 43 72 61 73 68 20 6f 6e       /* Crash on
1830: 20 74 68 65 20 69 43 72 61 73 68 27 74 68 20 63   the iCrash'th c
1840: 61 6c 6c 20 74 6f 20 78 53 79 6e 63 28 29 20 2a  all to xSync() *
1850: 2f 0a 20 20 63 68 61 72 20 7a 43 72 61 73 68 46  /.  char zCrashF
1860: 69 6c 65 5b 35 30 30 5d 3b 20 20 20 20 20 20 20  ile[500];       
1870: 20 2f 2a 20 43 72 61 73 68 20 64 75 72 69 6e 67   /* Crash during
1880: 20 61 6e 20 78 53 79 6e 63 28 29 20 6f 6e 20 74   an xSync() on t
1890: 68 69 73 20 66 69 6c 65 20 2a 2f 20 0a 7d 3b 0a  his file */ .};.
18a0: 0a 73 74 61 74 69 63 20 43 72 61 73 68 47 6c 6f  .static CrashGlo
18b0: 62 61 6c 20 67 20 3d 20 7b 30 2c 20 30 2c 20 53  bal g = {0, 0, S
18c0: 51 4c 49 54 45 5f 44 45 46 41 55 4c 54 5f 53 45  QLITE_DEFAULT_SE
18d0: 43 54 4f 52 5f 53 49 5a 45 2c 20 30 2c 20 30 7d  CTOR_SIZE, 0, 0}
18e0: 3b 0a 0a 2f 2a 0a 2a 2a 20 53 65 74 20 74 68 69  ;../*.** Set thi
18f0: 73 20 67 6c 6f 62 61 6c 20 76 61 72 69 61 62 6c  s global variabl
1900: 65 20 74 6f 20 31 20 74 6f 20 65 6e 61 62 6c 65  e to 1 to enable
1910: 20 63 72 61 73 68 20 74 65 73 74 69 6e 67 2e 0a   crash testing..
1920: 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 73 71  */.static int sq
1930: 6c 69 74 65 33 43 72 61 73 68 54 65 73 74 45 6e  lite3CrashTestEn
1940: 61 62 6c 65 20 3d 20 30 3b 0a 0a 2f 2a 0a 2a 2a  able = 0;../*.**
1950: 20 46 6c 75 73 68 20 74 68 65 20 77 72 69 74 65   Flush the write
1960: 2d 6c 69 73 74 20 61 73 20 69 66 20 78 53 79 6e  -list as if xSyn
1970: 63 28 29 20 68 61 64 20 62 65 65 6e 20 63 61 6c  c() had been cal
1980: 6c 65 64 20 6f 6e 20 66 69 6c 65 20 68 61 6e 64  led on file hand
1990: 6c 65 0a 2a 2a 20 70 46 69 6c 65 2e 20 49 66 20  le.** pFile. If 
19a0: 69 73 43 72 61 73 68 20 69 73 20 74 72 75 65 2c  isCrash is true,
19b0: 20 73 69 6d 75 6c 61 74 65 20 61 20 63 72 61 73   simulate a cras
19c0: 68 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74  h..*/.static int
19d0: 20 77 72 69 74 65 4c 69 73 74 53 79 6e 63 28 43   writeListSync(C
19e0: 72 61 73 68 46 69 6c 65 20 2a 70 46 69 6c 65 2c  rashFile *pFile,
19f0: 20 69 6e 74 20 69 73 43 72 61 73 68 29 7b 0a 20   int isCrash){. 
1a00: 20 69 6e 74 20 72 63 20 3d 20 53 51 4c 49 54 45   int rc = SQLITE
1a10: 5f 4f 4b 3b 0a 20 20 69 6e 74 20 69 44 63 20 3d  _OK;.  int iDc =
1a20: 20 67 2e 69 44 65 76 69 63 65 43 68 61 72 61 63   g.iDeviceCharac
1a30: 74 65 72 69 73 74 69 63 73 3b 0a 0a 20 20 57 72  teristics;..  Wr
1a40: 69 74 65 42 75 66 66 65 72 20 2a 70 57 72 69 74  iteBuffer *pWrit
1a50: 65 3b 0a 20 20 57 72 69 74 65 42 75 66 66 65 72  e;.  WriteBuffer
1a60: 20 2a 2a 70 70 50 74 72 3b 0a 0a 20 20 2f 2a 20   **ppPtr;..  /* 
1a70: 49 66 20 74 68 69 73 20 69 73 20 6e 6f 74 20 61  If this is not a
1a80: 20 63 72 61 73 68 20 73 69 6d 75 6c 61 74 69 6f   crash simulatio
1a90: 6e 2c 20 73 65 74 20 70 46 69 6e 61 6c 20 74 6f  n, set pFinal to
1aa0: 20 70 6f 69 6e 74 20 74 6f 20 74 68 65 20 0a 20   point to the . 
1ab0: 20 2a 2a 20 6c 61 73 74 20 65 6c 65 6d 65 6e 74   ** last element
1ac0: 20 6f 66 20 74 68 65 20 77 72 69 74 65 2d 6c 69   of the write-li
1ad0: 73 74 20 74 68 61 74 20 69 73 20 61 73 73 6f 63  st that is assoc
1ae0: 69 61 74 65 64 20 77 69 74 68 20 66 69 6c 65 20  iated with file 
1af0: 68 61 6e 64 6c 65 0a 20 20 2a 2a 20 70 46 69 6c  handle.  ** pFil
1b00: 65 2e 0a 20 20 2a 2a 0a 20 20 2a 2a 20 49 66 20  e..  **.  ** If 
1b10: 74 68 69 73 20 69 73 20 61 20 63 72 61 73 68 20  this is a crash 
1b20: 73 69 6d 75 6c 61 74 69 6f 6e 2c 20 73 65 74 20  simulation, set 
1b30: 70 46 69 6e 61 6c 20 74 6f 20 61 6e 20 61 72 62  pFinal to an arb
1b40: 69 74 72 61 72 69 6c 79 20 73 65 6c 65 63 74 65  itrarily selecte
1b50: 64 0a 20 20 2a 2a 20 65 6c 65 6d 65 6e 74 20 6f  d.  ** element o
1b60: 66 20 74 68 65 20 77 72 69 74 65 2d 6c 69 73 74  f the write-list
1b70: 2e 0a 20 20 2a 2f 0a 20 20 57 72 69 74 65 42 75  ..  */.  WriteBu
1b80: 66 66 65 72 20 2a 70 46 69 6e 61 6c 20 3d 20 30  ffer *pFinal = 0
1b90: 3b 0a 20 20 69 66 28 20 21 69 73 43 72 61 73 68  ;.  if( !isCrash
1ba0: 20 29 7b 0a 20 20 20 20 66 6f 72 28 70 57 72 69   ){.    for(pWri
1bb0: 74 65 3d 67 2e 70 57 72 69 74 65 4c 69 73 74 3b  te=g.pWriteList;
1bc0: 20 70 57 72 69 74 65 3b 20 70 57 72 69 74 65 3d   pWrite; pWrite=
1bd0: 70 57 72 69 74 65 2d 3e 70 4e 65 78 74 29 7b 0a  pWrite->pNext){.
1be0: 20 20 20 20 20 20 69 66 28 20 70 57 72 69 74 65        if( pWrite
1bf0: 2d 3e 70 46 69 6c 65 3d 3d 70 46 69 6c 65 20 29  ->pFile==pFile )
1c00: 7b 0a 20 20 20 20 20 20 20 20 70 46 69 6e 61 6c  {.        pFinal
1c10: 20 3d 20 70 57 72 69 74 65 3b 0a 20 20 20 20 20   = pWrite;.     
1c20: 20 7d 0a 20 20 20 20 7d 0a 20 20 7d 65 6c 73 65   }.    }.  }else
1c30: 20 69 66 28 20 69 44 63 26 28 53 51 4c 49 54 45   if( iDc&(SQLITE
1c40: 5f 49 4f 43 41 50 5f 53 45 51 55 45 4e 54 49 41  _IOCAP_SEQUENTIA
1c50: 4c 7c 53 51 4c 49 54 45 5f 49 4f 43 41 50 5f 53  L|SQLITE_IOCAP_S
1c60: 41 46 45 5f 41 50 50 45 4e 44 29 20 29 7b 0a 20  AFE_APPEND) ){. 
1c70: 20 20 20 69 6e 74 20 6e 57 72 69 74 65 20 3d 20     int nWrite = 
1c80: 30 3b 0a 20 20 20 20 69 6e 74 20 69 46 69 6e 61  0;.    int iFina
1c90: 6c 3b 0a 20 20 20 20 66 6f 72 28 70 57 72 69 74  l;.    for(pWrit
1ca0: 65 3d 67 2e 70 57 72 69 74 65 4c 69 73 74 3b 20  e=g.pWriteList; 
1cb0: 70 57 72 69 74 65 3b 20 70 57 72 69 74 65 3d 70  pWrite; pWrite=p
1cc0: 57 72 69 74 65 2d 3e 70 4e 65 78 74 29 20 6e 57  Write->pNext) nW
1cd0: 72 69 74 65 2b 2b 3b 0a 20 20 20 20 73 71 6c 69  rite++;.    sqli
1ce0: 74 65 33 52 61 6e 64 6f 6d 6e 65 73 73 28 73 69  te3Randomness(si
1cf0: 7a 65 6f 66 28 69 6e 74 29 2c 20 26 69 46 69 6e  zeof(int), &iFin
1d00: 61 6c 29 3b 0a 20 20 20 20 69 46 69 6e 61 6c 20  al);.    iFinal 
1d10: 3d 20 28 28 69 46 69 6e 61 6c 3c 30 29 3f 2d 31  = ((iFinal<0)?-1
1d20: 2a 69 46 69 6e 61 6c 3a 69 46 69 6e 61 6c 29 25  *iFinal:iFinal)%
1d30: 6e 57 72 69 74 65 3b 0a 20 20 20 20 66 6f 72 28  nWrite;.    for(
1d40: 70 57 72 69 74 65 3d 67 2e 70 57 72 69 74 65 4c  pWrite=g.pWriteL
1d50: 69 73 74 3b 20 69 46 69 6e 61 6c 3e 30 3b 20 70  ist; iFinal>0; p
1d60: 57 72 69 74 65 3d 70 57 72 69 74 65 2d 3e 70 4e  Write=pWrite->pN
1d70: 65 78 74 29 20 69 46 69 6e 61 6c 2d 2d 3b 0a 20  ext) iFinal--;. 
1d80: 20 20 20 70 46 69 6e 61 6c 20 3d 20 70 57 72 69     pFinal = pWri
1d90: 74 65 3b 0a 20 20 7d 0a 0a 23 69 66 64 65 66 20  te;.  }..#ifdef 
1da0: 54 52 41 43 45 5f 43 52 41 53 48 54 45 53 54 0a  TRACE_CRASHTEST.
1db0: 20 20 70 72 69 6e 74 66 28 22 53 79 6e 63 20 25    printf("Sync %
1dc0: 73 20 28 69 73 20 25 73 20 63 72 61 73 68 29 5c  s (is %s crash)\
1dd0: 6e 22 2c 20 70 46 69 6c 65 2d 3e 7a 4e 61 6d 65  n", pFile->zName
1de0: 2c 20 28 69 73 43 72 61 73 68 3f 22 61 22 3a 22  , (isCrash?"a":"
1df0: 6e 6f 74 20 61 22 29 29 3b 0a 23 65 6e 64 69 66  not a"));.#endif
1e00: 0a 0a 20 20 70 70 50 74 72 20 3d 20 26 67 2e 70  ..  ppPtr = &g.p
1e10: 57 72 69 74 65 4c 69 73 74 3b 0a 20 20 66 6f 72  WriteList;.  for
1e20: 28 70 57 72 69 74 65 3d 2a 70 70 50 74 72 3b 20  (pWrite=*ppPtr; 
1e30: 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 26 26  rc==SQLITE_OK &&
1e40: 20 70 57 72 69 74 65 3b 20 70 57 72 69 74 65 3d   pWrite; pWrite=
1e50: 2a 70 70 50 74 72 29 7b 0a 20 20 20 20 73 71 6c  *ppPtr){.    sql
1e60: 69 74 65 33 5f 66 69 6c 65 20 2a 70 52 65 61 6c  ite3_file *pReal
1e70: 46 69 6c 65 20 3d 20 70 57 72 69 74 65 2d 3e 70  File = pWrite->p
1e80: 46 69 6c 65 2d 3e 70 52 65 61 6c 46 69 6c 65 3b  File->pRealFile;
1e90: 0a 0a 20 20 20 20 2f 2a 20 28 65 41 63 74 69 6f  ..    /* (eActio
1ea0: 6e 3d 3d 31 29 20 20 20 20 20 20 2d 3e 20 77 72  n==1)      -> wr
1eb0: 69 74 65 20 62 6c 6f 63 6b 20 6f 75 74 20 6e 6f  ite block out no
1ec0: 72 6d 61 6c 6c 79 2c 0a 20 20 20 20 2a 2a 20 28  rmally,.    ** (
1ed0: 65 41 63 74 69 6f 6e 3d 3d 32 29 20 20 20 20 20  eAction==2)     
1ee0: 20 2d 3e 20 64 6f 20 6e 6f 74 68 69 6e 67 2c 0a   -> do nothing,.
1ef0: 20 20 20 20 2a 2a 20 28 65 41 63 74 69 6f 6e 3d      ** (eAction=
1f00: 3d 33 29 20 20 20 20 20 20 2d 3e 20 74 72 61 73  =3)      -> tras
1f10: 68 20 73 65 63 74 6f 72 73 2e 0a 20 20 20 20 2a  h sectors..    *
1f20: 2f 0a 20 20 20 20 69 6e 74 20 65 41 63 74 69 6f  /.    int eActio
1f30: 6e 20 3d 20 30 3b 0a 20 20 20 20 69 66 28 20 21  n = 0;.    if( !
1f40: 69 73 43 72 61 73 68 20 29 7b 0a 20 20 20 20 20  isCrash ){.     
1f50: 20 65 41 63 74 69 6f 6e 20 3d 20 32 3b 0a 20 20   eAction = 2;.  
1f60: 20 20 20 20 69 66 28 20 28 70 57 72 69 74 65 2d      if( (pWrite-
1f70: 3e 70 46 69 6c 65 3d 3d 70 46 69 6c 65 20 7c 7c  >pFile==pFile ||
1f80: 20 69 44 63 26 53 51 4c 49 54 45 5f 49 4f 43 41   iDc&SQLITE_IOCA
1f90: 50 5f 53 45 51 55 45 4e 54 49 41 4c 29 20 29 7b  P_SEQUENTIAL) ){
1fa0: 0a 20 20 20 20 20 20 20 20 65 41 63 74 69 6f 6e  .        eAction
1fb0: 20 3d 20 31 3b 0a 20 20 20 20 20 20 7d 0a 20 20   = 1;.      }.  
1fc0: 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 63    }else{.      c
1fd0: 68 61 72 20 72 61 6e 64 6f 6d 3b 0a 20 20 20 20  har random;.    
1fe0: 20 20 73 71 6c 69 74 65 33 52 61 6e 64 6f 6d 6e    sqlite3Randomn
1ff0: 65 73 73 28 31 2c 20 26 72 61 6e 64 6f 6d 29 3b  ess(1, &random);
2000: 0a 0a 20 20 20 20 20 20 2f 2a 20 44 6f 20 6e 6f  ..      /* Do no
2010: 74 20 73 65 6c 65 63 74 20 6f 70 74 69 6f 6e 20  t select option 
2020: 33 20 28 73 65 63 74 6f 72 20 74 72 61 73 68 69  3 (sector trashi
2030: 6e 67 29 20 69 66 20 74 68 65 20 49 4f 43 41 50  ng) if the IOCAP
2040: 5f 41 54 4f 4d 49 43 20 66 6c 61 67 20 0a 20 20  _ATOMIC flag .  
2050: 20 20 20 20 2a 2a 20 69 73 20 73 65 74 20 6f 72      ** is set or
2060: 20 74 68 69 73 20 69 73 20 61 6e 20 4f 73 54 72   this is an OsTr
2070: 75 6e 63 61 74 65 28 29 2c 20 6e 6f 74 20 61 6e  uncate(), not an
2080: 20 4f 73 77 72 69 74 65 28 29 2e 0a 20 20 20 20   Oswrite()..    
2090: 20 20 2a 2f 0a 20 20 20 20 20 20 69 66 28 20 28    */.      if( (
20a0: 69 44 63 26 53 51 4c 49 54 45 5f 49 4f 43 41 50  iDc&SQLITE_IOCAP
20b0: 5f 41 54 4f 4d 49 43 29 20 7c 7c 20 28 70 57 72  _ATOMIC) || (pWr
20c0: 69 74 65 2d 3e 7a 42 75 66 3d 3d 30 29 20 29 7b  ite->zBuf==0) ){
20d0: 0a 20 20 20 20 20 20 20 20 72 61 6e 64 6f 6d 20  .        random 
20e0: 26 3d 20 30 78 30 31 3b 0a 20 20 20 20 20 20 7d  &= 0x01;.      }
20f0: 0a 0a 20 20 20 20 20 20 2f 2a 20 49 66 20 49 4f  ..      /* If IO
2100: 43 41 50 5f 53 45 51 55 45 4e 54 49 41 4c 20 69  CAP_SEQUENTIAL i
2110: 73 20 73 65 74 20 61 6e 64 20 74 68 69 73 20 69  s set and this i
2120: 73 20 6e 6f 74 20 74 68 65 20 66 69 6e 61 6c 20  s not the final 
2130: 65 6e 74 72 79 0a 20 20 20 20 20 20 2a 2a 20 69  entry.      ** i
2140: 6e 20 74 68 65 20 74 72 75 6e 63 61 74 65 64 20  n the truncated 
2150: 77 72 69 74 65 2d 6c 69 73 74 2c 20 61 6c 77 61  write-list, alwa
2160: 79 73 20 73 65 6c 65 63 74 20 6f 70 74 69 6f 6e  ys select option
2170: 20 31 20 28 77 72 69 74 65 0a 20 20 20 20 20 20   1 (write.      
2180: 2a 2a 20 6f 75 74 20 63 6f 72 72 65 63 74 6c 79  ** out correctly
2190: 29 2e 0a 20 20 20 20 20 20 2a 2f 0a 20 20 20 20  )..      */.    
21a0: 20 20 69 66 28 20 28 69 44 63 26 53 51 4c 49 54    if( (iDc&SQLIT
21b0: 45 5f 49 4f 43 41 50 5f 53 45 51 55 45 4e 54 49  E_IOCAP_SEQUENTI
21c0: 41 4c 20 26 26 20 70 57 72 69 74 65 21 3d 70 46  AL && pWrite!=pF
21d0: 69 6e 61 6c 29 20 29 7b 0a 20 20 20 20 20 20 20  inal) ){.       
21e0: 20 72 61 6e 64 6f 6d 20 3d 20 30 3b 0a 20 20 20   random = 0;.   
21f0: 20 20 20 7d 0a 0a 20 20 20 20 20 20 2f 2a 20 49     }..      /* I
2200: 66 20 49 4f 43 41 50 5f 53 41 46 45 5f 41 50 50  f IOCAP_SAFE_APP
2210: 45 4e 44 20 69 73 20 73 65 74 20 61 6e 64 20 74  END is set and t
2220: 68 69 73 20 4f 73 57 72 69 74 65 28 29 20 6f 70  his OsWrite() op
2230: 65 72 61 74 69 6f 6e 20 69 73 0a 20 20 20 20 20  eration is.     
2240: 20 2a 2a 20 61 6e 20 61 70 70 65 6e 64 20 28 66   ** an append (f
2250: 69 72 73 74 20 62 79 74 65 20 6f 66 20 74 68 65  irst byte of the
2260: 20 77 72 69 74 74 65 6e 20 72 65 67 69 6f 6e 20   written region 
2270: 69 73 20 31 20 62 79 74 65 20 70 61 73 74 20 74  is 1 byte past t
2280: 68 65 0a 20 20 20 20 20 20 2a 2a 20 63 75 72 72  he.      ** curr
2290: 65 6e 74 20 45 4f 46 29 2c 20 61 6c 77 61 79 73  ent EOF), always
22a0: 20 73 65 6c 65 63 74 20 6f 70 74 69 6f 6e 20 31   select option 1
22b0: 20 28 77 72 69 74 65 20 6f 75 74 20 63 6f 72 72   (write out corr
22c0: 65 63 74 6c 79 29 2e 0a 20 20 20 20 20 20 2a 2f  ectly)..      */
22d0: 0a 20 20 20 20 20 20 69 66 28 20 69 44 63 26 53  .      if( iDc&S
22e0: 51 4c 49 54 45 5f 49 4f 43 41 50 5f 53 41 46 45  QLITE_IOCAP_SAFE
22f0: 5f 41 50 50 45 4e 44 20 26 26 20 70 57 72 69 74  _APPEND && pWrit
2300: 65 2d 3e 7a 42 75 66 20 29 7b 0a 20 20 20 20 20  e->zBuf ){.     
2310: 20 20 20 69 36 34 20 69 53 69 7a 65 3b 0a 20 20     i64 iSize;.  
2320: 20 20 20 20 20 20 73 71 6c 69 74 65 33 4f 73 46        sqlite3OsF
2330: 69 6c 65 53 69 7a 65 28 70 52 65 61 6c 46 69 6c  ileSize(pRealFil
2340: 65 2c 20 26 69 53 69 7a 65 29 3b 0a 20 20 20 20  e, &iSize);.    
2350: 20 20 20 20 69 66 28 20 69 53 69 7a 65 3d 3d 70      if( iSize==p
2360: 57 72 69 74 65 2d 3e 69 4f 66 66 73 65 74 20 29  Write->iOffset )
2370: 7b 0a 20 20 20 20 20 20 20 20 20 20 72 61 6e 64  {.          rand
2380: 6f 6d 20 3d 20 30 3b 0a 20 20 20 20 20 20 20 20  om = 0;.        
2390: 7d 0a 20 20 20 20 20 20 7d 0a 0a 20 20 20 20 20  }.      }..     
23a0: 20 69 66 28 20 28 72 61 6e 64 6f 6d 26 30 78 30   if( (random&0x0
23b0: 36 29 3d 3d 30 78 30 36 20 29 7b 0a 20 20 20 20  6)==0x06 ){.    
23c0: 20 20 20 20 65 41 63 74 69 6f 6e 20 3d 20 33 3b      eAction = 3;
23d0: 0a 20 20 20 20 20 20 7d 65 6c 73 65 7b 0a 20 20  .      }else{.  
23e0: 20 20 20 20 20 20 65 41 63 74 69 6f 6e 20 3d 20        eAction = 
23f0: 28 28 72 61 6e 64 6f 6d 26 30 78 30 31 29 3f 32  ((random&0x01)?2
2400: 3a 31 29 3b 0a 20 20 20 20 20 20 7d 0a 20 20 20  :1);.      }.   
2410: 20 7d 0a 0a 20 20 20 20 73 77 69 74 63 68 28 20   }..    switch( 
2420: 65 41 63 74 69 6f 6e 20 29 7b 0a 20 20 20 20 20  eAction ){.     
2430: 20 63 61 73 65 20 31 3a 20 7b 20 20 20 20 20 20   case 1: {      
2440: 20 20 20 20 20 20 20 20 20 2f 2a 20 57 72 69 74           /* Writ
2450: 65 20 6f 75 74 20 63 6f 72 72 65 63 74 6c 79 20  e out correctly 
2460: 2a 2f 0a 20 20 20 20 20 20 20 20 69 66 28 20 70  */.        if( p
2470: 57 72 69 74 65 2d 3e 7a 42 75 66 20 29 7b 0a 20  Write->zBuf ){. 
2480: 20 20 20 20 20 20 20 20 20 72 63 20 3d 20 73 71           rc = sq
2490: 6c 69 74 65 33 4f 73 57 72 69 74 65 28 0a 20 20  lite3OsWrite(.  
24a0: 20 20 20 20 20 20 20 20 20 20 20 20 70 52 65 61              pRea
24b0: 6c 46 69 6c 65 2c 20 70 57 72 69 74 65 2d 3e 7a  lFile, pWrite->z
24c0: 42 75 66 2c 20 70 57 72 69 74 65 2d 3e 6e 42 75  Buf, pWrite->nBu
24d0: 66 2c 20 70 57 72 69 74 65 2d 3e 69 4f 66 66 73  f, pWrite->iOffs
24e0: 65 74 0a 20 20 20 20 20 20 20 20 20 20 29 3b 0a  et.          );.
24f0: 20 20 20 20 20 20 20 20 7d 65 6c 73 65 7b 0a 20          }else{. 
2500: 20 20 20 20 20 20 20 20 20 72 63 20 3d 20 73 71           rc = sq
2510: 6c 69 74 65 33 4f 73 54 72 75 6e 63 61 74 65 28  lite3OsTruncate(
2520: 70 52 65 61 6c 46 69 6c 65 2c 20 70 57 72 69 74  pRealFile, pWrit
2530: 65 2d 3e 69 4f 66 66 73 65 74 29 3b 0a 20 20 20  e->iOffset);.   
2540: 20 20 20 20 20 7d 0a 20 20 20 20 20 20 20 20 2a       }.        *
2550: 70 70 50 74 72 20 3d 20 70 57 72 69 74 65 2d 3e  ppPtr = pWrite->
2560: 70 4e 65 78 74 3b 0a 23 69 66 64 65 66 20 54 52  pNext;.#ifdef TR
2570: 41 43 45 5f 43 52 41 53 48 54 45 53 54 0a 20 20  ACE_CRASHTEST.  
2580: 20 20 20 20 20 20 69 66 28 20 69 73 43 72 61 73        if( isCras
2590: 68 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20 70  h ){.          p
25a0: 72 69 6e 74 66 28 22 57 72 69 74 69 6e 67 20 25  rintf("Writing %
25b0: 64 20 62 79 74 65 73 20 40 20 25 64 20 28 25 73  d bytes @ %d (%s
25c0: 29 5c 6e 22 2c 20 0a 20 20 20 20 20 20 20 20 20  )\n", .         
25d0: 20 20 20 70 57 72 69 74 65 2d 3e 6e 42 75 66 2c     pWrite->nBuf,
25e0: 20 28 69 6e 74 29 70 57 72 69 74 65 2d 3e 69 4f   (int)pWrite->iO
25f0: 66 66 73 65 74 2c 20 70 57 72 69 74 65 2d 3e 70  ffset, pWrite->p
2600: 46 69 6c 65 2d 3e 7a 4e 61 6d 65 0a 20 20 20 20  File->zName.    
2610: 20 20 20 20 20 20 29 3b 0a 20 20 20 20 20 20 20        );.       
2620: 20 7d 0a 23 65 6e 64 69 66 0a 20 20 20 20 20 20   }.#endif.      
2630: 20 20 73 71 6c 69 74 65 33 5f 66 72 65 65 28 70    sqlite3_free(p
2640: 57 72 69 74 65 29 3b 0a 20 20 20 20 20 20 20 20  Write);.        
2650: 62 72 65 61 6b 3b 0a 20 20 20 20 20 20 7d 0a 20  break;.      }. 
2660: 20 20 20 20 20 63 61 73 65 20 32 3a 20 7b 20 20       case 2: {  
2670: 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
2680: 44 6f 20 6e 6f 74 68 69 6e 67 20 2a 2f 0a 20 20  Do nothing */.  
2690: 20 20 20 20 20 20 70 70 50 74 72 20 3d 20 26 70        ppPtr = &p
26a0: 57 72 69 74 65 2d 3e 70 4e 65 78 74 3b 0a 23 69  Write->pNext;.#i
26b0: 66 64 65 66 20 54 52 41 43 45 5f 43 52 41 53 48  fdef TRACE_CRASH
26c0: 54 45 53 54 0a 20 20 20 20 20 20 20 20 69 66 28  TEST.        if(
26d0: 20 69 73 43 72 61 73 68 20 29 7b 0a 20 20 20 20   isCrash ){.    
26e0: 20 20 20 20 20 20 70 72 69 6e 74 66 28 22 4f 6d        printf("Om
26f0: 69 74 69 6e 67 20 25 64 20 62 79 74 65 73 20 40  iting %d bytes @
2700: 20 25 64 20 28 25 73 29 5c 6e 22 2c 20 0a 20 20   %d (%s)\n", .  
2710: 20 20 20 20 20 20 20 20 20 20 70 57 72 69 74 65            pWrite
2720: 2d 3e 6e 42 75 66 2c 20 28 69 6e 74 29 70 57 72  ->nBuf, (int)pWr
2730: 69 74 65 2d 3e 69 4f 66 66 73 65 74 2c 20 70 57  ite->iOffset, pW
2740: 72 69 74 65 2d 3e 70 46 69 6c 65 2d 3e 7a 4e 61  rite->pFile->zNa
2750: 6d 65 0a 20 20 20 20 20 20 20 20 20 20 29 3b 0a  me.          );.
2760: 20 20 20 20 20 20 20 20 7d 0a 23 65 6e 64 69 66          }.#endif
2770: 0a 20 20 20 20 20 20 20 20 62 72 65 61 6b 3b 0a  .        break;.
2780: 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 63 61        }.      ca
2790: 73 65 20 33 3a 20 7b 20 20 20 20 20 20 20 20 20  se 3: {         
27a0: 20 20 20 20 20 20 2f 2a 20 54 72 61 73 68 20 73        /* Trash s
27b0: 65 63 74 6f 72 73 20 2a 2f 0a 20 20 20 20 20 20  ectors */.      
27c0: 20 20 75 38 20 2a 7a 47 61 72 62 61 67 65 3b 0a    u8 *zGarbage;.
27d0: 20 20 20 20 20 20 20 20 69 6e 74 20 69 46 69 72          int iFir
27e0: 73 74 20 3d 20 28 70 57 72 69 74 65 2d 3e 69 4f  st = (pWrite->iO
27f0: 66 66 73 65 74 2f 67 2e 69 53 65 63 74 6f 72 53  ffset/g.iSectorS
2800: 69 7a 65 29 3b 0a 20 20 20 20 20 20 20 20 69 6e  ize);.        in
2810: 74 20 69 4c 61 73 74 20 3d 20 28 70 57 72 69 74  t iLast = (pWrit
2820: 65 2d 3e 69 4f 66 66 73 65 74 2b 70 57 72 69 74  e->iOffset+pWrit
2830: 65 2d 3e 6e 42 75 66 2d 31 29 2f 67 2e 69 53 65  e->nBuf-1)/g.iSe
2840: 63 74 6f 72 53 69 7a 65 3b 0a 0a 20 20 20 20 20  ctorSize;..     
2850: 20 20 20 61 73 73 65 72 74 28 70 57 72 69 74 65     assert(pWrite
2860: 2d 3e 7a 42 75 66 29 3b 0a 0a 23 69 66 64 65 66  ->zBuf);..#ifdef
2870: 20 54 52 41 43 45 5f 43 52 41 53 48 54 45 53 54   TRACE_CRASHTEST
2880: 0a 20 20 20 20 20 20 20 20 70 72 69 6e 74 66 28  .        printf(
2890: 22 54 72 61 73 68 69 6e 67 20 25 64 20 73 65 63  "Trashing %d sec
28a0: 74 6f 72 73 20 40 20 73 65 63 74 6f 72 20 25 64  tors @ sector %d
28b0: 20 28 25 73 29 5c 6e 22 2c 20 0a 20 20 20 20 20   (%s)\n", .     
28c0: 20 20 20 20 20 20 20 31 2b 69 4c 61 73 74 2d 69         1+iLast-i
28d0: 46 69 72 73 74 2c 20 69 46 69 72 73 74 2c 20 70  First, iFirst, p
28e0: 57 72 69 74 65 2d 3e 70 46 69 6c 65 2d 3e 7a 4e  Write->pFile->zN
28f0: 61 6d 65 0a 20 20 20 20 20 20 20 20 29 3b 0a 23  ame.        );.#
2900: 65 6e 64 69 66 0a 0a 20 20 20 20 20 20 20 20 7a  endif..        z
2910: 47 61 72 62 61 67 65 20 3d 20 73 71 6c 69 74 65  Garbage = sqlite
2920: 33 5f 6d 61 6c 6c 6f 63 28 67 2e 69 53 65 63 74  3_malloc(g.iSect
2930: 6f 72 53 69 7a 65 29 3b 0a 20 20 20 20 20 20 20  orSize);.       
2940: 20 69 66 28 20 7a 47 61 72 62 61 67 65 20 29 7b   if( zGarbage ){
2950: 0a 20 20 20 20 20 20 20 20 20 20 73 71 6c 69 74  .          sqlit
2960: 65 33 5f 69 6e 74 36 34 20 69 3b 0a 20 20 20 20  e3_int64 i;.    
2970: 20 20 20 20 20 20 66 6f 72 28 69 3d 69 46 69 72        for(i=iFir
2980: 73 74 3b 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f  st; rc==SQLITE_O
2990: 4b 20 26 26 20 69 3c 3d 69 4c 61 73 74 3b 20 69  K && i<=iLast; i
29a0: 2b 2b 29 7b 0a 20 20 20 20 20 20 20 20 20 20 20  ++){.           
29b0: 20 73 71 6c 69 74 65 33 52 61 6e 64 6f 6d 6e 65   sqlite3Randomne
29c0: 73 73 28 67 2e 69 53 65 63 74 6f 72 53 69 7a 65  ss(g.iSectorSize
29d0: 2c 20 7a 47 61 72 62 61 67 65 29 3b 20 0a 20 20  , zGarbage); .  
29e0: 20 20 20 20 20 20 20 20 20 20 72 63 20 3d 20 73            rc = s
29f0: 71 6c 69 74 65 33 4f 73 57 72 69 74 65 28 0a 20  qlite3OsWrite(. 
2a00: 20 20 20 20 20 20 20 20 20 20 20 20 20 70 52 65               pRe
2a10: 61 6c 46 69 6c 65 2c 20 7a 47 61 72 62 61 67 65  alFile, zGarbage
2a20: 2c 20 67 2e 69 53 65 63 74 6f 72 53 69 7a 65 2c  , g.iSectorSize,
2a30: 20 69 2a 67 2e 69 53 65 63 74 6f 72 53 69 7a 65   i*g.iSectorSize
2a40: 0a 20 20 20 20 20 20 20 20 20 20 20 20 29 3b 0a  .            );.
2a50: 20 20 20 20 20 20 20 20 20 20 7d 0a 20 20 20 20            }.    
2a60: 20 20 20 20 20 20 73 71 6c 69 74 65 33 5f 66 72        sqlite3_fr
2a70: 65 65 28 7a 47 61 72 62 61 67 65 29 3b 0a 20 20  ee(zGarbage);.  
2a80: 20 20 20 20 20 20 7d 65 6c 73 65 7b 0a 20 20 20        }else{.   
2a90: 20 20 20 20 20 20 20 72 63 20 3d 20 53 51 4c 49         rc = SQLI
2aa0: 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20 20 20 20 20  TE_NOMEM;.      
2ab0: 20 20 7d 0a 0a 20 20 20 20 20 20 20 20 70 70 50    }..        ppP
2ac0: 74 72 20 3d 20 26 70 57 72 69 74 65 2d 3e 70 4e  tr = &pWrite->pN
2ad0: 65 78 74 3b 0a 20 20 20 20 20 20 20 20 62 72 65  ext;.        bre
2ae0: 61 6b 3b 0a 20 20 20 20 20 20 7d 0a 0a 20 20 20  ak;.      }..   
2af0: 20 20 20 64 65 66 61 75 6c 74 3a 0a 20 20 20 20     default:.    
2b00: 20 20 20 20 61 73 73 65 72 74 28 21 22 43 61 6e      assert(!"Can
2b10: 6e 6f 74 20 68 61 70 70 65 6e 22 29 3b 0a 20 20  not happen");.  
2b20: 20 20 7d 0a 0a 20 20 20 20 69 66 28 20 70 57 72    }..    if( pWr
2b30: 69 74 65 3d 3d 70 46 69 6e 61 6c 20 29 20 62 72  ite==pFinal ) br
2b40: 65 61 6b 3b 0a 20 20 7d 0a 0a 20 20 69 66 28 20  eak;.  }..  if( 
2b50: 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 26 26  rc==SQLITE_OK &&
2b60: 20 69 73 43 72 61 73 68 20 29 7b 0a 20 20 20 20   isCrash ){.    
2b70: 65 78 69 74 28 2d 31 29 3b 0a 20 20 7d 0a 0a 20  exit(-1);.  }.. 
2b80: 20 66 6f 72 28 70 57 72 69 74 65 3d 67 2e 70 57   for(pWrite=g.pW
2b90: 72 69 74 65 4c 69 73 74 3b 20 70 57 72 69 74 65  riteList; pWrite
2ba0: 20 26 26 20 70 57 72 69 74 65 2d 3e 70 4e 65 78   && pWrite->pNex
2bb0: 74 3b 20 70 57 72 69 74 65 3d 70 57 72 69 74 65  t; pWrite=pWrite
2bc0: 2d 3e 70 4e 65 78 74 29 3b 0a 20 20 67 2e 70 57  ->pNext);.  g.pW
2bd0: 72 69 74 65 4c 69 73 74 45 6e 64 20 3d 20 70 57  riteListEnd = pW
2be0: 72 69 74 65 3b 0a 0a 20 20 72 65 74 75 72 6e 20  rite;..  return 
2bf0: 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 41 64 64  rc;.}../*.** Add
2c00: 20 61 6e 20 65 6e 74 72 79 20 74 6f 20 74 68 65   an entry to the
2c10: 20 65 6e 64 20 6f 66 20 74 68 65 20 77 72 69 74   end of the writ
2c20: 65 2d 6c 69 73 74 2e 0a 2a 2f 0a 73 74 61 74 69  e-list..*/.stati
2c30: 63 20 69 6e 74 20 77 72 69 74 65 4c 69 73 74 41  c int writeListA
2c40: 70 70 65 6e 64 28 0a 20 20 73 71 6c 69 74 65 33  ppend(.  sqlite3
2c50: 5f 66 69 6c 65 20 2a 70 46 69 6c 65 2c 0a 20 20  _file *pFile,.  
2c60: 73 71 6c 69 74 65 33 5f 69 6e 74 36 34 20 69 4f  sqlite3_int64 iO
2c70: 66 66 73 65 74 2c 0a 20 20 63 6f 6e 73 74 20 75  ffset,.  const u
2c80: 38 20 2a 7a 42 75 66 2c 0a 20 20 69 6e 74 20 6e  8 *zBuf,.  int n
2c90: 42 75 66 0a 29 7b 0a 20 20 57 72 69 74 65 42 75  Buf.){.  WriteBu
2ca0: 66 66 65 72 20 2a 70 4e 65 77 3b 0a 0a 20 20 61  ffer *pNew;..  a
2cb0: 73 73 65 72 74 28 28 7a 42 75 66 20 26 26 20 6e  ssert((zBuf && n
2cc0: 42 75 66 29 20 7c 7c 20 28 21 6e 42 75 66 20 26  Buf) || (!nBuf &
2cd0: 26 20 21 7a 42 75 66 29 29 3b 0a 0a 20 20 70 4e  & !zBuf));..  pN
2ce0: 65 77 20 3d 20 28 57 72 69 74 65 42 75 66 66 65  ew = (WriteBuffe
2cf0: 72 20 2a 29 73 71 6c 69 74 65 33 4d 61 6c 6c 6f  r *)sqlite3Mallo
2d00: 63 5a 65 72 6f 28 73 69 7a 65 6f 66 28 57 72 69  cZero(sizeof(Wri
2d10: 74 65 42 75 66 66 65 72 29 20 2b 20 6e 42 75 66  teBuffer) + nBuf
2d20: 29 3b 0a 20 20 70 4e 65 77 2d 3e 69 4f 66 66 73  );.  pNew->iOffs
2d30: 65 74 20 3d 20 69 4f 66 66 73 65 74 3b 0a 20 20  et = iOffset;.  
2d40: 70 4e 65 77 2d 3e 6e 42 75 66 20 3d 20 6e 42 75  pNew->nBuf = nBu
2d50: 66 3b 0a 20 20 70 4e 65 77 2d 3e 70 46 69 6c 65  f;.  pNew->pFile
2d60: 20 3d 20 28 43 72 61 73 68 46 69 6c 65 20 2a 29   = (CrashFile *)
2d70: 70 46 69 6c 65 3b 0a 20 20 69 66 28 20 7a 42 75  pFile;.  if( zBu
2d80: 66 20 29 7b 0a 20 20 20 20 70 4e 65 77 2d 3e 7a  f ){.    pNew->z
2d90: 42 75 66 20 3d 20 28 75 38 20 2a 29 26 70 4e 65  Buf = (u8 *)&pNe
2da0: 77 5b 31 5d 3b 0a 20 20 20 20 6d 65 6d 63 70 79  w[1];.    memcpy
2db0: 28 70 4e 65 77 2d 3e 7a 42 75 66 2c 20 7a 42 75  (pNew->zBuf, zBu
2dc0: 66 2c 20 6e 42 75 66 29 3b 0a 20 20 7d 0a 0a 20  f, nBuf);.  }.. 
2dd0: 20 69 66 28 20 67 2e 70 57 72 69 74 65 4c 69 73   if( g.pWriteLis
2de0: 74 20 29 7b 0a 20 20 20 20 61 73 73 65 72 74 28  t ){.    assert(
2df0: 67 2e 70 57 72 69 74 65 4c 69 73 74 45 6e 64 29  g.pWriteListEnd)
2e00: 3b 0a 20 20 20 20 67 2e 70 57 72 69 74 65 4c 69  ;.    g.pWriteLi
2e10: 73 74 45 6e 64 2d 3e 70 4e 65 78 74 20 3d 20 70  stEnd->pNext = p
2e20: 4e 65 77 3b 0a 20 20 7d 65 6c 73 65 7b 0a 20 20  New;.  }else{.  
2e30: 20 20 67 2e 70 57 72 69 74 65 4c 69 73 74 20 3d    g.pWriteList =
2e40: 20 70 4e 65 77 3b 0a 20 20 7d 0a 20 20 67 2e 70   pNew;.  }.  g.p
2e50: 57 72 69 74 65 4c 69 73 74 45 6e 64 20 3d 20 70  WriteListEnd = p
2e60: 4e 65 77 3b 0a 20 20 0a 20 20 72 65 74 75 72 6e  New;.  .  return
2e70: 20 53 51 4c 49 54 45 5f 4f 4b 3b 0a 7d 0a 0a 2f   SQLITE_OK;.}../
2e80: 2a 0a 2a 2a 20 43 6c 6f 73 65 20 61 20 63 72 61  *.** Close a cra
2e90: 73 68 2d 66 69 6c 65 2e 0a 2a 2f 0a 73 74 61 74  sh-file..*/.stat
2ea0: 69 63 20 69 6e 74 20 63 66 43 6c 6f 73 65 28 73  ic int cfClose(s
2eb0: 71 6c 69 74 65 33 5f 66 69 6c 65 20 2a 70 46 69  qlite3_file *pFi
2ec0: 6c 65 29 7b 0a 20 20 43 72 61 73 68 46 69 6c 65  le){.  CrashFile
2ed0: 20 2a 70 43 72 61 73 68 20 3d 20 28 43 72 61 73   *pCrash = (Cras
2ee0: 68 46 69 6c 65 20 2a 29 70 46 69 6c 65 3b 0a 20  hFile *)pFile;. 
2ef0: 20 77 72 69 74 65 4c 69 73 74 53 79 6e 63 28 70   writeListSync(p
2f00: 43 72 61 73 68 2c 20 30 29 3b 0a 20 20 73 71 6c  Crash, 0);.  sql
2f10: 69 74 65 33 4f 73 43 6c 6f 73 65 28 70 43 72 61  ite3OsClose(pCra
2f20: 73 68 2d 3e 70 52 65 61 6c 46 69 6c 65 29 3b 0a  sh->pRealFile);.
2f30: 20 20 72 65 74 75 72 6e 20 53 51 4c 49 54 45 5f    return SQLITE_
2f40: 4f 4b 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 52 65 61  OK;.}../*.** Rea
2f50: 64 20 64 61 74 61 20 66 72 6f 6d 20 61 20 63 72  d data from a cr
2f60: 61 73 68 2d 66 69 6c 65 2e 0a 2a 2f 0a 73 74 61  ash-file..*/.sta
2f70: 74 69 63 20 69 6e 74 20 63 66 52 65 61 64 28 0a  tic int cfRead(.
2f80: 20 20 73 71 6c 69 74 65 33 5f 66 69 6c 65 20 2a    sqlite3_file *
2f90: 70 46 69 6c 65 2c 20 0a 20 20 76 6f 69 64 20 2a  pFile, .  void *
2fa0: 7a 42 75 66 2c 20 0a 20 20 69 6e 74 20 69 41 6d  zBuf, .  int iAm
2fb0: 74 2c 20 0a 20 20 73 71 6c 69 74 65 5f 69 6e 74  t, .  sqlite_int
2fc0: 36 34 20 69 4f 66 73 74 0a 29 7b 0a 20 20 43 72  64 iOfst.){.  Cr
2fd0: 61 73 68 46 69 6c 65 20 2a 70 43 72 61 73 68 20  ashFile *pCrash 
2fe0: 3d 20 28 43 72 61 73 68 46 69 6c 65 20 2a 29 70  = (CrashFile *)p
2ff0: 46 69 6c 65 3b 0a 0a 20 20 2f 2a 20 43 68 65 63  File;..  /* Chec
3000: 6b 20 74 68 65 20 66 69 6c 65 2d 73 69 7a 65 20  k the file-size 
3010: 74 6f 20 73 65 65 20 69 66 20 74 68 69 73 20 69  to see if this i
3020: 73 20 61 20 73 68 6f 72 74 2d 72 65 61 64 20 2a  s a short-read *
3030: 2f 0a 20 20 69 66 28 20 70 43 72 61 73 68 2d 3e  /.  if( pCrash->
3040: 69 53 69 7a 65 3c 28 69 4f 66 73 74 2b 69 41 6d  iSize<(iOfst+iAm
3050: 74 29 20 29 7b 0a 20 20 20 20 72 65 74 75 72 6e  t) ){.    return
3060: 20 53 51 4c 49 54 45 5f 49 4f 45 52 52 5f 53 48   SQLITE_IOERR_SH
3070: 4f 52 54 5f 52 45 41 44 3b 0a 20 20 7d 0a 0a 20  ORT_READ;.  }.. 
3080: 20 6d 65 6d 63 70 79 28 7a 42 75 66 2c 20 26 70   memcpy(zBuf, &p
3090: 43 72 61 73 68 2d 3e 7a 44 61 74 61 5b 69 4f 66  Crash->zData[iOf
30a0: 73 74 5d 2c 20 69 41 6d 74 29 3b 0a 20 20 72 65  st], iAmt);.  re
30b0: 74 75 72 6e 20 53 51 4c 49 54 45 5f 4f 4b 3b 0a  turn SQLITE_OK;.
30c0: 7d 0a 0a 2f 2a 0a 2a 2a 20 57 72 69 74 65 20 64  }../*.** Write d
30d0: 61 74 61 20 74 6f 20 61 20 63 72 61 73 68 2d 66  ata to a crash-f
30e0: 69 6c 65 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69  ile..*/.static i
30f0: 6e 74 20 63 66 57 72 69 74 65 28 0a 20 20 73 71  nt cfWrite(.  sq
3100: 6c 69 74 65 33 5f 66 69 6c 65 20 2a 70 46 69 6c  lite3_file *pFil
3110: 65 2c 20 0a 20 20 63 6f 6e 73 74 20 76 6f 69 64  e, .  const void
3120: 20 2a 7a 42 75 66 2c 20 0a 20 20 69 6e 74 20 69   *zBuf, .  int i
3130: 41 6d 74 2c 20 0a 20 20 73 71 6c 69 74 65 5f 69  Amt, .  sqlite_i
3140: 6e 74 36 34 20 69 4f 66 73 74 0a 29 7b 0a 20 20  nt64 iOfst.){.  
3150: 43 72 61 73 68 46 69 6c 65 20 2a 70 43 72 61 73  CrashFile *pCras
3160: 68 20 3d 20 28 43 72 61 73 68 46 69 6c 65 20 2a  h = (CrashFile *
3170: 29 70 46 69 6c 65 3b 0a 20 20 69 66 28 20 69 41  )pFile;.  if( iA
3180: 6d 74 2b 69 4f 66 73 74 3e 70 43 72 61 73 68 2d  mt+iOfst>pCrash-
3190: 3e 69 53 69 7a 65 20 29 7b 0a 20 20 20 20 70 43  >iSize ){.    pC
31a0: 72 61 73 68 2d 3e 69 53 69 7a 65 20 3d 20 69 41  rash->iSize = iA
31b0: 6d 74 2b 69 4f 66 73 74 3b 0a 20 20 7d 0a 20 20  mt+iOfst;.  }.  
31c0: 77 68 69 6c 65 28 20 70 43 72 61 73 68 2d 3e 69  while( pCrash->i
31d0: 53 69 7a 65 3e 70 43 72 61 73 68 2d 3e 6e 44 61  Size>pCrash->nDa
31e0: 74 61 20 29 7b 0a 20 20 20 20 75 38 20 2a 7a 4e  ta ){.    u8 *zN
31f0: 65 77 3b 0a 20 20 20 20 69 6e 74 20 6e 4e 65 77  ew;.    int nNew
3200: 20 3d 20 28 70 43 72 61 73 68 2d 3e 6e 44 61 74   = (pCrash->nDat
3210: 61 2a 32 29 20 2b 20 34 30 39 36 3b 0a 20 20 20  a*2) + 4096;.   
3220: 20 7a 4e 65 77 20 3d 20 73 71 6c 69 74 65 33 5f   zNew = sqlite3_
3230: 72 65 61 6c 6c 6f 63 28 70 43 72 61 73 68 2d 3e  realloc(pCrash->
3240: 7a 44 61 74 61 2c 20 6e 4e 65 77 29 3b 0a 20 20  zData, nNew);.  
3250: 20 20 69 66 28 20 21 7a 4e 65 77 20 29 7b 0a 20    if( !zNew ){. 
3260: 20 20 20 20 20 72 65 74 75 72 6e 20 53 51 4c 49       return SQLI
3270: 54 45 5f 4e 4f 4d 45 4d 3b 0a 20 20 20 20 7d 0a  TE_NOMEM;.    }.
3280: 20 20 20 20 6d 65 6d 73 65 74 28 26 7a 4e 65 77      memset(&zNew
3290: 5b 70 43 72 61 73 68 2d 3e 6e 44 61 74 61 5d 2c  [pCrash->nData],
32a0: 20 30 2c 20 6e 4e 65 77 2d 70 43 72 61 73 68 2d   0, nNew-pCrash-
32b0: 3e 6e 44 61 74 61 29 3b 0a 20 20 20 20 70 43 72  >nData);.    pCr
32c0: 61 73 68 2d 3e 6e 44 61 74 61 20 3d 20 6e 4e 65  ash->nData = nNe
32d0: 77 3b 0a 20 20 20 20 70 43 72 61 73 68 2d 3e 7a  w;.    pCrash->z
32e0: 44 61 74 61 20 3d 20 7a 4e 65 77 3b 0a 20 20 7d  Data = zNew;.  }
32f0: 0a 20 20 6d 65 6d 63 70 79 28 26 70 43 72 61 73  .  memcpy(&pCras
3300: 68 2d 3e 7a 44 61 74 61 5b 69 4f 66 73 74 5d 2c  h->zData[iOfst],
3310: 20 7a 42 75 66 2c 20 69 41 6d 74 29 3b 0a 20 20   zBuf, iAmt);.  
3320: 72 65 74 75 72 6e 20 77 72 69 74 65 4c 69 73 74  return writeList
3330: 41 70 70 65 6e 64 28 70 46 69 6c 65 2c 20 69 4f  Append(pFile, iO
3340: 66 73 74 2c 20 7a 42 75 66 2c 20 69 41 6d 74 29  fst, zBuf, iAmt)
3350: 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 54 72 75 6e 63  ;.}../*.** Trunc
3360: 61 74 65 20 61 20 63 72 61 73 68 2d 66 69 6c 65  ate a crash-file
3370: 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20  ..*/.static int 
3380: 63 66 54 72 75 6e 63 61 74 65 28 73 71 6c 69 74  cfTruncate(sqlit
3390: 65 33 5f 66 69 6c 65 20 2a 70 46 69 6c 65 2c 20  e3_file *pFile, 
33a0: 73 71 6c 69 74 65 5f 69 6e 74 36 34 20 73 69 7a  sqlite_int64 siz
33b0: 65 29 7b 0a 20 20 43 72 61 73 68 46 69 6c 65 20  e){.  CrashFile 
33c0: 2a 70 43 72 61 73 68 20 3d 20 28 43 72 61 73 68  *pCrash = (Crash
33d0: 46 69 6c 65 20 2a 29 70 46 69 6c 65 3b 0a 20 20  File *)pFile;.  
33e0: 61 73 73 65 72 74 28 73 69 7a 65 3e 3d 30 29 3b  assert(size>=0);
33f0: 0a 20 20 69 66 28 20 70 43 72 61 73 68 2d 3e 69  .  if( pCrash->i
3400: 53 69 7a 65 3e 73 69 7a 65 20 29 7b 0a 20 20 20  Size>size ){.   
3410: 20 70 43 72 61 73 68 2d 3e 69 53 69 7a 65 20 3d   pCrash->iSize =
3420: 20 73 69 7a 65 3b 0a 20 20 7d 0a 20 20 72 65 74   size;.  }.  ret
3430: 75 72 6e 20 77 72 69 74 65 4c 69 73 74 41 70 70  urn writeListApp
3440: 65 6e 64 28 70 46 69 6c 65 2c 20 73 69 7a 65 2c  end(pFile, size,
3450: 20 30 2c 20 30 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a   0, 0);.}../*.**
3460: 20 53 79 6e 63 20 61 20 63 72 61 73 68 2d 66 69   Sync a crash-fi
3470: 6c 65 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e  le..*/.static in
3480: 74 20 63 66 53 79 6e 63 28 73 71 6c 69 74 65 33  t cfSync(sqlite3
3490: 5f 66 69 6c 65 20 2a 70 46 69 6c 65 2c 20 69 6e  _file *pFile, in
34a0: 74 20 66 6c 61 67 73 29 7b 0a 20 20 43 72 61 73  t flags){.  Cras
34b0: 68 46 69 6c 65 20 2a 70 43 72 61 73 68 20 3d 20  hFile *pCrash = 
34c0: 28 43 72 61 73 68 46 69 6c 65 20 2a 29 70 46 69  (CrashFile *)pFi
34d0: 6c 65 3b 0a 20 20 69 6e 74 20 69 73 43 72 61 73  le;.  int isCras
34e0: 68 20 3d 20 30 3b 0a 0a 20 20 63 6f 6e 73 74 20  h = 0;..  const 
34f0: 63 68 61 72 20 2a 7a 4e 61 6d 65 20 3d 20 70 43  char *zName = pC
3500: 72 61 73 68 2d 3e 7a 4e 61 6d 65 3b 0a 20 20 63  rash->zName;.  c
3510: 6f 6e 73 74 20 63 68 61 72 20 2a 7a 43 72 61 73  onst char *zCras
3520: 68 46 69 6c 65 20 3d 20 67 2e 7a 43 72 61 73 68  hFile = g.zCrash
3530: 46 69 6c 65 3b 0a 20 20 69 6e 74 20 6e 4e 61 6d  File;.  int nNam
3540: 65 20 3d 20 73 74 72 6c 65 6e 28 7a 4e 61 6d 65  e = strlen(zName
3550: 29 3b 0a 20 20 69 6e 74 20 6e 43 72 61 73 68 46  );.  int nCrashF
3560: 69 6c 65 20 3d 20 73 74 72 6c 65 6e 28 7a 43 72  ile = strlen(zCr
3570: 61 73 68 46 69 6c 65 29 3b 0a 0a 20 20 69 66 28  ashFile);..  if(
3580: 20 6e 43 72 61 73 68 46 69 6c 65 3e 30 20 26 26   nCrashFile>0 &&
3590: 20 7a 43 72 61 73 68 46 69 6c 65 5b 6e 43 72 61   zCrashFile[nCra
35a0: 73 68 46 69 6c 65 2d 31 5d 3d 3d 27 2a 27 20 29  shFile-1]=='*' )
35b0: 7b 0a 20 20 20 20 6e 43 72 61 73 68 46 69 6c 65  {.    nCrashFile
35c0: 2d 2d 3b 0a 20 20 20 20 69 66 28 20 6e 4e 61 6d  --;.    if( nNam
35d0: 65 3e 6e 43 72 61 73 68 46 69 6c 65 20 29 20 6e  e>nCrashFile ) n
35e0: 4e 61 6d 65 20 3d 20 6e 43 72 61 73 68 46 69 6c  Name = nCrashFil
35f0: 65 3b 0a 20 20 7d 0a 0a 20 20 69 66 28 20 6e 4e  e;.  }..  if( nN
3600: 61 6d 65 3d 3d 6e 43 72 61 73 68 46 69 6c 65 20  ame==nCrashFile 
3610: 26 26 20 30 3d 3d 6d 65 6d 63 6d 70 28 7a 4e 61  && 0==memcmp(zNa
3620: 6d 65 2c 20 7a 43 72 61 73 68 46 69 6c 65 2c 20  me, zCrashFile, 
3630: 6e 4e 61 6d 65 29 20 29 7b 0a 20 20 20 20 69 66  nName) ){.    if
3640: 28 20 28 2d 2d 67 2e 69 43 72 61 73 68 29 3d 3d  ( (--g.iCrash)==
3650: 30 20 29 20 69 73 43 72 61 73 68 20 3d 20 31 3b  0 ) isCrash = 1;
3660: 0a 20 20 7d 0a 0a 20 20 72 65 74 75 72 6e 20 77  .  }..  return w
3670: 72 69 74 65 4c 69 73 74 53 79 6e 63 28 70 43 72  riteListSync(pCr
3680: 61 73 68 2c 20 69 73 43 72 61 73 68 29 3b 0a 7d  ash, isCrash);.}
3690: 0a 0a 2f 2a 0a 2a 2a 20 52 65 74 75 72 6e 20 74  ../*.** Return t
36a0: 68 65 20 63 75 72 72 65 6e 74 20 66 69 6c 65 2d  he current file-
36b0: 73 69 7a 65 20 6f 66 20 74 68 65 20 63 72 61 73  size of the cras
36c0: 68 2d 66 69 6c 65 2e 0a 2a 2f 0a 73 74 61 74 69  h-file..*/.stati
36d0: 63 20 69 6e 74 20 63 66 46 69 6c 65 53 69 7a 65  c int cfFileSize
36e0: 28 73 71 6c 69 74 65 33 5f 66 69 6c 65 20 2a 70  (sqlite3_file *p
36f0: 46 69 6c 65 2c 20 73 71 6c 69 74 65 5f 69 6e 74  File, sqlite_int
3700: 36 34 20 2a 70 53 69 7a 65 29 7b 0a 20 20 43 72  64 *pSize){.  Cr
3710: 61 73 68 46 69 6c 65 20 2a 70 43 72 61 73 68 20  ashFile *pCrash 
3720: 3d 20 28 43 72 61 73 68 46 69 6c 65 20 2a 29 70  = (CrashFile *)p
3730: 46 69 6c 65 3b 0a 20 20 2a 70 53 69 7a 65 20 3d  File;.  *pSize =
3740: 20 28 69 36 34 29 70 43 72 61 73 68 2d 3e 69 53   (i64)pCrash->iS
3750: 69 7a 65 3b 0a 20 20 72 65 74 75 72 6e 20 53 51  ize;.  return SQ
3760: 4c 49 54 45 5f 4f 4b 3b 0a 7d 0a 0a 2f 2a 0a 2a  LITE_OK;.}../*.*
3770: 2a 20 43 61 6c 6c 73 20 72 65 6c 61 74 65 64 20  * Calls related 
3780: 74 6f 20 66 69 6c 65 2d 6c 6f 63 6b 73 20 61 72  to file-locks ar
3790: 65 20 70 61 73 73 65 64 20 6f 6e 20 74 6f 20 74  e passed on to t
37a0: 68 65 20 72 65 61 6c 20 66 69 6c 65 20 68 61 6e  he real file han
37b0: 64 6c 65 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69  dle..*/.static i
37c0: 6e 74 20 63 66 4c 6f 63 6b 28 73 71 6c 69 74 65  nt cfLock(sqlite
37d0: 33 5f 66 69 6c 65 20 2a 70 46 69 6c 65 2c 20 69  3_file *pFile, i
37e0: 6e 74 20 65 4c 6f 63 6b 29 7b 0a 20 20 72 65 74  nt eLock){.  ret
37f0: 75 72 6e 20 73 71 6c 69 74 65 33 4f 73 4c 6f 63  urn sqlite3OsLoc
3800: 6b 28 28 28 43 72 61 73 68 46 69 6c 65 20 2a 29  k(((CrashFile *)
3810: 70 46 69 6c 65 29 2d 3e 70 52 65 61 6c 46 69 6c  pFile)->pRealFil
3820: 65 2c 20 65 4c 6f 63 6b 29 3b 0a 7d 0a 73 74 61  e, eLock);.}.sta
3830: 74 69 63 20 69 6e 74 20 63 66 55 6e 6c 6f 63 6b  tic int cfUnlock
3840: 28 73 71 6c 69 74 65 33 5f 66 69 6c 65 20 2a 70  (sqlite3_file *p
3850: 46 69 6c 65 2c 20 69 6e 74 20 65 4c 6f 63 6b 29  File, int eLock)
3860: 7b 0a 20 20 72 65 74 75 72 6e 20 73 71 6c 69 74  {.  return sqlit
3870: 65 33 4f 73 55 6e 6c 6f 63 6b 28 28 28 43 72 61  e3OsUnlock(((Cra
3880: 73 68 46 69 6c 65 20 2a 29 70 46 69 6c 65 29 2d  shFile *)pFile)-
3890: 3e 70 52 65 61 6c 46 69 6c 65 2c 20 65 4c 6f 63  >pRealFile, eLoc
38a0: 6b 29 3b 0a 7d 0a 73 74 61 74 69 63 20 69 6e 74  k);.}.static int
38b0: 20 63 66 43 68 65 63 6b 52 65 73 65 72 76 65 64   cfCheckReserved
38c0: 4c 6f 63 6b 28 73 71 6c 69 74 65 33 5f 66 69 6c  Lock(sqlite3_fil
38d0: 65 20 2a 70 46 69 6c 65 29 7b 0a 20 20 72 65 74  e *pFile){.  ret
38e0: 75 72 6e 20 73 71 6c 69 74 65 33 4f 73 43 68 65  urn sqlite3OsChe
38f0: 63 6b 52 65 73 65 72 76 65 64 4c 6f 63 6b 28 28  ckReservedLock((
3900: 28 43 72 61 73 68 46 69 6c 65 20 2a 29 70 46 69  (CrashFile *)pFi
3910: 6c 65 29 2d 3e 70 52 65 61 6c 46 69 6c 65 29 3b  le)->pRealFile);
3920: 0a 7d 0a 73 74 61 74 69 63 20 69 6e 74 20 63 66  .}.static int cf
3930: 4c 6f 63 6b 53 74 61 74 65 28 73 71 6c 69 74 65  LockState(sqlite
3940: 33 5f 66 69 6c 65 20 2a 70 46 69 6c 65 29 7b 0a  3_file *pFile){.
3950: 20 20 72 65 74 75 72 6e 20 73 71 6c 69 74 65 33    return sqlite3
3960: 4f 73 4c 6f 63 6b 53 74 61 74 65 28 28 28 43 72  OsLockState(((Cr
3970: 61 73 68 46 69 6c 65 20 2a 29 70 46 69 6c 65 29  ashFile *)pFile)
3980: 2d 3e 70 52 65 61 6c 46 69 6c 65 29 3b 0a 7d 0a  ->pRealFile);.}.
3990: 73 74 61 74 69 63 20 69 6e 74 20 63 66 42 72 65  static int cfBre
39a0: 61 6b 4c 6f 63 6b 28 73 71 6c 69 74 65 33 5f 66  akLock(sqlite3_f
39b0: 69 6c 65 20 2a 70 46 69 6c 65 29 7b 0a 20 20 72  ile *pFile){.  r
39c0: 65 74 75 72 6e 20 73 71 6c 69 74 65 33 4f 73 42  eturn sqlite3OsB
39d0: 72 65 61 6b 4c 6f 63 6b 28 28 28 43 72 61 73 68  reakLock(((Crash
39e0: 46 69 6c 65 20 2a 29 70 46 69 6c 65 29 2d 3e 70  File *)pFile)->p
39f0: 52 65 61 6c 46 69 6c 65 29 3b 0a 7d 0a 0a 2f 2a  RealFile);.}../*
3a00: 0a 2a 2a 20 54 68 65 20 78 53 65 63 74 6f 72 53  .** The xSectorS
3a10: 69 7a 65 28 29 20 61 6e 64 20 78 44 65 76 69 63  ize() and xDevic
3a20: 65 43 68 61 72 61 63 74 65 72 69 73 74 69 63 73  eCharacteristics
3a30: 28 29 20 66 75 6e 63 74 69 6f 6e 73 20 72 65 74  () functions ret
3a40: 75 72 6e 0a 2a 2a 20 74 68 65 20 67 6c 6f 62 61  urn.** the globa
3a50: 6c 20 76 61 6c 75 65 73 20 63 6f 6e 66 69 67 75  l values configu
3a60: 72 65 64 20 62 79 20 74 68 65 20 5b 73 71 6c 69  red by the [sqli
3a70: 74 65 5f 63 72 61 73 68 70 61 72 61 6d 73 5d 20  te_crashparams] 
3a80: 74 63 6c 0a 2a 20 20 69 6e 74 65 72 66 61 63 65  tcl.*  interface
3a90: 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20  ..*/.static int 
3aa0: 63 66 53 65 63 74 6f 72 53 69 7a 65 28 73 71 6c  cfSectorSize(sql
3ab0: 69 74 65 33 5f 66 69 6c 65 20 2a 70 46 69 6c 65  ite3_file *pFile
3ac0: 29 7b 0a 20 20 72 65 74 75 72 6e 20 67 2e 69 53  ){.  return g.iS
3ad0: 65 63 74 6f 72 53 69 7a 65 3b 0a 7d 0a 73 74 61  ectorSize;.}.sta
3ae0: 74 69 63 20 69 6e 74 20 63 66 44 65 76 69 63 65  tic int cfDevice
3af0: 43 68 61 72 61 63 74 65 72 69 73 74 69 63 73 28  Characteristics(
3b00: 73 71 6c 69 74 65 33 5f 66 69 6c 65 20 2a 70 46  sqlite3_file *pF
3b10: 69 6c 65 29 7b 0a 20 20 72 65 74 75 72 6e 20 67  ile){.  return g
3b20: 2e 69 44 65 76 69 63 65 43 68 61 72 61 63 74 65  .iDeviceCharacte
3b30: 72 69 73 74 69 63 73 3b 0a 7d 0a 0a 73 74 61 74  ristics;.}..stat
3b40: 69 63 20 63 6f 6e 73 74 20 73 71 6c 69 74 65 33  ic const sqlite3
3b50: 5f 69 6f 5f 6d 65 74 68 6f 64 73 20 43 72 61 73  _io_methods Cras
3b60: 68 46 69 6c 65 56 74 61 62 20 3d 20 7b 0a 20 20  hFileVtab = {.  
3b70: 31 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 20  1,              
3b80: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a                /*
3b90: 20 69 56 65 72 73 69 6f 6e 20 2a 2f 0a 20 20 63   iVersion */.  c
3ba0: 66 43 6c 6f 73 65 2c 20 20 20 20 20 20 20 20 20  fClose,         
3bb0: 20 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20               /* 
3bc0: 78 43 6c 6f 73 65 20 2a 2f 0a 20 20 63 66 52 65  xClose */.  cfRe
3bd0: 61 64 2c 20 20 20 20 20 20 20 20 20 20 20 20 20  ad,             
3be0: 20 20 20 20 20 20 20 20 20 20 2f 2a 20 78 52 65            /* xRe
3bf0: 61 64 20 2a 2f 0a 20 20 63 66 57 72 69 74 65 2c  ad */.  cfWrite,
3c00: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
3c10: 20 20 20 20 20 20 2f 2a 20 78 57 72 69 74 65 20        /* xWrite 
3c20: 2a 2f 0a 20 20 63 66 54 72 75 6e 63 61 74 65 2c  */.  cfTruncate,
3c30: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
3c40: 20 20 20 2f 2a 20 78 54 72 75 6e 63 61 74 65 20     /* xTruncate 
3c50: 2a 2f 0a 20 20 63 66 53 79 6e 63 2c 20 20 20 20  */.  cfSync,    
3c60: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
3c70: 20 20 20 2f 2a 20 78 53 79 6e 63 20 2a 2f 0a 20     /* xSync */. 
3c80: 20 63 66 46 69 6c 65 53 69 7a 65 2c 20 20 20 20   cfFileSize,    
3c90: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
3ca0: 2a 20 78 46 69 6c 65 53 69 7a 65 20 2a 2f 0a 20  * xFileSize */. 
3cb0: 20 63 66 4c 6f 63 6b 2c 20 20 20 20 20 20 20 20   cfLock,        
3cc0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 2f                 /
3cd0: 2a 20 78 4c 6f 63 6b 20 2a 2f 0a 20 20 63 66 55  * xLock */.  cfU
3ce0: 6e 6c 6f 63 6b 2c 20 20 20 20 20 20 20 20 20 20  nlock,          
3cf0: 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 78 55             /* xU
3d00: 6e 6c 6f 63 6b 20 2a 2f 0a 20 20 63 66 43 68 65  nlock */.  cfChe
3d10: 63 6b 52 65 73 65 72 76 65 64 4c 6f 63 6b 2c 20  ckReservedLock, 
3d20: 20 20 20 20 20 20 20 20 20 2f 2a 20 78 43 68 65           /* xChe
3d30: 63 6b 52 65 73 65 72 76 65 64 4c 6f 63 6b 20 2a  ckReservedLock *
3d40: 2f 0a 20 20 63 66 42 72 65 61 6b 4c 6f 63 6b 2c  /.  cfBreakLock,
3d50: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
3d60: 20 20 2f 2a 20 78 42 72 65 61 6b 4c 6f 63 6b 20    /* xBreakLock 
3d70: 2a 2f 0a 20 20 63 66 4c 6f 63 6b 53 74 61 74 65  */.  cfLockState
3d80: 2c 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20  ,               
3d90: 20 20 20 2f 2a 20 78 4c 6f 63 6b 53 74 61 74 65     /* xLockState
3da0: 20 2a 2f 0a 20 20 63 66 53 65 63 74 6f 72 53 69   */.  cfSectorSi
3db0: 7a 65 2c 20 20 20 20 20 20 20 20 20 20 20 20 20  ze,             
3dc0: 20 20 20 20 2f 2a 20 78 53 65 63 74 6f 72 53 69      /* xSectorSi
3dd0: 7a 65 20 2a 2f 0a 20 20 63 66 44 65 76 69 63 65  ze */.  cfDevice
3de0: 43 68 61 72 61 63 74 65 72 69 73 74 69 63 73 20  Characteristics 
3df0: 20 20 20 20 20 20 2f 2a 20 78 44 65 76 69 63 65        /* xDevice
3e00: 43 68 61 72 61 63 74 65 72 69 73 74 69 63 73 20  Characteristics 
3e10: 2a 2f 0a 7d 3b 0a 0a 2f 2a 0a 2a 2a 20 41 70 70  */.};../*.** App
3e20: 6c 69 63 61 74 69 6f 6e 20 64 61 74 61 20 66 6f  lication data fo
3e30: 72 20 74 68 65 20 63 72 61 73 68 20 56 46 53 0a  r the crash VFS.
3e40: 2a 2f 0a 73 74 72 75 63 74 20 63 72 61 73 68 41  */.struct crashA
3e50: 70 70 44 61 74 61 20 7b 0a 20 20 73 71 6c 69 74  ppData {.  sqlit
3e60: 65 33 5f 76 66 73 20 2a 70 4f 72 69 67 3b 20 20  e3_vfs *pOrig;  
3e70: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
3e80: 20 2f 2a 20 57 72 61 70 70 65 64 20 76 66 73 20   /* Wrapped vfs 
3e90: 73 74 72 75 63 74 75 72 65 20 2a 2f 0a 7d 3b 0a  structure */.};.
3ea0: 0a 2f 2a 0a 2a 2a 20 4f 70 65 6e 20 61 20 63 72  ./*.** Open a cr
3eb0: 61 73 68 2d 66 69 6c 65 20 66 69 6c 65 20 68 61  ash-file file ha
3ec0: 6e 64 6c 65 2e 0a 2a 2a 0a 2a 2a 20 54 68 65 20  ndle..**.** The 
3ed0: 63 61 6c 6c 65 72 20 77 69 6c 6c 20 68 61 76 65  caller will have
3ee0: 20 61 6c 6c 6f 63 61 74 65 64 20 70 56 66 73 2d   allocated pVfs-
3ef0: 3e 73 7a 4f 73 46 69 6c 65 20 62 79 74 65 73 20  >szOsFile bytes 
3f00: 6f 66 20 73 70 61 63 65 0a 2a 2a 20 61 74 20 70  of space.** at p
3f10: 46 69 6c 65 2e 20 54 68 69 73 20 66 69 6c 65 20  File. This file 
3f20: 75 73 65 73 20 74 68 69 73 20 73 70 61 63 65 20  uses this space 
3f30: 66 6f 72 20 74 68 65 20 43 72 61 73 68 46 69 6c  for the CrashFil
3f40: 65 20 73 74 72 75 63 74 75 72 65 0a 2a 2a 20 61  e structure.** a
3f50: 6e 64 20 61 6c 6c 6f 63 61 74 65 73 20 73 70 61  nd allocates spa
3f60: 63 65 20 66 6f 72 20 74 68 65 20 22 72 65 61 6c  ce for the "real
3f70: 22 20 66 69 6c 65 20 73 74 72 75 63 74 75 72 65  " file structure
3f80: 20 75 73 69 6e 67 20 0a 2a 2a 20 73 71 6c 69 74   using .** sqlit
3f90: 65 33 5f 6d 61 6c 6c 6f 63 28 29 2e 20 54 68 65  e3_malloc(). The
3fa0: 20 61 73 73 75 6d 70 74 69 6f 6e 20 68 65 72 65   assumption here
3fb0: 20 69 73 20 28 70 56 66 73 2d 3e 73 7a 4f 73 46   is (pVfs->szOsF
3fc0: 69 6c 65 29 20 69 73 0a 2a 2a 20 65 71 75 61 6c  ile) is.** equal
3fd0: 20 6f 72 20 67 72 65 61 74 65 72 20 74 68 61 6e   or greater than
3fe0: 20 73 69 7a 65 6f 66 28 43 72 61 73 68 46 69 6c   sizeof(CrashFil
3ff0: 65 29 2e 0a 2a 2f 0a 73 74 61 74 69 63 20 69 6e  e)..*/.static in
4000: 74 20 63 66 4f 70 65 6e 28 0a 20 20 73 71 6c 69  t cfOpen(.  sqli
4010: 74 65 33 5f 76 66 73 20 2a 70 43 66 56 66 73 2c  te3_vfs *pCfVfs,
4020: 0a 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a  .  const char *z
4030: 4e 61 6d 65 2c 0a 20 20 73 71 6c 69 74 65 33 5f  Name,.  sqlite3_
4040: 66 69 6c 65 20 2a 70 46 69 6c 65 2c 0a 20 20 69  file *pFile,.  i
4050: 6e 74 20 66 6c 61 67 73 2c 0a 20 20 69 6e 74 20  nt flags,.  int 
4060: 2a 70 4f 75 74 46 6c 61 67 73 0a 29 7b 0a 20 20  *pOutFlags.){.  
4070: 73 71 6c 69 74 65 33 5f 76 66 73 20 2a 70 56 66  sqlite3_vfs *pVf
4080: 73 20 3d 20 28 73 71 6c 69 74 65 33 5f 76 66 73  s = (sqlite3_vfs
4090: 20 2a 29 70 43 66 56 66 73 2d 3e 70 41 70 70 44   *)pCfVfs->pAppD
40a0: 61 74 61 3b 0a 20 20 69 6e 74 20 72 63 3b 0a 20  ata;.  int rc;. 
40b0: 20 43 72 61 73 68 46 69 6c 65 20 2a 70 57 72 61   CrashFile *pWra
40c0: 70 70 65 72 20 3d 20 28 43 72 61 73 68 46 69 6c  pper = (CrashFil
40d0: 65 20 2a 29 70 46 69 6c 65 3b 0a 20 20 73 71 6c  e *)pFile;.  sql
40e0: 69 74 65 33 5f 66 69 6c 65 20 2a 70 52 65 61 6c  ite3_file *pReal
40f0: 20 3d 20 28 73 71 6c 69 74 65 33 5f 66 69 6c 65   = (sqlite3_file
4100: 2a 29 26 70 57 72 61 70 70 65 72 5b 31 5d 3b 0a  *)&pWrapper[1];.
4110: 0a 20 20 6d 65 6d 73 65 74 28 70 57 72 61 70 70  .  memset(pWrapp
4120: 65 72 2c 20 30 2c 20 73 69 7a 65 6f 66 28 43 72  er, 0, sizeof(Cr
4130: 61 73 68 46 69 6c 65 29 29 3b 0a 20 20 72 63 20  ashFile));.  rc 
4140: 3d 20 73 71 6c 69 74 65 33 4f 73 4f 70 65 6e 28  = sqlite3OsOpen(
4150: 70 56 66 73 2c 20 7a 4e 61 6d 65 2c 20 70 52 65  pVfs, zName, pRe
4160: 61 6c 2c 20 66 6c 61 67 73 2c 20 70 4f 75 74 46  al, flags, pOutF
4170: 6c 61 67 73 29 3b 0a 0a 20 20 69 66 28 20 72 63  lags);..  if( rc
4180: 3d 3d 53 51 4c 49 54 45 5f 4f 4b 20 29 7b 0a 20  ==SQLITE_OK ){. 
4190: 20 20 20 69 36 34 20 69 53 69 7a 65 3b 0a 20 20     i64 iSize;.  
41a0: 20 20 70 57 72 61 70 70 65 72 2d 3e 70 4d 65 74    pWrapper->pMet
41b0: 68 6f 64 20 3d 20 26 43 72 61 73 68 46 69 6c 65  hod = &CrashFile
41c0: 56 74 61 62 3b 0a 20 20 20 20 70 57 72 61 70 70  Vtab;.    pWrapp
41d0: 65 72 2d 3e 7a 4e 61 6d 65 20 3d 20 28 63 68 61  er->zName = (cha
41e0: 72 20 2a 29 7a 4e 61 6d 65 3b 0a 20 20 20 20 70  r *)zName;.    p
41f0: 57 72 61 70 70 65 72 2d 3e 70 52 65 61 6c 46 69  Wrapper->pRealFi
4200: 6c 65 20 3d 20 70 52 65 61 6c 3b 0a 20 20 20 20  le = pReal;.    
4210: 72 63 20 3d 20 73 71 6c 69 74 65 33 4f 73 46 69  rc = sqlite3OsFi
4220: 6c 65 53 69 7a 65 28 70 52 65 61 6c 2c 20 26 69  leSize(pReal, &i
4230: 53 69 7a 65 29 3b 0a 20 20 20 20 70 57 72 61 70  Size);.    pWrap
4240: 70 65 72 2d 3e 69 53 69 7a 65 20 3d 20 28 69 6e  per->iSize = (in
4250: 74 29 69 53 69 7a 65 3b 0a 20 20 7d 0a 20 20 69  t)iSize;.  }.  i
4260: 66 28 20 72 63 3d 3d 53 51 4c 49 54 45 5f 4f 4b  f( rc==SQLITE_OK
4270: 20 29 7b 0a 20 20 20 20 70 57 72 61 70 70 65 72   ){.    pWrapper
4280: 2d 3e 6e 44 61 74 61 20 3d 20 28 34 30 39 36 20  ->nData = (4096 
4290: 2b 20 70 57 72 61 70 70 65 72 2d 3e 69 53 69 7a  + pWrapper->iSiz
42a0: 65 29 3b 0a 20 20 20 20 70 57 72 61 70 70 65 72  e);.    pWrapper
42b0: 2d 3e 7a 44 61 74 61 20 3d 20 73 71 6c 69 74 65  ->zData = sqlite
42c0: 33 5f 6d 61 6c 6c 6f 63 28 70 57 72 61 70 70 65  3_malloc(pWrappe
42d0: 72 2d 3e 6e 44 61 74 61 29 3b 0a 20 20 20 20 69  r->nData);.    i
42e0: 66 28 20 70 57 72 61 70 70 65 72 2d 3e 7a 44 61  f( pWrapper->zDa
42f0: 74 61 20 29 7b 0a 20 20 20 20 20 20 6d 65 6d 73  ta ){.      mems
4300: 65 74 28 70 57 72 61 70 70 65 72 2d 3e 7a 44 61  et(pWrapper->zDa
4310: 74 61 2c 20 30 2c 20 70 57 72 61 70 70 65 72 2d  ta, 0, pWrapper-
4320: 3e 6e 44 61 74 61 29 3b 0a 20 20 20 20 20 20 72  >nData);.      r
4330: 63 20 3d 20 73 71 6c 69 74 65 33 4f 73 52 65 61  c = sqlite3OsRea
4340: 64 28 70 52 65 61 6c 2c 20 70 57 72 61 70 70 65  d(pReal, pWrappe
4350: 72 2d 3e 7a 44 61 74 61 2c 20 70 57 72 61 70 70  r->zData, pWrapp
4360: 65 72 2d 3e 69 53 69 7a 65 2c 20 30 29 3b 20 0a  er->iSize, 0); .
4370: 20 20 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20      }else{.     
4380: 20 72 63 20 3d 20 53 51 4c 49 54 45 5f 4e 4f 4d   rc = SQLITE_NOM
4390: 45 4d 3b 0a 20 20 20 20 7d 0a 20 20 7d 0a 20 20  EM;.    }.  }.  
43a0: 69 66 28 20 72 63 21 3d 53 51 4c 49 54 45 5f 4f  if( rc!=SQLITE_O
43b0: 4b 20 26 26 20 70 57 72 61 70 70 65 72 2d 3e 70  K && pWrapper->p
43c0: 4d 65 74 68 6f 64 20 29 7b 0a 20 20 20 20 73 71  Method ){.    sq
43d0: 6c 69 74 65 33 4f 73 43 6c 6f 73 65 28 70 46 69  lite3OsClose(pFi
43e0: 6c 65 29 3b 0a 20 20 7d 0a 20 20 72 65 74 75 72  le);.  }.  retur
43f0: 6e 20 72 63 3b 0a 7d 0a 0a 73 74 61 74 69 63 20  n rc;.}..static 
4400: 69 6e 74 20 63 66 44 65 6c 65 74 65 28 73 71 6c  int cfDelete(sql
4410: 69 74 65 33 5f 76 66 73 20 2a 70 43 66 56 66 73  ite3_vfs *pCfVfs
4420: 2c 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 50  , const char *zP
4430: 61 74 68 2c 20 69 6e 74 20 64 69 72 53 79 6e 63  ath, int dirSync
4440: 29 7b 0a 20 20 73 71 6c 69 74 65 33 5f 76 66 73  ){.  sqlite3_vfs
4450: 20 2a 70 56 66 73 20 3d 20 28 73 71 6c 69 74 65   *pVfs = (sqlite
4460: 33 5f 76 66 73 20 2a 29 70 43 66 56 66 73 2d 3e  3_vfs *)pCfVfs->
4470: 70 41 70 70 44 61 74 61 3b 0a 20 20 72 65 74 75  pAppData;.  retu
4480: 72 6e 20 70 56 66 73 2d 3e 78 44 65 6c 65 74 65  rn pVfs->xDelete
4490: 28 70 56 66 73 2c 20 7a 50 61 74 68 2c 20 64 69  (pVfs, zPath, di
44a0: 72 53 79 6e 63 29 3b 0a 7d 0a 73 74 61 74 69 63  rSync);.}.static
44b0: 20 69 6e 74 20 63 66 41 63 63 65 73 73 28 73 71   int cfAccess(sq
44c0: 6c 69 74 65 33 5f 76 66 73 20 2a 70 43 66 56 66  lite3_vfs *pCfVf
44d0: 73 2c 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a  s, const char *z
44e0: 50 61 74 68 2c 20 69 6e 74 20 66 6c 61 67 73 29  Path, int flags)
44f0: 7b 0a 20 20 73 71 6c 69 74 65 33 5f 76 66 73 20  {.  sqlite3_vfs 
4500: 2a 70 56 66 73 20 3d 20 28 73 71 6c 69 74 65 33  *pVfs = (sqlite3
4510: 5f 76 66 73 20 2a 29 70 43 66 56 66 73 2d 3e 70  _vfs *)pCfVfs->p
4520: 41 70 70 44 61 74 61 3b 0a 20 20 72 65 74 75 72  AppData;.  retur
4530: 6e 20 70 56 66 73 2d 3e 78 41 63 63 65 73 73 28  n pVfs->xAccess(
4540: 70 56 66 73 2c 20 7a 50 61 74 68 2c 20 66 6c 61  pVfs, zPath, fla
4550: 67 73 29 3b 0a 7d 0a 73 74 61 74 69 63 20 69 6e  gs);.}.static in
4560: 74 20 63 66 47 65 74 54 65 6d 70 4e 61 6d 65 28  t cfGetTempName(
4570: 73 71 6c 69 74 65 33 5f 76 66 73 20 2a 70 43 66  sqlite3_vfs *pCf
4580: 56 66 73 2c 20 63 68 61 72 20 2a 7a 42 75 66 4f  Vfs, char *zBufO
4590: 75 74 29 7b 0a 20 20 73 71 6c 69 74 65 33 5f 76  ut){.  sqlite3_v
45a0: 66 73 20 2a 70 56 66 73 20 3d 20 28 73 71 6c 69  fs *pVfs = (sqli
45b0: 74 65 33 5f 76 66 73 20 2a 29 70 43 66 56 66 73  te3_vfs *)pCfVfs
45c0: 2d 3e 70 41 70 70 44 61 74 61 3b 0a 20 20 72 65  ->pAppData;.  re
45d0: 74 75 72 6e 20 70 56 66 73 2d 3e 78 47 65 74 54  turn pVfs->xGetT
45e0: 65 6d 70 4e 61 6d 65 28 70 56 66 73 2c 20 7a 42  empName(pVfs, zB
45f0: 75 66 4f 75 74 29 3b 0a 7d 0a 73 74 61 74 69 63  ufOut);.}.static
4600: 20 69 6e 74 20 63 66 46 75 6c 6c 50 61 74 68 6e   int cfFullPathn
4610: 61 6d 65 28 73 71 6c 69 74 65 33 5f 76 66 73 20  ame(sqlite3_vfs 
4620: 2a 70 43 66 56 66 73 2c 20 63 6f 6e 73 74 20 63  *pCfVfs, const c
4630: 68 61 72 20 2a 7a 50 61 74 68 2c 20 63 68 61 72  har *zPath, char
4640: 20 2a 7a 50 61 74 68 4f 75 74 29 7b 0a 20 20 73   *zPathOut){.  s
4650: 71 6c 69 74 65 33 5f 76 66 73 20 2a 70 56 66 73  qlite3_vfs *pVfs
4660: 20 3d 20 28 73 71 6c 69 74 65 33 5f 76 66 73 20   = (sqlite3_vfs 
4670: 2a 29 70 43 66 56 66 73 2d 3e 70 41 70 70 44 61  *)pCfVfs->pAppDa
4680: 74 61 3b 0a 20 20 72 65 74 75 72 6e 20 70 56 66  ta;.  return pVf
4690: 73 2d 3e 78 46 75 6c 6c 50 61 74 68 6e 61 6d 65  s->xFullPathname
46a0: 28 70 56 66 73 2c 20 7a 50 61 74 68 2c 20 7a 50  (pVfs, zPath, zP
46b0: 61 74 68 4f 75 74 29 3b 0a 7d 0a 73 74 61 74 69  athOut);.}.stati
46c0: 63 20 76 6f 69 64 20 2a 63 66 44 6c 4f 70 65 6e  c void *cfDlOpen
46d0: 28 73 71 6c 69 74 65 33 5f 76 66 73 20 2a 70 43  (sqlite3_vfs *pC
46e0: 66 56 66 73 2c 20 63 6f 6e 73 74 20 63 68 61 72  fVfs, const char
46f0: 20 2a 7a 50 61 74 68 29 7b 0a 20 20 73 71 6c 69   *zPath){.  sqli
4700: 74 65 33 5f 76 66 73 20 2a 70 56 66 73 20 3d 20  te3_vfs *pVfs = 
4710: 28 73 71 6c 69 74 65 33 5f 76 66 73 20 2a 29 70  (sqlite3_vfs *)p
4720: 43 66 56 66 73 2d 3e 70 41 70 70 44 61 74 61 3b  CfVfs->pAppData;
4730: 0a 20 20 72 65 74 75 72 6e 20 70 56 66 73 2d 3e  .  return pVfs->
4740: 78 44 6c 4f 70 65 6e 28 70 56 66 73 2c 20 7a 50  xDlOpen(pVfs, zP
4750: 61 74 68 29 3b 0a 7d 0a 73 74 61 74 69 63 20 76  ath);.}.static v
4760: 6f 69 64 20 63 66 44 6c 45 72 72 6f 72 28 73 71  oid cfDlError(sq
4770: 6c 69 74 65 33 5f 76 66 73 20 2a 70 43 66 56 66  lite3_vfs *pCfVf
4780: 73 2c 20 69 6e 74 20 6e 42 79 74 65 2c 20 63 68  s, int nByte, ch
4790: 61 72 20 2a 7a 45 72 72 4d 73 67 29 7b 0a 20 20  ar *zErrMsg){.  
47a0: 73 71 6c 69 74 65 33 5f 76 66 73 20 2a 70 56 66  sqlite3_vfs *pVf
47b0: 73 20 3d 20 28 73 71 6c 69 74 65 33 5f 76 66 73  s = (sqlite3_vfs
47c0: 20 2a 29 70 43 66 56 66 73 2d 3e 70 41 70 70 44   *)pCfVfs->pAppD
47d0: 61 74 61 3b 0a 20 20 70 56 66 73 2d 3e 78 44 6c  ata;.  pVfs->xDl
47e0: 45 72 72 6f 72 28 70 56 66 73 2c 20 6e 42 79 74  Error(pVfs, nByt
47f0: 65 2c 20 7a 45 72 72 4d 73 67 29 3b 0a 7d 0a 73  e, zErrMsg);.}.s
4800: 74 61 74 69 63 20 76 6f 69 64 20 2a 63 66 44 6c  tatic void *cfDl
4810: 53 79 6d 28 73 71 6c 69 74 65 33 5f 76 66 73 20  Sym(sqlite3_vfs 
4820: 2a 70 43 66 56 66 73 2c 20 76 6f 69 64 20 2a 70  *pCfVfs, void *p
4830: 48 61 6e 64 6c 65 2c 20 63 6f 6e 73 74 20 63 68  Handle, const ch
4840: 61 72 20 2a 7a 53 79 6d 62 6f 6c 29 7b 0a 20 20  ar *zSymbol){.  
4850: 73 71 6c 69 74 65 33 5f 76 66 73 20 2a 70 56 66  sqlite3_vfs *pVf
4860: 73 20 3d 20 28 73 71 6c 69 74 65 33 5f 76 66 73  s = (sqlite3_vfs
4870: 20 2a 29 70 43 66 56 66 73 2d 3e 70 41 70 70 44   *)pCfVfs->pAppD
4880: 61 74 61 3b 0a 20 20 72 65 74 75 72 6e 20 70 56  ata;.  return pV
4890: 66 73 2d 3e 78 44 6c 53 79 6d 28 70 56 66 73 2c  fs->xDlSym(pVfs,
48a0: 20 70 48 61 6e 64 6c 65 2c 20 7a 53 79 6d 62 6f   pHandle, zSymbo
48b0: 6c 29 3b 0a 7d 0a 73 74 61 74 69 63 20 76 6f 69  l);.}.static voi
48c0: 64 20 63 66 44 6c 43 6c 6f 73 65 28 73 71 6c 69  d cfDlClose(sqli
48d0: 74 65 33 5f 76 66 73 20 2a 70 43 66 56 66 73 2c  te3_vfs *pCfVfs,
48e0: 20 76 6f 69 64 20 2a 70 48 61 6e 64 6c 65 29 7b   void *pHandle){
48f0: 0a 20 20 73 71 6c 69 74 65 33 5f 76 66 73 20 2a  .  sqlite3_vfs *
4900: 70 56 66 73 20 3d 20 28 73 71 6c 69 74 65 33 5f  pVfs = (sqlite3_
4910: 76 66 73 20 2a 29 70 43 66 56 66 73 2d 3e 70 41  vfs *)pCfVfs->pA
4920: 70 70 44 61 74 61 3b 0a 20 20 70 56 66 73 2d 3e  ppData;.  pVfs->
4930: 78 44 6c 43 6c 6f 73 65 28 70 56 66 73 2c 20 70  xDlClose(pVfs, p
4940: 48 61 6e 64 6c 65 29 3b 0a 7d 0a 73 74 61 74 69  Handle);.}.stati
4950: 63 20 69 6e 74 20 63 66 52 61 6e 64 6f 6d 6e 65  c int cfRandomne
4960: 73 73 28 73 71 6c 69 74 65 33 5f 76 66 73 20 2a  ss(sqlite3_vfs *
4970: 70 43 66 56 66 73 2c 20 69 6e 74 20 6e 42 79 74  pCfVfs, int nByt
4980: 65 2c 20 63 68 61 72 20 2a 7a 42 75 66 4f 75 74  e, char *zBufOut
4990: 29 7b 0a 20 20 73 71 6c 69 74 65 33 5f 76 66 73  ){.  sqlite3_vfs
49a0: 20 2a 70 56 66 73 20 3d 20 28 73 71 6c 69 74 65   *pVfs = (sqlite
49b0: 33 5f 76 66 73 20 2a 29 70 43 66 56 66 73 2d 3e  3_vfs *)pCfVfs->
49c0: 70 41 70 70 44 61 74 61 3b 0a 20 20 72 65 74 75  pAppData;.  retu
49d0: 72 6e 20 70 56 66 73 2d 3e 78 52 61 6e 64 6f 6d  rn pVfs->xRandom
49e0: 6e 65 73 73 28 70 56 66 73 2c 20 6e 42 79 74 65  ness(pVfs, nByte
49f0: 2c 20 7a 42 75 66 4f 75 74 29 3b 0a 7d 0a 73 74  , zBufOut);.}.st
4a00: 61 74 69 63 20 69 6e 74 20 63 66 53 6c 65 65 70  atic int cfSleep
4a10: 28 73 71 6c 69 74 65 33 5f 76 66 73 20 2a 70 43  (sqlite3_vfs *pC
4a20: 66 56 66 73 2c 20 69 6e 74 20 6e 4d 69 63 72 6f  fVfs, int nMicro
4a30: 29 7b 0a 20 20 73 71 6c 69 74 65 33 5f 76 66 73  ){.  sqlite3_vfs
4a40: 20 2a 70 56 66 73 20 3d 20 28 73 71 6c 69 74 65   *pVfs = (sqlite
4a50: 33 5f 76 66 73 20 2a 29 70 43 66 56 66 73 2d 3e  3_vfs *)pCfVfs->
4a60: 70 41 70 70 44 61 74 61 3b 0a 20 20 72 65 74 75  pAppData;.  retu
4a70: 72 6e 20 70 56 66 73 2d 3e 78 53 6c 65 65 70 28  rn pVfs->xSleep(
4a80: 70 56 66 73 2c 20 6e 4d 69 63 72 6f 29 3b 0a 7d  pVfs, nMicro);.}
4a90: 0a 73 74 61 74 69 63 20 69 6e 74 20 63 66 43 75  .static int cfCu
4aa0: 72 72 65 6e 74 54 69 6d 65 28 73 71 6c 69 74 65  rrentTime(sqlite
4ab0: 33 5f 76 66 73 20 2a 70 43 66 56 66 73 2c 20 64  3_vfs *pCfVfs, d
4ac0: 6f 75 62 6c 65 20 2a 70 54 69 6d 65 4f 75 74 29  ouble *pTimeOut)
4ad0: 7b 0a 20 20 73 71 6c 69 74 65 33 5f 76 66 73 20  {.  sqlite3_vfs 
4ae0: 2a 70 56 66 73 20 3d 20 28 73 71 6c 69 74 65 33  *pVfs = (sqlite3
4af0: 5f 76 66 73 20 2a 29 70 43 66 56 66 73 2d 3e 70  _vfs *)pCfVfs->p
4b00: 41 70 70 44 61 74 61 3b 0a 20 20 72 65 74 75 72  AppData;.  retur
4b10: 6e 20 70 56 66 73 2d 3e 78 43 75 72 72 65 6e 74  n pVfs->xCurrent
4b20: 54 69 6d 65 28 70 56 66 73 2c 20 70 54 69 6d 65  Time(pVfs, pTime
4b30: 4f 75 74 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 20  Out);.}..static 
4b40: 69 6e 74 20 70 72 6f 63 65 73 73 44 65 76 53 79  int processDevSy
4b50: 6d 41 72 67 73 28 0a 20 20 54 63 6c 5f 49 6e 74  mArgs(.  Tcl_Int
4b60: 65 72 70 20 2a 69 6e 74 65 72 70 2c 0a 20 20 69  erp *interp,.  i
4b70: 6e 74 20 6f 62 6a 63 2c 0a 20 20 54 63 6c 5f 4f  nt objc,.  Tcl_O
4b80: 62 6a 20 2a 43 4f 4e 53 54 20 6f 62 6a 76 5b 5d  bj *CONST objv[]
4b90: 2c 0a 20 20 69 6e 74 20 2a 70 69 44 65 76 69 63  ,.  int *piDevic
4ba0: 65 43 68 61 72 2c 0a 20 20 69 6e 74 20 2a 70 69  eChar,.  int *pi
4bb0: 53 65 63 74 6f 72 53 69 7a 65 0a 29 7b 0a 20 20  SectorSize.){.  
4bc0: 73 74 72 75 63 74 20 44 65 76 69 63 65 46 6c 61  struct DeviceFla
4bd0: 67 20 7b 0a 20 20 20 20 63 68 61 72 20 2a 7a 4e  g {.    char *zN
4be0: 61 6d 65 3b 0a 20 20 20 20 69 6e 74 20 69 56 61  ame;.    int iVa
4bf0: 6c 75 65 3b 0a 20 20 7d 20 61 46 6c 61 67 5b 5d  lue;.  } aFlag[]
4c00: 20 3d 20 7b 0a 20 20 20 20 7b 20 22 61 74 6f 6d   = {.    { "atom
4c10: 69 63 22 2c 20 20 20 20 20 20 53 51 4c 49 54 45  ic",      SQLITE
4c20: 5f 49 4f 43 41 50 5f 41 54 4f 4d 49 43 20 20 20  _IOCAP_ATOMIC   
4c30: 20 20 20 7d 2c 0a 20 20 20 20 7b 20 22 61 74 6f     },.    { "ato
4c40: 6d 69 63 35 31 32 22 2c 20 20 20 53 51 4c 49 54  mic512",   SQLIT
4c50: 45 5f 49 4f 43 41 50 5f 41 54 4f 4d 49 43 35 31  E_IOCAP_ATOMIC51
4c60: 32 20 20 20 7d 2c 0a 20 20 20 20 7b 20 22 61 74  2   },.    { "at
4c70: 6f 6d 69 63 31 6b 22 2c 20 20 20 20 53 51 4c 49  omic1k",    SQLI
4c80: 54 45 5f 49 4f 43 41 50 5f 41 54 4f 4d 49 43 31  TE_IOCAP_ATOMIC1
4c90: 4b 20 20 20 20 7d 2c 0a 20 20 20 20 7b 20 22 61  K    },.    { "a
4ca0: 74 6f 6d 69 63 32 6b 22 2c 20 20 20 20 53 51 4c  tomic2k",    SQL
4cb0: 49 54 45 5f 49 4f 43 41 50 5f 41 54 4f 4d 49 43  ITE_IOCAP_ATOMIC
4cc0: 32 4b 20 20 20 20 7d 2c 0a 20 20 20 20 7b 20 22  2K    },.    { "
4cd0: 61 74 6f 6d 69 63 34 6b 22 2c 20 20 20 20 53 51  atomic4k",    SQ
4ce0: 4c 49 54 45 5f 49 4f 43 41 50 5f 41 54 4f 4d 49  LITE_IOCAP_ATOMI
4cf0: 43 34 4b 20 20 20 20 7d 2c 0a 20 20 20 20 7b 20  C4K    },.    { 
4d00: 22 61 74 6f 6d 69 63 38 6b 22 2c 20 20 20 20 53  "atomic8k",    S
4d10: 51 4c 49 54 45 5f 49 4f 43 41 50 5f 41 54 4f 4d  QLITE_IOCAP_ATOM
4d20: 49 43 38 4b 20 20 20 20 7d 2c 0a 20 20 20 20 7b  IC8K    },.    {
4d30: 20 22 61 74 6f 6d 69 63 31 36 6b 22 2c 20 20 20   "atomic16k",   
4d40: 53 51 4c 49 54 45 5f 49 4f 43 41 50 5f 41 54 4f  SQLITE_IOCAP_ATO
4d50: 4d 49 43 31 36 4b 20 20 20 7d 2c 0a 20 20 20 20  MIC16K   },.    
4d60: 7b 20 22 61 74 6f 6d 69 63 33 32 6b 22 2c 20 20  { "atomic32k",  
4d70: 20 53 51 4c 49 54 45 5f 49 4f 43 41 50 5f 41 54   SQLITE_IOCAP_AT
4d80: 4f 4d 49 43 33 32 4b 20 20 20 7d 2c 0a 20 20 20  OMIC32K   },.   
4d90: 20 7b 20 22 61 74 6f 6d 69 63 36 34 6b 22 2c 20   { "atomic64k", 
4da0: 20 20 53 51 4c 49 54 45 5f 49 4f 43 41 50 5f 41    SQLITE_IOCAP_A
4db0: 54 4f 4d 49 43 36 34 4b 20 20 20 7d 2c 0a 20 20  TOMIC64K   },.  
4dc0: 20 20 7b 20 22 73 65 71 75 65 6e 74 69 61 6c 22    { "sequential"
4dd0: 2c 20 20 53 51 4c 49 54 45 5f 49 4f 43 41 50 5f  ,  SQLITE_IOCAP_
4de0: 53 45 51 55 45 4e 54 49 41 4c 20 20 7d 2c 0a 20  SEQUENTIAL  },. 
4df0: 20 20 20 7b 20 22 73 61 66 65 5f 61 70 70 65 6e     { "safe_appen
4e00: 64 22 2c 20 53 51 4c 49 54 45 5f 49 4f 43 41 50  d", SQLITE_IOCAP
4e10: 5f 53 41 46 45 5f 41 50 50 45 4e 44 20 7d 2c 0a  _SAFE_APPEND },.
4e20: 20 20 20 20 7b 20 30 2c 20 30 20 7d 0a 20 20 7d      { 0, 0 }.  }
4e30: 3b 0a 0a 20 20 69 6e 74 20 69 3b 0a 20 20 69 6e  ;..  int i;.  in
4e40: 74 20 69 44 63 20 3d 20 30 3b 0a 20 20 69 6e 74  t iDc = 0;.  int
4e50: 20 69 53 65 63 74 6f 72 53 69 7a 65 20 3d 20 30   iSectorSize = 0
4e60: 3b 0a 20 20 69 6e 74 20 73 65 74 53 65 63 74 6f  ;.  int setSecto
4e70: 72 73 69 7a 65 20 3d 20 30 3b 0a 20 20 69 6e 74  rsize = 0;.  int
4e80: 20 73 65 74 44 65 76 69 63 65 43 68 61 72 20 3d   setDeviceChar =
4e90: 20 30 3b 0a 0a 20 20 66 6f 72 28 69 3d 30 3b 20   0;..  for(i=0; 
4ea0: 69 3c 6f 62 6a 63 3b 20 69 2b 3d 32 29 7b 0a 20  i<objc; i+=2){. 
4eb0: 20 20 20 69 6e 74 20 6e 4f 70 74 3b 0a 20 20 20     int nOpt;.   
4ec0: 20 63 68 61 72 20 2a 7a 4f 70 74 20 3d 20 54 63   char *zOpt = Tc
4ed0: 6c 5f 47 65 74 53 74 72 69 6e 67 46 72 6f 6d 4f  l_GetStringFromO
4ee0: 62 6a 28 6f 62 6a 76 5b 69 5d 2c 20 26 6e 4f 70  bj(objv[i], &nOp
4ef0: 74 29 3b 0a 0a 20 20 20 20 69 66 28 20 28 6e 4f  t);..    if( (nO
4f00: 70 74 3e 31 31 20 7c 7c 20 6e 4f 70 74 3c 32 20  pt>11 || nOpt<2 
4f10: 7c 7c 20 73 74 72 6e 63 6d 70 28 22 2d 73 65 63  || strncmp("-sec
4f20: 74 6f 72 73 69 7a 65 22 2c 20 7a 4f 70 74 2c 20  torsize", zOpt, 
4f30: 6e 4f 70 74 29 29 20 0a 20 20 20 20 20 26 26 20  nOpt)) .     && 
4f40: 28 6e 4f 70 74 3e 31 36 20 7c 7c 20 6e 4f 70 74  (nOpt>16 || nOpt
4f50: 3c 32 20 7c 7c 20 73 74 72 6e 63 6d 70 28 22 2d  <2 || strncmp("-
4f60: 63 68 61 72 61 63 74 65 72 69 73 74 69 63 73 22  characteristics"
4f70: 2c 20 7a 4f 70 74 2c 20 6e 4f 70 74 29 29 0a 20  , zOpt, nOpt)). 
4f80: 20 20 20 29 7b 0a 20 20 20 20 20 20 54 63 6c 5f     ){.      Tcl_
4f90: 41 70 70 65 6e 64 52 65 73 75 6c 74 28 69 6e 74  AppendResult(int
4fa0: 65 72 70 2c 20 0a 20 20 20 20 20 20 20 20 22 42  erp, .        "B
4fb0: 61 64 20 6f 70 74 69 6f 6e 3a 20 5c 22 22 2c 20  ad option: \"", 
4fc0: 7a 4f 70 74 2c 20 0a 20 20 20 20 20 20 20 20 22  zOpt, .        "
4fd0: 5c 22 20 2d 20 6d 75 73 74 20 62 65 20 5c 22 2d  \" - must be \"-
4fe0: 63 68 61 72 61 63 74 65 72 69 73 74 69 63 73 5c  characteristics\
4ff0: 22 20 6f 72 20 5c 22 2d 73 65 63 74 6f 72 73 69  " or \"-sectorsi
5000: 7a 65 5c 22 22 2c 20 30 0a 20 20 20 20 20 20 29  ze\"", 0.      )
5010: 3b 0a 20 20 20 20 20 20 72 65 74 75 72 6e 20 54  ;.      return T
5020: 43 4c 5f 45 52 52 4f 52 3b 0a 20 20 20 20 7d 0a  CL_ERROR;.    }.
5030: 20 20 20 20 69 66 28 20 69 3d 3d 6f 62 6a 63 2d      if( i==objc-
5040: 31 20 29 7b 0a 20 20 20 20 20 20 54 63 6c 5f 41  1 ){.      Tcl_A
5050: 70 70 65 6e 64 52 65 73 75 6c 74 28 69 6e 74 65  ppendResult(inte
5060: 72 70 2c 20 22 4f 70 74 69 6f 6e 20 72 65 71 75  rp, "Option requ
5070: 69 72 65 73 20 61 6e 20 61 72 67 75 6d 65 6e 74  ires an argument
5080: 3a 20 5c 22 22 2c 20 7a 4f 70 74 2c 20 22 5c 22  : \"", zOpt, "\"
5090: 22 2c 30 29 3b 0a 20 20 20 20 20 20 72 65 74 75  ",0);.      retu
50a0: 72 6e 20 54 43 4c 5f 45 52 52 4f 52 3b 0a 20 20  rn TCL_ERROR;.  
50b0: 20 20 7d 0a 0a 20 20 20 20 69 66 28 20 7a 4f 70    }..    if( zOp
50c0: 74 5b 31 5d 3d 3d 27 73 27 20 29 7b 0a 20 20 20  t[1]=='s' ){.   
50d0: 20 20 20 69 66 28 20 54 63 6c 5f 47 65 74 49 6e     if( Tcl_GetIn
50e0: 74 46 72 6f 6d 4f 62 6a 28 69 6e 74 65 72 70 2c  tFromObj(interp,
50f0: 20 6f 62 6a 76 5b 69 2b 31 5d 2c 20 26 69 53 65   objv[i+1], &iSe
5100: 63 74 6f 72 53 69 7a 65 29 20 29 7b 0a 20 20 20  ctorSize) ){.   
5110: 20 20 20 20 20 72 65 74 75 72 6e 20 54 43 4c 5f       return TCL_
5120: 45 52 52 4f 52 3b 0a 20 20 20 20 20 20 7d 0a 20  ERROR;.      }. 
5130: 20 20 20 20 20 73 65 74 53 65 63 74 6f 72 73 69       setSectorsi
5140: 7a 65 20 3d 20 31 3b 0a 20 20 20 20 7d 65 6c 73  ze = 1;.    }els
5150: 65 7b 0a 20 20 20 20 20 20 69 6e 74 20 6a 3b 0a  e{.      int j;.
5160: 20 20 20 20 20 20 54 63 6c 5f 4f 62 6a 20 2a 2a        Tcl_Obj **
5170: 61 70 4f 62 6a 3b 0a 20 20 20 20 20 20 69 6e 74  apObj;.      int
5180: 20 6e 4f 62 6a 3b 0a 20 20 20 20 20 20 69 66 28   nObj;.      if(
5190: 20 54 63 6c 5f 4c 69 73 74 4f 62 6a 47 65 74 45   Tcl_ListObjGetE
51a0: 6c 65 6d 65 6e 74 73 28 69 6e 74 65 72 70 2c 20  lements(interp, 
51b0: 6f 62 6a 76 5b 69 2b 31 5d 2c 20 26 6e 4f 62 6a  objv[i+1], &nObj
51c0: 2c 20 26 61 70 4f 62 6a 29 20 29 7b 0a 20 20 20  , &apObj) ){.   
51d0: 20 20 20 20 20 72 65 74 75 72 6e 20 54 43 4c 5f       return TCL_
51e0: 45 52 52 4f 52 3b 0a 20 20 20 20 20 20 7d 0a 20  ERROR;.      }. 
51f0: 20 20 20 20 20 66 6f 72 28 6a 3d 30 3b 20 6a 3c       for(j=0; j<
5200: 6e 4f 62 6a 3b 20 6a 2b 2b 29 7b 0a 20 20 20 20  nObj; j++){.    
5210: 20 20 20 20 69 6e 74 20 72 63 3b 0a 20 20 20 20      int rc;.    
5220: 20 20 20 20 69 6e 74 20 69 43 68 6f 69 63 65 3b      int iChoice;
5230: 0a 20 20 20 20 20 20 20 20 54 63 6c 5f 4f 62 6a  .        Tcl_Obj
5240: 20 2a 70 46 6c 61 67 20 3d 20 54 63 6c 5f 44 75   *pFlag = Tcl_Du
5250: 70 6c 69 63 61 74 65 4f 62 6a 28 61 70 4f 62 6a  plicateObj(apObj
5260: 5b 6a 5d 29 3b 0a 20 20 20 20 20 20 20 20 54 63  [j]);.        Tc
5270: 6c 5f 49 6e 63 72 52 65 66 43 6f 75 6e 74 28 70  l_IncrRefCount(p
5280: 46 6c 61 67 29 3b 0a 20 20 20 20 20 20 20 20 54  Flag);.        T
5290: 63 6c 5f 55 74 66 54 6f 4c 6f 77 65 72 28 54 63  cl_UtfToLower(Tc
52a0: 6c 5f 47 65 74 53 74 72 69 6e 67 28 70 46 6c 61  l_GetString(pFla
52b0: 67 29 29 3b 0a 20 0a 20 20 20 20 20 20 20 20 72  g));. .        r
52c0: 63 20 3d 20 54 63 6c 5f 47 65 74 49 6e 64 65 78  c = Tcl_GetIndex
52d0: 46 72 6f 6d 4f 62 6a 53 74 72 75 63 74 28 0a 20  FromObjStruct(. 
52e0: 20 20 20 20 20 20 20 20 20 20 20 69 6e 74 65 72             inter
52f0: 70 2c 20 70 46 6c 61 67 2c 20 61 46 6c 61 67 2c  p, pFlag, aFlag,
5300: 20 73 69 7a 65 6f 66 28 61 46 6c 61 67 5b 30 5d   sizeof(aFlag[0]
5310: 29 2c 20 22 6e 6f 20 73 75 63 68 20 66 6c 61 67  ), "no such flag
5320: 22 2c 20 30 2c 20 26 69 43 68 6f 69 63 65 0a 20  ", 0, &iChoice. 
5330: 20 20 20 20 20 20 20 29 3b 0a 20 20 20 20 20 20         );.      
5340: 20 20 54 63 6c 5f 44 65 63 72 52 65 66 43 6f 75    Tcl_DecrRefCou
5350: 6e 74 28 70 46 6c 61 67 29 3b 0a 20 20 20 20 20  nt(pFlag);.     
5360: 20 20 20 69 66 28 20 72 63 20 29 7b 0a 20 20 20     if( rc ){.   
5370: 20 20 20 20 20 20 20 72 65 74 75 72 6e 20 54 43         return TC
5380: 4c 5f 45 52 52 4f 52 3b 0a 20 20 20 20 20 20 20  L_ERROR;.       
5390: 20 7d 0a 0a 20 20 20 20 20 20 20 20 69 44 63 20   }..        iDc 
53a0: 7c 3d 20 61 46 6c 61 67 5b 69 43 68 6f 69 63 65  |= aFlag[iChoice
53b0: 5d 2e 69 56 61 6c 75 65 3b 0a 20 20 20 20 20 20  ].iValue;.      
53c0: 7d 0a 20 20 20 20 20 20 73 65 74 44 65 76 69 63  }.      setDevic
53d0: 65 43 68 61 72 20 3d 20 31 3b 0a 20 20 20 20 7d  eChar = 1;.    }
53e0: 0a 20 20 7d 0a 0a 20 20 69 66 28 20 73 65 74 44  .  }..  if( setD
53f0: 65 76 69 63 65 43 68 61 72 20 29 7b 0a 20 20 20  eviceChar ){.   
5400: 20 2a 70 69 44 65 76 69 63 65 43 68 61 72 20 3d   *piDeviceChar =
5410: 20 69 44 63 3b 0a 20 20 7d 0a 20 20 69 66 28 20   iDc;.  }.  if( 
5420: 73 65 74 53 65 63 74 6f 72 73 69 7a 65 20 29 7b  setSectorsize ){
5430: 0a 20 20 20 20 2a 70 69 53 65 63 74 6f 72 53 69  .    *piSectorSi
5440: 7a 65 20 3d 20 69 53 65 63 74 6f 72 53 69 7a 65  ze = iSectorSize
5450: 3b 0a 20 20 7d 0a 0a 20 20 72 65 74 75 72 6e 20  ;.  }..  return 
5460: 54 43 4c 5f 4f 4b 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a  TCL_OK;.}../*.**
5470: 20 74 63 6c 63 6d 64 3a 20 20 20 73 71 6c 69 74   tclcmd:   sqlit
5480: 65 5f 63 72 61 73 68 70 61 72 61 6d 73 20 3f 4f  e_crashparams ?O
5490: 50 54 49 4f 4e 53 3f 20 44 45 4c 41 59 20 43 52  PTIONS? DELAY CR
54a0: 41 53 48 46 49 4c 45 0a 2a 2a 0a 2a 2a 20 54 68  ASHFILE.**.** Th
54b0: 69 73 20 70 72 6f 63 65 64 75 72 65 20 69 6d 70  is procedure imp
54c0: 6c 65 6d 65 6e 74 73 20 61 20 54 43 4c 20 63 6f  lements a TCL co
54d0: 6d 6d 61 6e 64 20 74 68 61 74 20 65 6e 61 62 6c  mmand that enabl
54e0: 65 73 20 63 72 61 73 68 20 74 65 73 74 69 6e 67  es crash testing
54f0: 0a 2a 2a 20 69 6e 20 74 65 73 74 66 69 78 74 75  .** in testfixtu
5500: 72 65 2e 20 20 4f 6e 63 65 20 65 6e 61 62 6c 65  re.  Once enable
5510: 64 2c 20 63 72 61 73 68 20 74 65 73 74 69 6e 67  d, crash testing
5520: 20 63 61 6e 6e 6f 74 20 62 65 20 64 69 73 61 62   cannot be disab
5530: 6c 65 64 2e 0a 2a 2a 0a 2a 2a 20 41 76 61 69 6c  led..**.** Avail
5540: 61 62 6c 65 20 6f 70 74 69 6f 6e 73 20 61 72 65  able options are
5550: 20 22 2d 63 68 61 72 61 63 74 65 72 69 73 74 69   "-characteristi
5560: 63 73 22 20 61 6e 64 20 22 2d 73 65 63 74 6f 72  cs" and "-sector
5570: 73 69 7a 65 22 2e 20 42 6f 74 68 20 72 65 71 75  size". Both requ
5580: 69 72 65 0a 2a 2a 20 61 6e 20 61 72 67 75 6d 65  ire.** an argume
5590: 6e 74 2e 20 46 6f 72 20 2d 73 65 63 74 6f 72 73  nt. For -sectors
55a0: 69 7a 65 2c 20 74 68 69 73 20 69 73 20 74 68 65  ize, this is the
55b0: 20 73 69 6d 75 6c 61 74 65 64 20 73 65 63 74 6f   simulated secto
55c0: 72 20 73 69 7a 65 20 69 6e 0a 2a 2a 20 62 79 74  r size in.** byt
55d0: 65 73 2e 20 46 6f 72 20 2d 63 68 61 72 61 63 74  es. For -charact
55e0: 65 72 69 73 74 69 63 73 2c 20 74 68 65 20 61 72  eristics, the ar
55f0: 67 75 6d 65 6e 74 20 6d 75 73 74 20 62 65 20 61  gument must be a
5600: 20 6c 69 73 74 20 6f 66 20 69 6f 2d 63 61 70 61   list of io-capa
5610: 62 69 6c 69 74 79 0a 2a 2a 20 66 6c 61 67 73 20  bility.** flags 
5620: 74 6f 20 73 69 6d 75 6c 61 74 65 2e 20 56 61 6c  to simulate. Val
5630: 69 64 20 66 6c 61 67 73 20 61 72 65 20 22 61 74  id flags are "at
5640: 6f 6d 69 63 22 2c 20 22 61 74 6f 6d 69 63 35 31  omic", "atomic51
5650: 32 22 2c 20 22 61 74 6f 6d 69 63 31 4b 22 2c 0a  2", "atomic1K",.
5660: 2a 2a 20 22 61 74 6f 6d 69 63 32 4b 22 2c 20 22  ** "atomic2K", "
5670: 61 74 6f 6d 69 63 34 4b 22 2c 20 22 61 74 6f 6d  atomic4K", "atom
5680: 69 63 38 4b 22 2c 20 22 61 74 6f 6d 69 63 31 36  ic8K", "atomic16
5690: 4b 22 2c 20 22 61 74 6f 6d 69 63 33 32 4b 22 2c  K", "atomic32K",
56a0: 20 0a 2a 2a 20 22 61 74 6f 6d 69 63 36 34 4b 22   .** "atomic64K"
56b0: 2c 20 22 73 65 71 75 65 6e 74 69 61 6c 22 20 61  , "sequential" a
56c0: 6e 64 20 22 73 61 66 65 5f 61 70 70 65 6e 64 22  nd "safe_append"
56d0: 2e 0a 2a 2a 0a 2a 2a 20 45 78 61 6d 70 6c 65 3a  ..**.** Example:
56e0: 0a 2a 2a 0a 2a 2a 20 20 20 73 71 6c 69 74 65 5f  .**.**   sqlite_
56f0: 63 72 61 73 68 70 61 72 61 6d 73 20 2d 73 65 63  crashparams -sec
5700: 74 20 31 30 32 34 20 2d 63 68 61 72 20 7b 61 74  t 1024 -char {at
5710: 6f 6d 69 63 20 73 65 71 75 65 6e 74 69 61 6c 7d  omic sequential}
5720: 20 2e 2f 74 65 73 74 2e 64 62 20 31 0a 2a 2a 0a   ./test.db 1.**.
5730: 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 63 72  */.static int cr
5740: 61 73 68 50 61 72 61 6d 73 4f 62 6a 43 6d 64 28  ashParamsObjCmd(
5750: 0a 20 20 76 6f 69 64 20 2a 20 63 6c 69 65 6e 74  .  void * client
5760: 44 61 74 61 2c 0a 20 20 54 63 6c 5f 49 6e 74 65  Data,.  Tcl_Inte
5770: 72 70 20 2a 69 6e 74 65 72 70 2c 0a 20 20 69 6e  rp *interp,.  in
5780: 74 20 6f 62 6a 63 2c 0a 20 20 54 63 6c 5f 4f 62  t objc,.  Tcl_Ob
5790: 6a 20 2a 43 4f 4e 53 54 20 6f 62 6a 76 5b 5d 0a  j *CONST objv[].
57a0: 29 7b 0a 20 20 69 6e 74 20 69 44 65 6c 61 79 3b  ){.  int iDelay;
57b0: 0a 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a  .  const char *z
57c0: 43 72 61 73 68 46 69 6c 65 3b 0a 20 20 69 6e 74  CrashFile;.  int
57d0: 20 6e 43 72 61 73 68 46 69 6c 65 2c 20 69 44 63   nCrashFile, iDc
57e0: 2c 20 69 53 65 63 74 6f 72 53 69 7a 65 3b 0a 0a  , iSectorSize;..
57f0: 20 20 73 74 61 74 69 63 20 73 71 6c 69 74 65 33    static sqlite3
5800: 5f 76 66 73 20 63 72 61 73 68 56 66 73 20 3d 20  _vfs crashVfs = 
5810: 7b 0a 20 20 20 20 31 2c 20 20 20 20 20 20 20 20  {.    1,        
5820: 20 20 20 20 20 20 20 20 20 20 2f 2a 20 69 56 65            /* iVe
5830: 72 73 69 6f 6e 20 2a 2f 0a 20 20 20 20 30 2c 20  rsion */.    0, 
5840: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
5850: 20 2f 2a 20 73 7a 4f 73 46 69 6c 65 20 2a 2f 0a   /* szOsFile */.
5860: 20 20 20 20 30 2c 20 20 20 20 20 20 20 20 20 20      0,          
5870: 20 20 20 20 20 20 20 20 2f 2a 20 6d 78 50 61 74          /* mxPat
5880: 68 6e 61 6d 65 20 2a 2f 0a 20 20 20 20 30 2c 20  hname */.    0, 
5890: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
58a0: 20 2f 2a 20 70 4e 65 78 74 20 2a 2f 0a 20 20 20   /* pNext */.   
58b0: 20 22 63 72 61 73 68 22 2c 20 20 20 20 20 20 20   "crash",       
58c0: 20 20 20 20 20 2f 2a 20 7a 4e 61 6d 65 20 2a 2f       /* zName */
58d0: 0a 20 20 20 20 30 2c 20 20 20 20 20 20 20 20 20  .    0,         
58e0: 20 20 20 20 20 20 20 20 20 2f 2a 20 70 41 70 70           /* pApp
58f0: 44 61 74 61 20 2a 2f 0a 20 20 0a 20 20 20 20 63  Data */.  .    c
5900: 66 4f 70 65 6e 2c 20 20 20 20 20 20 20 20 20 20  fOpen,          
5910: 20 20 20 20 20 2f 2a 20 78 4f 70 65 6e 20 2a 2f       /* xOpen */
5920: 0a 20 20 20 20 63 66 44 65 6c 65 74 65 2c 20 20  .    cfDelete,  
5930: 20 20 20 20 20 20 20 20 20 20 20 2f 2a 20 78 44             /* xD
5940: 65 6c 65 74 65 20 2a 2f 0a 20 20 20 20 63 66 41  elete */.    cfA
5950: 63 63 65 73 73 2c 20 20 20 20 20 20 20 20 20 20  ccess,          
5960: 20 20 20 2f 2a 20 78 41 63 63 65 73 73 20 2a 2f     /* xAccess */
5970: 0a 20 20 20 20 63 66 47 65 74 54 65 6d 70 4e 61  .    cfGetTempNa
5980: 6d 65 2c 20 20 20 20 20 20 20 20 2f 2a 20 78 47  me,        /* xG
5990: 65 74 54 65 6d 70 4e 61 6d 65 20 2a 2f 0a 20 20  etTempName */.  
59a0: 20 20 63 66 46 75 6c 6c 50 61 74 68 6e 61 6d 65    cfFullPathname
59b0: 2c 20 20 20 20 20 20 20 2f 2a 20 78 46 75 6c 6c  ,       /* xFull
59c0: 50 61 74 68 6e 61 6d 65 20 2a 2f 0a 20 20 20 20  Pathname */.    
59d0: 63 66 44 6c 4f 70 65 6e 2c 20 20 20 20 20 20 20  cfDlOpen,       
59e0: 20 20 20 20 20 20 2f 2a 20 78 44 6c 4f 70 65 6e        /* xDlOpen
59f0: 20 2a 2f 0a 20 20 20 20 63 66 44 6c 45 72 72 6f   */.    cfDlErro
5a00: 72 2c 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a  r,            /*
5a10: 20 78 44 6c 45 72 72 6f 72 20 2a 2f 0a 20 20 20   xDlError */.   
5a20: 20 63 66 44 6c 53 79 6d 2c 20 20 20 20 20 20 20   cfDlSym,       
5a30: 20 20 20 20 20 20 20 2f 2a 20 78 44 6c 53 79 6d         /* xDlSym
5a40: 20 2a 2f 0a 20 20 20 20 63 66 44 6c 43 6c 6f 73   */.    cfDlClos
5a50: 65 2c 20 20 20 20 20 20 20 20 20 20 20 20 2f 2a  e,            /*
5a60: 20 78 44 6c 43 6c 6f 73 65 20 2a 2f 0a 20 20 20   xDlClose */.   
5a70: 20 63 66 52 61 6e 64 6f 6d 6e 65 73 73 2c 20 20   cfRandomness,  
5a80: 20 20 20 20 20 20 20 2f 2a 20 78 52 61 6e 64 6f         /* xRando
5a90: 6d 6e 65 73 73 20 2a 2f 0a 20 20 20 20 63 66 53  mness */.    cfS
5aa0: 6c 65 65 70 2c 20 20 20 20 20 20 20 20 20 20 20  leep,           
5ab0: 20 20 20 2f 2a 20 78 53 6c 65 65 70 20 2a 2f 0a     /* xSleep */.
5ac0: 20 20 20 20 63 66 43 75 72 72 65 6e 74 54 69 6d      cfCurrentTim
5ad0: 65 20 20 20 20 20 20 20 20 20 2f 2a 20 78 43 75  e         /* xCu
5ae0: 72 72 65 6e 74 54 69 6d 65 20 2a 2f 0a 20 20 7d  rrentTime */.  }
5af0: 3b 0a 0a 0a 20 20 69 66 28 20 63 72 61 73 68 56  ;...  if( crashV
5b00: 66 73 2e 70 41 70 70 44 61 74 61 3d 3d 30 20 29  fs.pAppData==0 )
5b10: 7b 0a 20 20 20 20 73 71 6c 69 74 65 33 5f 76 66  {.    sqlite3_vf
5b20: 73 20 2a 70 4f 72 69 67 69 6e 61 6c 56 66 73 20  s *pOriginalVfs 
5b30: 3d 20 73 71 6c 69 74 65 33 5f 76 66 73 5f 66 69  = sqlite3_vfs_fi
5b40: 6e 64 28 30 29 3b 0a 20 20 20 20 63 72 61 73 68  nd(0);.    crash
5b50: 56 66 73 2e 6d 78 50 61 74 68 6e 61 6d 65 20 3d  Vfs.mxPathname =
5b60: 20 70 4f 72 69 67 69 6e 61 6c 56 66 73 2d 3e 6d   pOriginalVfs->m
5b70: 78 50 61 74 68 6e 61 6d 65 3b 0a 20 20 20 20 63  xPathname;.    c
5b80: 72 61 73 68 56 66 73 2e 70 41 70 70 44 61 74 61  rashVfs.pAppData
5b90: 20 3d 20 28 76 6f 69 64 20 2a 29 70 4f 72 69 67   = (void *)pOrig
5ba0: 69 6e 61 6c 56 66 73 3b 0a 20 20 20 20 63 72 61  inalVfs;.    cra
5bb0: 73 68 56 66 73 2e 73 7a 4f 73 46 69 6c 65 20 3d  shVfs.szOsFile =
5bc0: 20 73 69 7a 65 6f 66 28 43 72 61 73 68 46 69 6c   sizeof(CrashFil
5bd0: 65 29 20 2b 20 70 4f 72 69 67 69 6e 61 6c 56 66  e) + pOriginalVf
5be0: 73 2d 3e 73 7a 4f 73 46 69 6c 65 3b 0a 20 20 20  s->szOsFile;.   
5bf0: 20 2f 2a 20 73 71 6c 69 74 65 33 5f 76 66 73 5f   /* sqlite3_vfs_
5c00: 75 6e 72 65 67 69 73 74 65 72 28 70 4f 72 69 67  unregister(pOrig
5c10: 69 6e 61 6c 56 66 73 29 3b 20 2a 2f 0a 20 20 20  inalVfs); */.   
5c20: 20 73 71 6c 69 74 65 33 5f 76 66 73 5f 72 65 67   sqlite3_vfs_reg
5c30: 69 73 74 65 72 28 26 63 72 61 73 68 56 66 73 2c  ister(&crashVfs,
5c40: 20 31 29 3b 0a 20 20 7d 0a 0a 20 20 69 44 63 20   1);.  }..  iDc 
5c50: 3d 20 2d 31 3b 0a 20 20 69 53 65 63 74 6f 72 53  = -1;.  iSectorS
5c60: 69 7a 65 20 3d 20 2d 31 3b 0a 0a 20 20 69 66 28  ize = -1;..  if(
5c70: 20 6f 62 6a 63 3c 33 20 29 7b 0a 20 20 20 20 54   objc<3 ){.    T
5c80: 63 6c 5f 57 72 6f 6e 67 4e 75 6d 41 72 67 73 28  cl_WrongNumArgs(
5c90: 69 6e 74 65 72 70 2c 20 31 2c 20 6f 62 6a 76 2c  interp, 1, objv,
5ca0: 20 22 3f 4f 50 54 49 4f 4e 53 3f 20 44 45 4c 41   "?OPTIONS? DELA
5cb0: 59 20 43 52 41 53 48 46 49 4c 45 22 29 3b 0a 20  Y CRASHFILE");. 
5cc0: 20 20 20 67 6f 74 6f 20 65 72 72 6f 72 3b 0a 20     goto error;. 
5cd0: 20 7d 0a 0a 20 20 7a 43 72 61 73 68 46 69 6c 65   }..  zCrashFile
5ce0: 20 3d 20 54 63 6c 5f 47 65 74 53 74 72 69 6e 67   = Tcl_GetString
5cf0: 46 72 6f 6d 4f 62 6a 28 6f 62 6a 76 5b 6f 62 6a  FromObj(objv[obj
5d00: 63 2d 31 5d 2c 20 26 6e 43 72 61 73 68 46 69 6c  c-1], &nCrashFil
5d10: 65 29 3b 0a 20 20 69 66 28 20 6e 43 72 61 73 68  e);.  if( nCrash
5d20: 46 69 6c 65 3e 3d 73 69 7a 65 6f 66 28 67 2e 7a  File>=sizeof(g.z
5d30: 43 72 61 73 68 46 69 6c 65 29 20 29 7b 0a 20 20  CrashFile) ){.  
5d40: 20 20 54 63 6c 5f 41 70 70 65 6e 64 52 65 73 75    Tcl_AppendResu
5d50: 6c 74 28 69 6e 74 65 72 70 2c 20 22 46 69 6c 65  lt(interp, "File
5d60: 6e 61 6d 65 20 69 73 20 74 6f 6f 20 6c 6f 6e 67  name is too long
5d70: 3a 20 5c 22 22 2c 20 7a 43 72 61 73 68 46 69 6c  : \"", zCrashFil
5d80: 65 2c 20 22 5c 22 22 2c 20 30 29 3b 0a 20 20 20  e, "\"", 0);.   
5d90: 20 67 6f 74 6f 20 65 72 72 6f 72 3b 0a 20 20 7d   goto error;.  }
5da0: 0a 20 20 69 66 28 20 54 63 6c 5f 47 65 74 49 6e  .  if( Tcl_GetIn
5db0: 74 46 72 6f 6d 4f 62 6a 28 69 6e 74 65 72 70 2c  tFromObj(interp,
5dc0: 20 6f 62 6a 76 5b 6f 62 6a 63 2d 32 5d 2c 20 26   objv[objc-2], &
5dd0: 69 44 65 6c 61 79 29 20 29 7b 0a 20 20 20 20 67  iDelay) ){.    g
5de0: 6f 74 6f 20 65 72 72 6f 72 3b 0a 20 20 7d 0a 0a  oto error;.  }..
5df0: 20 20 69 66 28 20 70 72 6f 63 65 73 73 44 65 76    if( processDev
5e00: 53 79 6d 41 72 67 73 28 69 6e 74 65 72 70 2c 20  SymArgs(interp, 
5e10: 6f 62 6a 63 2d 33 2c 20 26 6f 62 6a 76 5b 31 5d  objc-3, &objv[1]
5e20: 2c 20 26 69 44 63 2c 20 26 69 53 65 63 74 6f 72  , &iDc, &iSector
5e30: 53 69 7a 65 29 20 29 7b 0a 20 20 20 20 72 65 74  Size) ){.    ret
5e40: 75 72 6e 20 54 43 4c 5f 45 52 52 4f 52 3b 0a 20  urn TCL_ERROR;. 
5e50: 20 7d 0a 0a 20 20 69 66 28 20 69 44 63 3e 3d 30   }..  if( iDc>=0
5e60: 20 29 7b 0a 20 20 20 20 67 2e 69 44 65 76 69 63   ){.    g.iDevic
5e70: 65 43 68 61 72 61 63 74 65 72 69 73 74 69 63 73  eCharacteristics
5e80: 20 3d 20 69 44 63 3b 0a 20 20 7d 0a 20 20 69 66   = iDc;.  }.  if
5e90: 28 20 69 53 65 63 74 6f 72 53 69 7a 65 3e 3d 30  ( iSectorSize>=0
5ea0: 20 29 7b 0a 20 20 20 20 67 2e 69 53 65 63 74 6f   ){.    g.iSecto
5eb0: 72 53 69 7a 65 20 3d 20 69 53 65 63 74 6f 72 53  rSize = iSectorS
5ec0: 69 7a 65 3b 0a 20 20 7d 0a 0a 20 20 67 2e 69 43  ize;.  }..  g.iC
5ed0: 72 61 73 68 20 3d 20 69 44 65 6c 61 79 3b 0a 20  rash = iDelay;. 
5ee0: 20 6d 65 6d 63 70 79 28 67 2e 7a 43 72 61 73 68   memcpy(g.zCrash
5ef0: 46 69 6c 65 2c 20 7a 43 72 61 73 68 46 69 6c 65  File, zCrashFile
5f00: 2c 20 6e 43 72 61 73 68 46 69 6c 65 2b 31 29 3b  , nCrashFile+1);
5f10: 0a 20 20 73 71 6c 69 74 65 33 43 72 61 73 68 54  .  sqlite3CrashT
5f20: 65 73 74 45 6e 61 62 6c 65 20 3d 20 31 3b 0a 20  estEnable = 1;. 
5f30: 20 72 65 74 75 72 6e 20 54 43 4c 5f 4f 4b 3b 0a   return TCL_OK;.
5f40: 0a 65 72 72 6f 72 3a 0a 20 20 72 65 74 75 72 6e  .error:.  return
5f50: 20 54 43 4c 5f 45 52 52 4f 52 3b 0a 7d 0a 0a 73   TCL_ERROR;.}..s
5f60: 74 61 74 69 63 20 69 6e 74 20 64 65 76 53 79 6d  tatic int devSym
5f70: 4f 62 6a 43 6d 64 28 0a 20 20 76 6f 69 64 20 2a  ObjCmd(.  void *
5f80: 20 63 6c 69 65 6e 74 44 61 74 61 2c 0a 20 20 54   clientData,.  T
5f90: 63 6c 5f 49 6e 74 65 72 70 20 2a 69 6e 74 65 72  cl_Interp *inter
5fa0: 70 2c 0a 20 20 69 6e 74 20 6f 62 6a 63 2c 0a 20  p,.  int objc,. 
5fb0: 20 54 63 6c 5f 4f 62 6a 20 2a 43 4f 4e 53 54 20   Tcl_Obj *CONST 
5fc0: 6f 62 6a 76 5b 5d 0a 29 7b 0a 0a 20 20 65 78 74  objv[].){..  ext
5fd0: 65 72 6e 20 69 6e 74 20 73 71 6c 69 74 65 33 5f  ern int sqlite3_
5fe0: 74 65 73 74 5f 64 65 76 69 63 65 5f 63 68 61 72  test_device_char
5ff0: 61 63 74 65 72 69 73 74 69 63 73 3b 0a 20 20 65  acteristics;.  e
6000: 78 74 65 72 6e 20 69 6e 74 20 73 71 6c 69 74 65  xtern int sqlite
6010: 33 5f 74 65 73 74 5f 73 65 63 74 6f 72 5f 73 69  3_test_sector_si
6020: 7a 65 3b 0a 0a 20 20 69 6e 74 20 69 44 63 20 3d  ze;..  int iDc =
6030: 20 2d 31 3b 0a 20 20 69 6e 74 20 69 53 65 63 74   -1;.  int iSect
6040: 6f 72 53 69 7a 65 20 3d 20 2d 31 3b 0a 20 20 69  orSize = -1;.  i
6050: 66 28 20 70 72 6f 63 65 73 73 44 65 76 53 79 6d  f( processDevSym
6060: 41 72 67 73 28 69 6e 74 65 72 70 2c 20 6f 62 6a  Args(interp, obj
6070: 63 2d 31 2c 20 26 6f 62 6a 76 5b 31 5d 2c 20 26  c-1, &objv[1], &
6080: 69 44 63 2c 20 26 69 53 65 63 74 6f 72 53 69 7a  iDc, &iSectorSiz
6090: 65 29 20 29 7b 0a 20 20 20 20 72 65 74 75 72 6e  e) ){.    return
60a0: 20 54 43 4c 5f 45 52 52 4f 52 3b 0a 20 20 7d 0a   TCL_ERROR;.  }.
60b0: 0a 20 20 69 66 28 20 69 44 63 3e 3d 30 20 29 7b  .  if( iDc>=0 ){
60c0: 0a 20 20 20 20 73 71 6c 69 74 65 33 5f 74 65 73  .    sqlite3_tes
60d0: 74 5f 64 65 76 69 63 65 5f 63 68 61 72 61 63 74  t_device_charact
60e0: 65 72 69 73 74 69 63 73 20 3d 20 69 44 63 3b 0a  eristics = iDc;.
60f0: 20 20 7d 0a 20 20 69 66 28 20 69 53 65 63 74 6f    }.  if( iSecto
6100: 72 53 69 7a 65 3e 3d 30 20 29 7b 0a 20 20 20 20  rSize>=0 ){.    
6110: 73 71 6c 69 74 65 33 5f 74 65 73 74 5f 73 65 63  sqlite3_test_sec
6120: 74 6f 72 5f 73 69 7a 65 20 3d 20 69 53 65 63 74  tor_size = iSect
6130: 6f 72 53 69 7a 65 3b 0a 20 20 7d 0a 0a 20 20 72  orSize;.  }..  r
6140: 65 74 75 72 6e 20 54 43 4c 5f 4f 4b 3b 0a 7d 0a  eturn TCL_OK;.}.
6150: 0a 23 65 6e 64 69 66 20 2f 2a 20 53 51 4c 49 54  .#endif /* SQLIT
6160: 45 5f 4f 4d 49 54 5f 44 49 53 4b 49 4f 20 2a 2f  E_OMIT_DISKIO */
6170: 0a 0a 2f 2a 0a 2a 2a 20 54 68 69 73 20 70 72 6f  ../*.** This pro
6180: 63 65 64 75 72 65 20 72 65 67 69 73 74 65 72 73  cedure registers
6190: 20 74 68 65 20 54 43 4c 20 70 72 6f 63 65 64 75   the TCL procedu
61a0: 72 65 73 20 64 65 66 69 6e 65 64 20 69 6e 20 74  res defined in t
61b0: 68 69 73 20 66 69 6c 65 2e 0a 2a 2f 0a 69 6e 74  his file..*/.int
61c0: 20 53 71 6c 69 74 65 74 65 73 74 36 5f 49 6e 69   Sqlitetest6_Ini
61d0: 74 28 54 63 6c 5f 49 6e 74 65 72 70 20 2a 69 6e  t(Tcl_Interp *in
61e0: 74 65 72 70 29 7b 0a 23 69 66 6e 64 65 66 20 53  terp){.#ifndef S
61f0: 51 4c 49 54 45 5f 4f 4d 49 54 5f 44 49 53 4b 49  QLITE_OMIT_DISKI
6200: 4f 0a 20 20 54 63 6c 5f 43 72 65 61 74 65 4f 62  O.  Tcl_CreateOb
6210: 6a 43 6f 6d 6d 61 6e 64 28 69 6e 74 65 72 70 2c  jCommand(interp,
6220: 20 22 73 71 6c 69 74 65 33 5f 63 72 61 73 68 70   "sqlite3_crashp
6230: 61 72 61 6d 73 22 2c 20 63 72 61 73 68 50 61 72  arams", crashPar
6240: 61 6d 73 4f 62 6a 43 6d 64 2c 20 30 2c 20 30 29  amsObjCmd, 0, 0)
6250: 3b 0a 20 20 54 63 6c 5f 43 72 65 61 74 65 4f 62  ;.  Tcl_CreateOb
6260: 6a 43 6f 6d 6d 61 6e 64 28 69 6e 74 65 72 70 2c  jCommand(interp,
6270: 20 22 73 71 6c 69 74 65 33 5f 73 69 6d 75 6c 61   "sqlite3_simula
6280: 74 65 5f 64 65 76 69 63 65 22 2c 20 64 65 76 53  te_device", devS
6290: 79 6d 4f 62 6a 43 6d 64 2c 20 30 2c 20 30 29 3b  ymObjCmd, 0, 0);
62a0: 0a 23 65 6e 64 69 66 0a 20 20 72 65 74 75 72 6e  .#endif.  return
62b0: 20 54 43 4c 5f 4f 4b 3b 0a 7d 0a 0a 23 65 6e 64   TCL_OK;.}..#end
62c0: 69 66 20 2f 2a 20 53 51 4c 49 54 45 5f 54 45 53  if /* SQLITE_TES
62d0: 54 20 2a 2f 0a                                   T */.