blob: ec83b139108ed783d227ff19f5003ae285264bdf [file] [log] [blame]
drh75897232000-05-29 14:26:00 +00001/*
drhb19a2bc2001-09-16 00:13:26 +00002** 2001 September 15
drh75897232000-05-29 14:26:00 +00003**
drhb19a2bc2001-09-16 00:13:26 +00004** The author disclaims copyright to this source code. In place of
5** a legal notice, here is a blessing:
drh75897232000-05-29 14:26:00 +00006**
drhb19a2bc2001-09-16 00:13:26 +00007** May you do good and not evil.
8** May you find forgiveness for yourself and forgive others.
9** May you share freely, never taking more than you give.
drh75897232000-05-29 14:26:00 +000010**
11*************************************************************************
12** This file contains code to implement the "sqlite" command line
13** utility for accessing SQLite databases.
drh75897232000-05-29 14:26:00 +000014*/
mistachkina3b2ff52011-09-16 20:16:36 +000015#if (defined(_WIN32) || defined(WIN32)) && !defined(_CRT_SECURE_NO_WARNINGS)
shane18e526c2008-12-10 22:30:24 +000016/* This needs to come before any includes for MSVC compiler */
17#define _CRT_SECURE_NO_WARNINGS
18#endif
19
drh36f7dd32011-10-13 16:02:17 +000020/*
21** Enable large-file support for fopen() and friends on unix.
22*/
23#ifndef SQLITE_DISABLE_LFS
24# define _LARGE_FILE 1
25# ifndef _FILE_OFFSET_BITS
26# define _FILE_OFFSET_BITS 64
27# endif
28# define _LARGEFILE_SOURCE 1
29#endif
30
drh75897232000-05-29 14:26:00 +000031#include <stdlib.h>
32#include <string.h>
33#include <stdio.h>
danielk19772a02e332004-06-05 08:04:36 +000034#include <assert.h>
drh1d482dd2004-05-31 18:23:07 +000035#include "sqlite3.h"
drhf442e332014-09-10 19:01:14 +000036#if SQLITE_USER_AUTHENTICATION
37# include "sqlite3userauth.h"
38#endif
drh75897232000-05-29 14:26:00 +000039#include <ctype.h>
drhb0603412007-02-28 04:47:26 +000040#include <stdarg.h>
persicom7e2dfdd2002-04-18 02:46:52 +000041
drh83905c92012-06-21 13:00:37 +000042#if !defined(_WIN32) && !defined(WIN32)
drh4c504392000-10-16 22:06:40 +000043# include <signal.h>
chw97185482008-11-17 08:05:31 +000044# if !defined(__RTP__) && !defined(_WRS_KERNEL)
45# include <pwd.h>
46# endif
drhdd45df82002-04-18 12:39:03 +000047# include <unistd.h>
48# include <sys/types.h>
drh4c504392000-10-16 22:06:40 +000049#endif
drh75897232000-05-29 14:26:00 +000050
drhaaa21b42014-02-11 14:37:51 +000051#if defined(HAVE_READLINE) && HAVE_READLINE!=0
drh8e7e7a22000-05-30 18:45:23 +000052# include <readline/readline.h>
53# include <readline/history.h>
drhaaa21b42014-02-11 14:37:51 +000054#else
55# undef HAVE_READLINE
drh81d7fd12010-12-08 00:02:26 +000056#endif
drhaaa21b42014-02-11 14:37:51 +000057#if defined(HAVE_EDITLINE) && !defined(HAVE_READLINE)
58# define HAVE_READLINE 1
59# include <editline/readline.h>
60#endif
61#if !defined(HAVE_READLINE)
persicom1d0b8722002-04-18 02:53:04 +000062# define add_history(X)
drh67505e72002-04-19 12:34:06 +000063# define read_history(X)
64# define write_history(X)
65# define stifle_history(X)
drh75897232000-05-29 14:26:00 +000066#endif
67
adamd2e8464a2006-09-06 21:39:40 +000068#if defined(_WIN32) || defined(WIN32)
69# include <io.h>
drh6976c212014-07-24 12:09:47 +000070# include <fcntl.h>
shane18e526c2008-12-10 22:30:24 +000071#define isatty(h) _isatty(h)
drh07901eb2014-02-28 19:37:45 +000072#ifndef access
73# define access(f,m) _access((f),(m))
74#endif
drh67ceaa62012-08-27 21:19:03 +000075#undef popen
drh53371f92013-07-25 17:07:03 +000076#define popen _popen
drh67ceaa62012-08-27 21:19:03 +000077#undef pclose
drh12cd6cf2013-06-29 15:40:22 +000078#define pclose _pclose
adamd2e8464a2006-09-06 21:39:40 +000079#else
drh4328c8b2003-04-26 02:50:11 +000080/* Make sure isatty() has a prototype.
81*/
drhb2acc3b2011-10-13 16:36:29 +000082extern int isatty(int);
drh4328c8b2003-04-26 02:50:11 +000083
drh53371f92013-07-25 17:07:03 +000084/* popen and pclose are not C89 functions and so are sometimes omitted from
85** the <stdio.h> header */
mistachkinf6418892013-08-28 01:54:12 +000086extern FILE *popen(const char*,const char*);
87extern int pclose(FILE*);
88#endif
drh53371f92013-07-25 17:07:03 +000089
chw65d3c132007-11-12 21:09:10 +000090#if defined(_WIN32_WCE)
91/* Windows CE (arm-wince-mingw32ce-gcc) does not provide isatty()
92 * thus we always assume that we have a console. That can be
93 * overridden with the -batch command line option.
94 */
95#define isatty(x) 1
96#endif
97
drhf0693c82011-10-11 20:41:54 +000098/* ctype macros that work with signed characters */
99#define IsSpace(X) isspace((unsigned char)X)
100#define IsDigit(X) isdigit((unsigned char)X)
101#define ToLower(X) (char)tolower((unsigned char)X)
102
drh43408312013-10-30 12:43:36 +0000103
104/* True if the timer is enabled */
105static int enableTimer = 0;
106
107/* Return the current wall-clock time */
108static sqlite3_int64 timeOfDay(void){
109 static sqlite3_vfs *clockVfs = 0;
110 sqlite3_int64 t;
111 if( clockVfs==0 ) clockVfs = sqlite3_vfs_find(0);
112 if( clockVfs->iVersion>=1 && clockVfs->xCurrentTimeInt64!=0 ){
113 clockVfs->xCurrentTimeInt64(clockVfs, &t);
114 }else{
115 double r;
116 clockVfs->xCurrentTime(clockVfs, &r);
117 t = (sqlite3_int64)(r*86400000.0);
118 }
119 return t;
120}
121
drhd5d0f642013-02-20 00:54:21 +0000122#if !defined(_WIN32) && !defined(WIN32) && !defined(_WRS_KERNEL) \
123 && !defined(__minux)
drh3b1a9882007-11-02 12:53:03 +0000124#include <sys/time.h>
125#include <sys/resource.h>
126
drhda108222009-02-25 19:07:24 +0000127/* Saved resource information for the beginning of an operation */
drh43408312013-10-30 12:43:36 +0000128static struct rusage sBegin; /* CPU time at start */
129static sqlite3_int64 iBegin; /* Wall-clock time at start */
drhda108222009-02-25 19:07:24 +0000130
drhda108222009-02-25 19:07:24 +0000131/*
132** Begin timing an operation
133*/
134static void beginTimer(void){
135 if( enableTimer ){
136 getrusage(RUSAGE_SELF, &sBegin);
drh43408312013-10-30 12:43:36 +0000137 iBegin = timeOfDay();
drhda108222009-02-25 19:07:24 +0000138 }
139}
140
141/* Return the difference of two time_structs in seconds */
142static double timeDiff(struct timeval *pStart, struct timeval *pEnd){
143 return (pEnd->tv_usec - pStart->tv_usec)*0.000001 +
144 (double)(pEnd->tv_sec - pStart->tv_sec);
145}
146
147/*
148** Print the timing results.
149*/
150static void endTimer(void){
151 if( enableTimer ){
152 struct rusage sEnd;
drh43408312013-10-30 12:43:36 +0000153 sqlite3_int64 iEnd = timeOfDay();
drhda108222009-02-25 19:07:24 +0000154 getrusage(RUSAGE_SELF, &sEnd);
drh43408312013-10-30 12:43:36 +0000155 printf("Run Time: real %.3f user %f sys %f\n",
156 (iEnd - iBegin)*0.001,
drhda108222009-02-25 19:07:24 +0000157 timeDiff(&sBegin.ru_utime, &sEnd.ru_utime),
158 timeDiff(&sBegin.ru_stime, &sEnd.ru_stime));
159 }
160}
shaneb320ccd2009-10-21 03:42:58 +0000161
drhda108222009-02-25 19:07:24 +0000162#define BEGIN_TIMER beginTimer()
163#define END_TIMER endTimer()
164#define HAS_TIMER 1
shaneb320ccd2009-10-21 03:42:58 +0000165
166#elif (defined(_WIN32) || defined(WIN32))
167
168#include <windows.h>
169
170/* Saved resource information for the beginning of an operation */
171static HANDLE hProcess;
172static FILETIME ftKernelBegin;
173static FILETIME ftUserBegin;
drh43408312013-10-30 12:43:36 +0000174static sqlite3_int64 ftWallBegin;
shaneb320ccd2009-10-21 03:42:58 +0000175typedef BOOL (WINAPI *GETPROCTIMES)(HANDLE, LPFILETIME, LPFILETIME, LPFILETIME, LPFILETIME);
176static GETPROCTIMES getProcessTimesAddr = NULL;
177
shaneb320ccd2009-10-21 03:42:58 +0000178/*
179** Check to see if we have timer support. Return 1 if necessary
180** support found (or found previously).
181*/
182static int hasTimer(void){
183 if( getProcessTimesAddr ){
184 return 1;
185 } else {
186 /* GetProcessTimes() isn't supported in WIN95 and some other Windows versions.
187 ** See if the version we are running on has it, and if it does, save off
188 ** a pointer to it and the current process handle.
189 */
190 hProcess = GetCurrentProcess();
191 if( hProcess ){
192 HINSTANCE hinstLib = LoadLibrary(TEXT("Kernel32.dll"));
193 if( NULL != hinstLib ){
194 getProcessTimesAddr = (GETPROCTIMES) GetProcAddress(hinstLib, "GetProcessTimes");
195 if( NULL != getProcessTimesAddr ){
196 return 1;
197 }
198 FreeLibrary(hinstLib);
199 }
200 }
201 }
202 return 0;
203}
204
205/*
206** Begin timing an operation
207*/
208static void beginTimer(void){
209 if( enableTimer && getProcessTimesAddr ){
210 FILETIME ftCreation, ftExit;
211 getProcessTimesAddr(hProcess, &ftCreation, &ftExit, &ftKernelBegin, &ftUserBegin);
drh43408312013-10-30 12:43:36 +0000212 ftWallBegin = timeOfDay();
shaneb320ccd2009-10-21 03:42:58 +0000213 }
214}
215
216/* Return the difference of two FILETIME structs in seconds */
217static double timeDiff(FILETIME *pStart, FILETIME *pEnd){
218 sqlite_int64 i64Start = *((sqlite_int64 *) pStart);
219 sqlite_int64 i64End = *((sqlite_int64 *) pEnd);
220 return (double) ((i64End - i64Start) / 10000000.0);
221}
222
223/*
224** Print the timing results.
225*/
226static void endTimer(void){
227 if( enableTimer && getProcessTimesAddr){
228 FILETIME ftCreation, ftExit, ftKernelEnd, ftUserEnd;
drh43408312013-10-30 12:43:36 +0000229 sqlite3_int64 ftWallEnd = timeOfDay();
shaneb320ccd2009-10-21 03:42:58 +0000230 getProcessTimesAddr(hProcess, &ftCreation, &ftExit, &ftKernelEnd, &ftUserEnd);
drh43408312013-10-30 12:43:36 +0000231 printf("Run Time: real %.3f user %f sys %f\n",
232 (ftWallEnd - ftWallBegin)*0.001,
shaneb320ccd2009-10-21 03:42:58 +0000233 timeDiff(&ftUserBegin, &ftUserEnd),
234 timeDiff(&ftKernelBegin, &ftKernelEnd));
235 }
236}
237
238#define BEGIN_TIMER beginTimer()
239#define END_TIMER endTimer()
240#define HAS_TIMER hasTimer()
241
drhda108222009-02-25 19:07:24 +0000242#else
243#define BEGIN_TIMER
244#define END_TIMER
245#define HAS_TIMER 0
246#endif
247
shanec0688ea2009-03-05 03:48:06 +0000248/*
249** Used to prevent warnings about unused parameters
250*/
251#define UNUSED_PARAMETER(x) (void)(x)
252
drhe91d16b2008-12-08 18:27:31 +0000253/*
drhc49f44e2006-10-26 18:15:42 +0000254** If the following flag is set, then command execution stops
255** at an error if we are not interactive.
256*/
257static int bail_on_error = 0;
258
259/*
drhc28490c2006-10-26 14:25:58 +0000260** Threat stdin as an interactive input if the following variable
261** is true. Otherwise, assume stdin is connected to a file or pipe.
262*/
263static int stdin_is_interactive = 1;
264
265/*
drh4c504392000-10-16 22:06:40 +0000266** The following is the open SQLite database. We make a pointer
267** to this database a static variable so that it can be accessed
268** by the SIGINT handler to interrupt database processing.
269*/
danielk197792f9a1b2004-06-19 09:08:16 +0000270static sqlite3 *db = 0;
drh4c504392000-10-16 22:06:40 +0000271
272/*
drh67505e72002-04-19 12:34:06 +0000273** True if an interrupt (Control-C) has been received.
274*/
drh43617e92006-03-06 20:55:46 +0000275static volatile int seenInterrupt = 0;
drh67505e72002-04-19 12:34:06 +0000276
277/*
persicom7e2dfdd2002-04-18 02:46:52 +0000278** This is the name of our program. It is set in main(), used
279** in a number of other places, mostly for error messages.
280*/
281static char *Argv0;
282
283/*
284** Prompt strings. Initialized in main. Settable with
285** .prompt main continue
286*/
287static char mainPrompt[20]; /* First line prompt. default: "sqlite> "*/
288static char continuePrompt[20]; /* Continuation prompt. default: " ...> " */
289
drhb0603412007-02-28 04:47:26 +0000290/*
291** Write I/O traces to the following stream.
292*/
rsebe0a9092007-07-30 18:24:38 +0000293#ifdef SQLITE_ENABLE_IOTRACE
drhb0603412007-02-28 04:47:26 +0000294static FILE *iotrace = 0;
rsebe0a9092007-07-30 18:24:38 +0000295#endif
drhb0603412007-02-28 04:47:26 +0000296
297/*
298** This routine works like printf in that its first argument is a
299** format string and subsequent arguments are values to be substituted
300** in place of % fields. The result of formatting this string
301** is written to iotrace.
302*/
rsebe0a9092007-07-30 18:24:38 +0000303#ifdef SQLITE_ENABLE_IOTRACE
drhb0603412007-02-28 04:47:26 +0000304static void iotracePrintf(const char *zFormat, ...){
305 va_list ap;
drhf075cd02007-02-28 06:14:25 +0000306 char *z;
drhb0603412007-02-28 04:47:26 +0000307 if( iotrace==0 ) return;
308 va_start(ap, zFormat);
drhf075cd02007-02-28 06:14:25 +0000309 z = sqlite3_vmprintf(zFormat, ap);
drhb0603412007-02-28 04:47:26 +0000310 va_end(ap);
drhf075cd02007-02-28 06:14:25 +0000311 fprintf(iotrace, "%s", z);
312 sqlite3_free(z);
drhb0603412007-02-28 04:47:26 +0000313}
rsebe0a9092007-07-30 18:24:38 +0000314#endif
drhb0603412007-02-28 04:47:26 +0000315
drh44c2eb12003-04-30 11:38:26 +0000316
persicom7e2dfdd2002-04-18 02:46:52 +0000317/*
drh83965662003-04-17 02:54:13 +0000318** Determines if a string is a number of not.
319*/
danielk19772e588c72005-12-09 14:25:08 +0000320static int isNumber(const char *z, int *realnum){
drhc8d74412004-08-31 23:41:26 +0000321 if( *z=='-' || *z=='+' ) z++;
drhf0693c82011-10-11 20:41:54 +0000322 if( !IsDigit(*z) ){
drhc8d74412004-08-31 23:41:26 +0000323 return 0;
324 }
325 z++;
326 if( realnum ) *realnum = 0;
drhf0693c82011-10-11 20:41:54 +0000327 while( IsDigit(*z) ){ z++; }
drhc8d74412004-08-31 23:41:26 +0000328 if( *z=='.' ){
329 z++;
drhf0693c82011-10-11 20:41:54 +0000330 if( !IsDigit(*z) ) return 0;
331 while( IsDigit(*z) ){ z++; }
drhc8d74412004-08-31 23:41:26 +0000332 if( realnum ) *realnum = 1;
333 }
334 if( *z=='e' || *z=='E' ){
335 z++;
336 if( *z=='+' || *z=='-' ) z++;
drhf0693c82011-10-11 20:41:54 +0000337 if( !IsDigit(*z) ) return 0;
338 while( IsDigit(*z) ){ z++; }
drhc8d74412004-08-31 23:41:26 +0000339 if( realnum ) *realnum = 1;
340 }
341 return *z==0;
342}
drh83965662003-04-17 02:54:13 +0000343
344/*
danielk1977bc6ada42004-06-30 08:20:16 +0000345** A global char* and an SQL function to access its current value
346** from within an SQL statement. This program used to use the
347** sqlite_exec_printf() API to substitue a string into an SQL statement.
348** The correct way to do this with sqlite3 is to use the bind API, but
349** since the shell is built around the callback paradigm it would be a lot
350** of work. Instead just use this hack, which is quite harmless.
351*/
352static const char *zShellStatic = 0;
353static void shellstaticFunc(
354 sqlite3_context *context,
355 int argc,
356 sqlite3_value **argv
357){
358 assert( 0==argc );
359 assert( zShellStatic );
shaned87897d2009-01-30 05:40:27 +0000360 UNUSED_PARAMETER(argc);
drh902b9ee2008-12-05 17:17:07 +0000361 UNUSED_PARAMETER(argv);
danielk1977bc6ada42004-06-30 08:20:16 +0000362 sqlite3_result_text(context, zShellStatic, -1, SQLITE_STATIC);
363}
364
365
366/*
drhfeac5f82004-08-01 00:10:45 +0000367** This routine reads a line of text from FILE in, stores
drh8e7e7a22000-05-30 18:45:23 +0000368** the text in memory obtained from malloc() and returns a pointer
369** to the text. NULL is returned at end of file, or if malloc()
370** fails.
371**
drh9f099fd2013-08-06 14:01:46 +0000372** If zLine is not NULL then it is a malloced buffer returned from
373** a previous call to this routine that may be reused.
drh8e7e7a22000-05-30 18:45:23 +0000374*/
drh9f099fd2013-08-06 14:01:46 +0000375static char *local_getline(char *zLine, FILE *in){
376 int nLine = zLine==0 ? 0 : 100;
377 int n = 0;
drh8e7e7a22000-05-30 18:45:23 +0000378
drhb07028f2011-10-14 21:49:18 +0000379 while( 1 ){
drh8e7e7a22000-05-30 18:45:23 +0000380 if( n+100>nLine ){
381 nLine = nLine*2 + 100;
382 zLine = realloc(zLine, nLine);
383 if( zLine==0 ) return 0;
384 }
drhdaffd0e2001-04-11 14:28:42 +0000385 if( fgets(&zLine[n], nLine - n, in)==0 ){
drh8e7e7a22000-05-30 18:45:23 +0000386 if( n==0 ){
387 free(zLine);
388 return 0;
389 }
390 zLine[n] = 0;
drh8e7e7a22000-05-30 18:45:23 +0000391 break;
392 }
drh9f099fd2013-08-06 14:01:46 +0000393 while( zLine[n] ) n++;
394 if( n>0 && zLine[n-1]=='\n' ){
drh8e7e7a22000-05-30 18:45:23 +0000395 n--;
shaneh13b36022009-12-17 21:07:15 +0000396 if( n>0 && zLine[n-1]=='\r' ) n--;
drh8e7e7a22000-05-30 18:45:23 +0000397 zLine[n] = 0;
drhb07028f2011-10-14 21:49:18 +0000398 break;
drh8e7e7a22000-05-30 18:45:23 +0000399 }
400 }
drh8e7e7a22000-05-30 18:45:23 +0000401 return zLine;
402}
403
404/*
drhc28490c2006-10-26 14:25:58 +0000405** Retrieve a single line of input text.
drh8e7e7a22000-05-30 18:45:23 +0000406**
drh9f099fd2013-08-06 14:01:46 +0000407** If in==0 then read from standard input and prompt before each line.
408** If isContinuation is true, then a continuation prompt is appropriate.
409** If isContinuation is zero, then the main prompt should be used.
410**
411** If zPrior is not NULL then it is a buffer from a prior call to this
412** routine that can be reused.
413**
414** The result is stored in space obtained from malloc() and must either
415** be freed by the caller or else passed back into this routine via the
416** zPrior argument for reuse.
drh8e7e7a22000-05-30 18:45:23 +0000417*/
drh9f099fd2013-08-06 14:01:46 +0000418static char *one_input_line(FILE *in, char *zPrior, int isContinuation){
drh8e7e7a22000-05-30 18:45:23 +0000419 char *zPrompt;
420 char *zResult;
drhdaffd0e2001-04-11 14:28:42 +0000421 if( in!=0 ){
drh9f099fd2013-08-06 14:01:46 +0000422 zResult = local_getline(zPrior, in);
drh8e7e7a22000-05-30 18:45:23 +0000423 }else{
drh9f099fd2013-08-06 14:01:46 +0000424 zPrompt = isContinuation ? continuePrompt : mainPrompt;
drhaaa21b42014-02-11 14:37:51 +0000425#if defined(HAVE_READLINE)
drh9f099fd2013-08-06 14:01:46 +0000426 free(zPrior);
427 zResult = readline(zPrompt);
428 if( zResult && *zResult ) add_history(zResult);
429#else
430 printf("%s", zPrompt);
431 fflush(stdout);
432 zResult = local_getline(zPrior, stdin);
danielk19774af00c62005-01-23 23:43:21 +0000433#endif
drh9f099fd2013-08-06 14:01:46 +0000434 }
drh8e7e7a22000-05-30 18:45:23 +0000435 return zResult;
436}
437
drhdcd87a92014-08-18 13:45:42 +0000438/*
439** Shell output mode information from before ".explain on",
440** saved so that it can be restored by ".explain off"
441*/
442typedef struct SavedModeInfo SavedModeInfo;
443struct SavedModeInfo {
444 int valid; /* Is there legit data in here? */
445 int mode; /* Mode prior to ".explain on" */
446 int showHeader; /* The ".header" setting prior to ".explain on" */
447 int colWidth[100]; /* Column widths prior to ".explain on" */
persicom7e2dfdd2002-04-18 02:46:52 +0000448};
drh45e29d82006-11-20 16:21:10 +0000449
drh8e7e7a22000-05-30 18:45:23 +0000450/*
drhdcd87a92014-08-18 13:45:42 +0000451** State information about the database connection is contained in an
452** instance of the following structure.
drh75897232000-05-29 14:26:00 +0000453*/
drhdcd87a92014-08-18 13:45:42 +0000454typedef struct ShellState ShellState;
455struct ShellState {
shane626a6e42009-10-22 17:30:15 +0000456 sqlite3 *db; /* The database */
drhdaffd0e2001-04-11 14:28:42 +0000457 int echoOn; /* True to echo input commands */
drhc2ce0be2014-05-29 12:36:14 +0000458 int autoEQP; /* Run EXPLAIN QUERY PLAN prior to seach SQL stmt */
shaneh642d8b82010-07-28 16:05:34 +0000459 int statsOn; /* True to display memory stats before each finalize */
drhc2ce0be2014-05-29 12:36:14 +0000460 int outCount; /* Revert to stdout when reaching zero */
drh28bd4bc2000-06-15 15:57:22 +0000461 int cnt; /* Number of records displayed so far */
462 FILE *out; /* Write results here */
drh42f64e52012-04-04 16:56:23 +0000463 FILE *traceOut; /* Output for sqlite3_trace() */
drh2f464a02011-10-13 00:41:49 +0000464 int nErr; /* Number of errors seen */
drh28bd4bc2000-06-15 15:57:22 +0000465 int mode; /* An output mode setting */
drh45e29d82006-11-20 16:21:10 +0000466 int writableSchema; /* True if PRAGMA writable_schema=ON */
drh28bd4bc2000-06-15 15:57:22 +0000467 int showHeader; /* True to show column names in List or Column mode */
drh44dec872014-08-30 15:49:25 +0000468 unsigned shellFlgs; /* Various flags */
drh33048c02001-10-01 14:29:22 +0000469 char *zDestTable; /* Name of destination table when MODE_Insert */
drh28bd4bc2000-06-15 15:57:22 +0000470 char separator[20]; /* Separator character for MODE_List */
drh6976c212014-07-24 12:09:47 +0000471 char newline[20]; /* Record separator in MODE_Csv */
drha0c66f52000-07-29 13:20:21 +0000472 int colWidth[100]; /* Requested width of each column when in column mode*/
473 int actualWidth[100]; /* Actual width of each column */
drh83965662003-04-17 02:54:13 +0000474 char nullvalue[20]; /* The text to print when a NULL comes back from
475 ** the database */
drhdcd87a92014-08-18 13:45:42 +0000476 SavedModeInfo normalMode;/* Holds the mode just before .explain ON */
drh44c2eb12003-04-30 11:38:26 +0000477 char outfile[FILENAME_MAX]; /* Filename for *out */
478 const char *zDbFilename; /* name of the database file */
drh05782482013-10-24 15:20:20 +0000479 char *zFreeOnClose; /* Filename to free when closing */
drha7e61d82011-03-12 17:02:57 +0000480 const char *zVfs; /* Name of VFS to use */
shane626a6e42009-10-22 17:30:15 +0000481 sqlite3_stmt *pStmt; /* Current statement if any. */
drh127f9d72010-02-23 01:47:00 +0000482 FILE *pLog; /* Write log output here */
dana98bf362013-11-13 18:35:01 +0000483 int *aiIndent; /* Array of indents used in MODE_Explain */
484 int nIndent; /* Size of array aiIndent[] */
danc4650bb2013-11-18 08:41:06 +0000485 int iIndent; /* Index of current op in aiIndent[] */
drh75897232000-05-29 14:26:00 +0000486};
487
488/*
drh44dec872014-08-30 15:49:25 +0000489** These are the allowed shellFlgs values
490*/
491#define SHFLG_Scratch 0x00001 /* The --scratch option is used */
492#define SHFLG_Pagecache 0x00002 /* The --pagecache option is used */
493#define SHFLG_Lookaside 0x00004 /* Lookaside memory is used */
494
495/*
drh75897232000-05-29 14:26:00 +0000496** These are the allowed modes.
497*/
drh967e8b72000-06-21 13:59:10 +0000498#define MODE_Line 0 /* One column per line. Blank line between records */
drh75897232000-05-29 14:26:00 +0000499#define MODE_Column 1 /* One record per line in neat columns */
500#define MODE_List 2 /* One record per line with a separator */
drhe3710332000-09-29 13:30:53 +0000501#define MODE_Semi 3 /* Same as MODE_List but append ";" to each line */
502#define MODE_Html 4 /* Generate an XHTML table */
503#define MODE_Insert 5 /* Generate SQL "insert" statements */
drhfeac5f82004-08-01 00:10:45 +0000504#define MODE_Tcl 6 /* Generate ANSI-C or TCL quoted elements */
drh8e64d1c2004-10-07 00:32:39 +0000505#define MODE_Csv 7 /* Quote strings, numbers are plain */
drh66ce4d02008-02-15 17:38:06 +0000506#define MODE_Explain 8 /* Like MODE_Column, but do not truncate data */
persicom7e2dfdd2002-04-18 02:46:52 +0000507
drh66ce4d02008-02-15 17:38:06 +0000508static const char *modeDescr[] = {
persicom7e2dfdd2002-04-18 02:46:52 +0000509 "line",
510 "column",
511 "list",
512 "semi",
513 "html",
drhfeac5f82004-08-01 00:10:45 +0000514 "insert",
515 "tcl",
drh8e64d1c2004-10-07 00:32:39 +0000516 "csv",
drh66ce4d02008-02-15 17:38:06 +0000517 "explain",
persicom7e2dfdd2002-04-18 02:46:52 +0000518};
drh75897232000-05-29 14:26:00 +0000519
520/*
521** Number of elements in an array
522*/
drh902b9ee2008-12-05 17:17:07 +0000523#define ArraySize(X) (int)(sizeof(X)/sizeof(X[0]))
drh75897232000-05-29 14:26:00 +0000524
525/*
drhea678832008-12-10 19:26:22 +0000526** Compute a string length that is limited to what can be stored in
527** lower 30 bits of a 32-bit signed integer.
528*/
drh4f21c4a2008-12-10 22:15:00 +0000529static int strlen30(const char *z){
drhea678832008-12-10 19:26:22 +0000530 const char *z2 = z;
531 while( *z2 ){ z2++; }
532 return 0x3fffffff & (int)(z2 - z);
533}
534
535/*
drh127f9d72010-02-23 01:47:00 +0000536** A callback for the sqlite3_log() interface.
537*/
538static void shellLog(void *pArg, int iErrCode, const char *zMsg){
drhdcd87a92014-08-18 13:45:42 +0000539 ShellState *p = (ShellState*)pArg;
drh127f9d72010-02-23 01:47:00 +0000540 if( p->pLog==0 ) return;
541 fprintf(p->pLog, "(%d) %s\n", iErrCode, zMsg);
542 fflush(p->pLog);
543}
544
545/*
shane626a6e42009-10-22 17:30:15 +0000546** Output the given string as a hex-encoded blob (eg. X'1234' )
547*/
548static void output_hex_blob(FILE *out, const void *pBlob, int nBlob){
549 int i;
550 char *zBlob = (char *)pBlob;
551 fprintf(out,"X'");
drhb202d702012-04-24 12:12:57 +0000552 for(i=0; i<nBlob; i++){ fprintf(out,"%02x",zBlob[i]&0xff); }
shane626a6e42009-10-22 17:30:15 +0000553 fprintf(out,"'");
554}
555
556/*
drh28bd4bc2000-06-15 15:57:22 +0000557** Output the given string as a quoted string using SQL quoting conventions.
558*/
559static void output_quoted_string(FILE *out, const char *z){
560 int i;
561 int nSingle = 0;
drh28bd4bc2000-06-15 15:57:22 +0000562 for(i=0; z[i]; i++){
563 if( z[i]=='\'' ) nSingle++;
drh28bd4bc2000-06-15 15:57:22 +0000564 }
565 if( nSingle==0 ){
566 fprintf(out,"'%s'",z);
drh28bd4bc2000-06-15 15:57:22 +0000567 }else{
568 fprintf(out,"'");
569 while( *z ){
570 for(i=0; z[i] && z[i]!='\''; i++){}
571 if( i==0 ){
572 fprintf(out,"''");
573 z++;
574 }else if( z[i]=='\'' ){
575 fprintf(out,"%.*s''",i,z);
576 z += i+1;
577 }else{
drhcd7d2732002-02-26 23:24:26 +0000578 fprintf(out,"%s",z);
drh28bd4bc2000-06-15 15:57:22 +0000579 break;
580 }
581 }
drhcd7d2732002-02-26 23:24:26 +0000582 fprintf(out,"'");
drh28bd4bc2000-06-15 15:57:22 +0000583 }
584}
585
586/*
drhfeac5f82004-08-01 00:10:45 +0000587** Output the given string as a quoted according to C or TCL quoting rules.
588*/
589static void output_c_string(FILE *out, const char *z){
590 unsigned int c;
591 fputc('"', out);
592 while( (c = *(z++))!=0 ){
593 if( c=='\\' ){
594 fputc(c, out);
595 fputc(c, out);
mistachkin585dcb22012-12-04 00:23:43 +0000596 }else if( c=='"' ){
597 fputc('\\', out);
598 fputc('"', out);
drhfeac5f82004-08-01 00:10:45 +0000599 }else if( c=='\t' ){
600 fputc('\\', out);
601 fputc('t', out);
602 }else if( c=='\n' ){
603 fputc('\\', out);
604 fputc('n', out);
605 }else if( c=='\r' ){
606 fputc('\\', out);
607 fputc('r', out);
mistachkinf6418892013-08-28 01:54:12 +0000608 }else if( !isprint(c&0xff) ){
drh0a8640d2005-08-30 20:12:02 +0000609 fprintf(out, "\\%03o", c&0xff);
drhfeac5f82004-08-01 00:10:45 +0000610 }else{
611 fputc(c, out);
612 }
613 }
614 fputc('"', out);
615}
616
617/*
drhc08a4f12000-06-15 16:49:48 +0000618** Output the given string with characters that are special to
619** HTML escaped.
620*/
621static void output_html_string(FILE *out, const char *z){
622 int i;
drhc3d6ba42014-01-13 20:38:35 +0000623 if( z==0 ) z = "";
drhc08a4f12000-06-15 16:49:48 +0000624 while( *z ){
shane43d9cb22009-10-21 14:11:48 +0000625 for(i=0; z[i]
626 && z[i]!='<'
627 && z[i]!='&'
628 && z[i]!='>'
629 && z[i]!='\"'
630 && z[i]!='\'';
631 i++){}
drhc08a4f12000-06-15 16:49:48 +0000632 if( i>0 ){
633 fprintf(out,"%.*s",i,z);
634 }
635 if( z[i]=='<' ){
636 fprintf(out,"&lt;");
637 }else if( z[i]=='&' ){
638 fprintf(out,"&amp;");
shane43d9cb22009-10-21 14:11:48 +0000639 }else if( z[i]=='>' ){
640 fprintf(out,"&gt;");
641 }else if( z[i]=='\"' ){
642 fprintf(out,"&quot;");
643 }else if( z[i]=='\'' ){
644 fprintf(out,"&#39;");
drhc08a4f12000-06-15 16:49:48 +0000645 }else{
646 break;
647 }
648 z += i + 1;
649 }
650}
651
652/*
drhc49f44e2006-10-26 18:15:42 +0000653** If a field contains any character identified by a 1 in the following
654** array, then the string must be quoted for CSV.
655*/
656static const char needCsvQuote[] = {
657 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
658 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
659 1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0,
660 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
661 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
662 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
663 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
664 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1,
665 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
666 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
667 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
668 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
669 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
670 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
671 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
672 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
673};
674
675/*
drh8e64d1c2004-10-07 00:32:39 +0000676** Output a single term of CSV. Actually, p->separator is used for
677** the separator, which may or may not be a comma. p->nullvalue is
drh6976c212014-07-24 12:09:47 +0000678** the null value. Strings are quoted if necessary. The separator
679** is only issued if bSep is true.
drh8e64d1c2004-10-07 00:32:39 +0000680*/
drhdcd87a92014-08-18 13:45:42 +0000681static void output_csv(ShellState *p, const char *z, int bSep){
drhc49f44e2006-10-26 18:15:42 +0000682 FILE *out = p->out;
drh8e64d1c2004-10-07 00:32:39 +0000683 if( z==0 ){
drhc49f44e2006-10-26 18:15:42 +0000684 fprintf(out,"%s",p->nullvalue);
drh8e64d1c2004-10-07 00:32:39 +0000685 }else{
drhc49f44e2006-10-26 18:15:42 +0000686 int i;
drh4f21c4a2008-12-10 22:15:00 +0000687 int nSep = strlen30(p->separator);
drhc49f44e2006-10-26 18:15:42 +0000688 for(i=0; z[i]; i++){
drhc85375d2007-12-18 15:41:44 +0000689 if( needCsvQuote[((unsigned char*)z)[i]]
690 || (z[i]==p->separator[0] &&
691 (nSep==1 || memcmp(z, p->separator, nSep)==0)) ){
drhc49f44e2006-10-26 18:15:42 +0000692 i = 0;
693 break;
694 }
695 }
696 if( i==0 ){
697 putc('"', out);
698 for(i=0; z[i]; i++){
699 if( z[i]=='"' ) putc('"', out);
700 putc(z[i], out);
701 }
702 putc('"', out);
703 }else{
704 fprintf(out, "%s", z);
705 }
drh8e64d1c2004-10-07 00:32:39 +0000706 }
707 if( bSep ){
drhd0e77882008-01-14 15:20:08 +0000708 fprintf(p->out, "%s", p->separator);
drh8e64d1c2004-10-07 00:32:39 +0000709 }
710}
711
danielk19774af00c62005-01-23 23:43:21 +0000712#ifdef SIGINT
drh8e64d1c2004-10-07 00:32:39 +0000713/*
drh4c504392000-10-16 22:06:40 +0000714** This routine runs when the user presses Ctrl-C
715*/
716static void interrupt_handler(int NotUsed){
drh902b9ee2008-12-05 17:17:07 +0000717 UNUSED_PARAMETER(NotUsed);
drh43ae8f62014-05-23 12:03:47 +0000718 seenInterrupt++;
719 if( seenInterrupt>2 ) exit(1);
danielk19776f8a5032004-05-10 10:34:51 +0000720 if( db ) sqlite3_interrupt(db);
drh4c504392000-10-16 22:06:40 +0000721}
danielk19774af00c62005-01-23 23:43:21 +0000722#endif
drh4c504392000-10-16 22:06:40 +0000723
724/*
shane626a6e42009-10-22 17:30:15 +0000725** This is the callback routine that the shell
drh75897232000-05-29 14:26:00 +0000726** invokes for each row of a query result.
727*/
shane626a6e42009-10-22 17:30:15 +0000728static int shell_callback(void *pArg, int nArg, char **azArg, char **azCol, int *aiType){
drh75897232000-05-29 14:26:00 +0000729 int i;
drhdcd87a92014-08-18 13:45:42 +0000730 ShellState *p = (ShellState*)pArg;
shaneb9fc17d2009-10-22 21:23:35 +0000731
drh75897232000-05-29 14:26:00 +0000732 switch( p->mode ){
733 case MODE_Line: {
drhe3710332000-09-29 13:30:53 +0000734 int w = 5;
drh6a535342001-10-19 16:44:56 +0000735 if( azArg==0 ) break;
drhe3710332000-09-29 13:30:53 +0000736 for(i=0; i<nArg; i++){
drh4f21c4a2008-12-10 22:15:00 +0000737 int len = strlen30(azCol[i] ? azCol[i] : "");
drhe3710332000-09-29 13:30:53 +0000738 if( len>w ) w = len;
739 }
drh75897232000-05-29 14:26:00 +0000740 if( p->cnt++>0 ) fprintf(p->out,"\n");
741 for(i=0; i<nArg; i++){
drh2cc55692006-06-27 20:39:04 +0000742 fprintf(p->out,"%*s = %s\n", w, azCol[i],
drha69d9162003-04-17 22:57:53 +0000743 azArg[i] ? azArg[i] : p->nullvalue);
drh75897232000-05-29 14:26:00 +0000744 }
745 break;
746 }
danielk19770d78bae2008-01-03 07:09:48 +0000747 case MODE_Explain:
drh75897232000-05-29 14:26:00 +0000748 case MODE_Column: {
drha0c66f52000-07-29 13:20:21 +0000749 if( p->cnt++==0 ){
drh75897232000-05-29 14:26:00 +0000750 for(i=0; i<nArg; i++){
drha0c66f52000-07-29 13:20:21 +0000751 int w, n;
752 if( i<ArraySize(p->colWidth) ){
danielk19770d78bae2008-01-03 07:09:48 +0000753 w = p->colWidth[i];
drh75897232000-05-29 14:26:00 +0000754 }else{
danielk19770d78bae2008-01-03 07:09:48 +0000755 w = 0;
drh75897232000-05-29 14:26:00 +0000756 }
drh078b1fd2012-09-21 13:40:02 +0000757 if( w==0 ){
drh4f21c4a2008-12-10 22:15:00 +0000758 w = strlen30(azCol[i] ? azCol[i] : "");
drha0c66f52000-07-29 13:20:21 +0000759 if( w<10 ) w = 10;
drh4f21c4a2008-12-10 22:15:00 +0000760 n = strlen30(azArg && azArg[i] ? azArg[i] : p->nullvalue);
drha0c66f52000-07-29 13:20:21 +0000761 if( w<n ) w = n;
762 }
763 if( i<ArraySize(p->actualWidth) ){
persicom1d0b8722002-04-18 02:53:04 +0000764 p->actualWidth[i] = w;
drha0c66f52000-07-29 13:20:21 +0000765 }
766 if( p->showHeader ){
drh078b1fd2012-09-21 13:40:02 +0000767 if( w<0 ){
768 fprintf(p->out,"%*.*s%s",-w,-w,azCol[i], i==nArg-1 ? "\n": " ");
769 }else{
770 fprintf(p->out,"%-*.*s%s",w,w,azCol[i], i==nArg-1 ? "\n": " ");
771 }
drha0c66f52000-07-29 13:20:21 +0000772 }
773 }
774 if( p->showHeader ){
775 for(i=0; i<nArg; i++){
776 int w;
777 if( i<ArraySize(p->actualWidth) ){
778 w = p->actualWidth[i];
drh078b1fd2012-09-21 13:40:02 +0000779 if( w<0 ) w = -w;
drha0c66f52000-07-29 13:20:21 +0000780 }else{
781 w = 10;
782 }
783 fprintf(p->out,"%-*.*s%s",w,w,"-----------------------------------"
784 "----------------------------------------------------------",
785 i==nArg-1 ? "\n": " ");
786 }
drh75897232000-05-29 14:26:00 +0000787 }
788 }
drh6a535342001-10-19 16:44:56 +0000789 if( azArg==0 ) break;
drh75897232000-05-29 14:26:00 +0000790 for(i=0; i<nArg; i++){
791 int w;
drha0c66f52000-07-29 13:20:21 +0000792 if( i<ArraySize(p->actualWidth) ){
793 w = p->actualWidth[i];
drh75897232000-05-29 14:26:00 +0000794 }else{
795 w = 10;
796 }
dana98bf362013-11-13 18:35:01 +0000797 if( p->mode==MODE_Explain && azArg[i] && strlen30(azArg[i])>w ){
drh4f21c4a2008-12-10 22:15:00 +0000798 w = strlen30(azArg[i]);
danielk19770d78bae2008-01-03 07:09:48 +0000799 }
dana98bf362013-11-13 18:35:01 +0000800 if( i==1 && p->aiIndent && p->pStmt ){
danc4650bb2013-11-18 08:41:06 +0000801 if( p->iIndent<p->nIndent ){
802 fprintf(p->out, "%*.s", p->aiIndent[p->iIndent], "");
dana98bf362013-11-13 18:35:01 +0000803 }
danc4650bb2013-11-18 08:41:06 +0000804 p->iIndent++;
dana98bf362013-11-13 18:35:01 +0000805 }
drh078b1fd2012-09-21 13:40:02 +0000806 if( w<0 ){
807 fprintf(p->out,"%*.*s%s",-w,-w,
808 azArg[i] ? azArg[i] : p->nullvalue, i==nArg-1 ? "\n": " ");
809 }else{
810 fprintf(p->out,"%-*.*s%s",w,w,
811 azArg[i] ? azArg[i] : p->nullvalue, i==nArg-1 ? "\n": " ");
812 }
drh75897232000-05-29 14:26:00 +0000813 }
814 break;
815 }
drhe3710332000-09-29 13:30:53 +0000816 case MODE_Semi:
drh75897232000-05-29 14:26:00 +0000817 case MODE_List: {
818 if( p->cnt++==0 && p->showHeader ){
819 for(i=0; i<nArg; i++){
820 fprintf(p->out,"%s%s",azCol[i], i==nArg-1 ? "\n" : p->separator);
821 }
822 }
drh6a535342001-10-19 16:44:56 +0000823 if( azArg==0 ) break;
drh75897232000-05-29 14:26:00 +0000824 for(i=0; i<nArg; i++){
drh4c653a02000-06-07 01:27:47 +0000825 char *z = azArg[i];
persicom7e2dfdd2002-04-18 02:46:52 +0000826 if( z==0 ) z = p->nullvalue;
drh71172c52002-01-24 00:00:21 +0000827 fprintf(p->out, "%s", z);
drhe3710332000-09-29 13:30:53 +0000828 if( i<nArg-1 ){
829 fprintf(p->out, "%s", p->separator);
830 }else if( p->mode==MODE_Semi ){
831 fprintf(p->out, ";\n");
832 }else{
833 fprintf(p->out, "\n");
834 }
drh75897232000-05-29 14:26:00 +0000835 }
836 break;
837 }
drh1e5d0e92000-05-31 23:33:17 +0000838 case MODE_Html: {
839 if( p->cnt++==0 && p->showHeader ){
mihailim57c591a2008-06-23 21:26:05 +0000840 fprintf(p->out,"<TR>");
drh1e5d0e92000-05-31 23:33:17 +0000841 for(i=0; i<nArg; i++){
shane43d9cb22009-10-21 14:11:48 +0000842 fprintf(p->out,"<TH>");
843 output_html_string(p->out, azCol[i]);
844 fprintf(p->out,"</TH>\n");
drh1e5d0e92000-05-31 23:33:17 +0000845 }
mihailim57c591a2008-06-23 21:26:05 +0000846 fprintf(p->out,"</TR>\n");
drh1e5d0e92000-05-31 23:33:17 +0000847 }
drh6a535342001-10-19 16:44:56 +0000848 if( azArg==0 ) break;
mihailim57c591a2008-06-23 21:26:05 +0000849 fprintf(p->out,"<TR>");
drh1e5d0e92000-05-31 23:33:17 +0000850 for(i=0; i<nArg; i++){
mihailim57c591a2008-06-23 21:26:05 +0000851 fprintf(p->out,"<TD>");
persicom7e2dfdd2002-04-18 02:46:52 +0000852 output_html_string(p->out, azArg[i] ? azArg[i] : p->nullvalue);
mihailim57c591a2008-06-23 21:26:05 +0000853 fprintf(p->out,"</TD>\n");
drh1e5d0e92000-05-31 23:33:17 +0000854 }
mihailim57c591a2008-06-23 21:26:05 +0000855 fprintf(p->out,"</TR>\n");
drh1e5d0e92000-05-31 23:33:17 +0000856 break;
857 }
drhfeac5f82004-08-01 00:10:45 +0000858 case MODE_Tcl: {
859 if( p->cnt++==0 && p->showHeader ){
860 for(i=0; i<nArg; i++){
drh2cc55692006-06-27 20:39:04 +0000861 output_c_string(p->out,azCol[i] ? azCol[i] : "");
mistachkin585dcb22012-12-04 00:23:43 +0000862 if(i<nArg-1) fprintf(p->out, "%s", p->separator);
drhfeac5f82004-08-01 00:10:45 +0000863 }
864 fprintf(p->out,"\n");
865 }
866 if( azArg==0 ) break;
867 for(i=0; i<nArg; i++){
868 output_c_string(p->out, azArg[i] ? azArg[i] : p->nullvalue);
mistachkin585dcb22012-12-04 00:23:43 +0000869 if(i<nArg-1) fprintf(p->out, "%s", p->separator);
drhfeac5f82004-08-01 00:10:45 +0000870 }
871 fprintf(p->out,"\n");
872 break;
873 }
drh8e64d1c2004-10-07 00:32:39 +0000874 case MODE_Csv: {
drh6976c212014-07-24 12:09:47 +0000875#if defined(WIN32) || defined(_WIN32)
876 fflush(p->out);
877 _setmode(_fileno(p->out), _O_BINARY);
878#endif
drh8e64d1c2004-10-07 00:32:39 +0000879 if( p->cnt++==0 && p->showHeader ){
880 for(i=0; i<nArg; i++){
drh2cc55692006-06-27 20:39:04 +0000881 output_csv(p, azCol[i] ? azCol[i] : "", i<nArg-1);
drh8e64d1c2004-10-07 00:32:39 +0000882 }
drh6976c212014-07-24 12:09:47 +0000883 fprintf(p->out,"%s",p->newline);
drh8e64d1c2004-10-07 00:32:39 +0000884 }
drh6976c212014-07-24 12:09:47 +0000885 if( azArg>0 ){
886 for(i=0; i<nArg; i++){
887 output_csv(p, azArg[i], i<nArg-1);
888 }
889 fprintf(p->out,"%s",p->newline);
drh8e64d1c2004-10-07 00:32:39 +0000890 }
drh6976c212014-07-24 12:09:47 +0000891#if defined(WIN32) || defined(_WIN32)
892 fflush(p->out);
893 _setmode(_fileno(p->out), _O_TEXT);
894#endif
drh8e64d1c2004-10-07 00:32:39 +0000895 break;
896 }
drh28bd4bc2000-06-15 15:57:22 +0000897 case MODE_Insert: {
shaneb9fc17d2009-10-22 21:23:35 +0000898 p->cnt++;
drh6a535342001-10-19 16:44:56 +0000899 if( azArg==0 ) break;
drh33048c02001-10-01 14:29:22 +0000900 fprintf(p->out,"INSERT INTO %s VALUES(",p->zDestTable);
drh28bd4bc2000-06-15 15:57:22 +0000901 for(i=0; i<nArg; i++){
902 char *zSep = i>0 ? ",": "";
shanead6b8d02009-10-22 18:12:58 +0000903 if( (azArg[i]==0) || (aiType && aiType[i]==SQLITE_NULL) ){
drh28bd4bc2000-06-15 15:57:22 +0000904 fprintf(p->out,"%sNULL",zSep);
shanead6b8d02009-10-22 18:12:58 +0000905 }else if( aiType && aiType[i]==SQLITE_TEXT ){
906 if( zSep[0] ) fprintf(p->out,"%s",zSep);
907 output_quoted_string(p->out, azArg[i]);
drhc2ce0be2014-05-29 12:36:14 +0000908 }else if( aiType && (aiType[i]==SQLITE_INTEGER
909 || aiType[i]==SQLITE_FLOAT) ){
shanead6b8d02009-10-22 18:12:58 +0000910 fprintf(p->out,"%s%s",zSep, azArg[i]);
shane626a6e42009-10-22 17:30:15 +0000911 }else if( aiType && aiType[i]==SQLITE_BLOB && p->pStmt ){
912 const void *pBlob = sqlite3_column_blob(p->pStmt, i);
913 int nBlob = sqlite3_column_bytes(p->pStmt, i);
914 if( zSep[0] ) fprintf(p->out,"%s",zSep);
915 output_hex_blob(p->out, pBlob, nBlob);
drhc8d74412004-08-31 23:41:26 +0000916 }else if( isNumber(azArg[i], 0) ){
drh28bd4bc2000-06-15 15:57:22 +0000917 fprintf(p->out,"%s%s",zSep, azArg[i]);
918 }else{
919 if( zSep[0] ) fprintf(p->out,"%s",zSep);
920 output_quoted_string(p->out, azArg[i]);
921 }
922 }
923 fprintf(p->out,");\n");
drh6a535342001-10-19 16:44:56 +0000924 break;
drh28bd4bc2000-06-15 15:57:22 +0000925 }
persicom1d0b8722002-04-18 02:53:04 +0000926 }
drh75897232000-05-29 14:26:00 +0000927 return 0;
928}
929
930/*
shane626a6e42009-10-22 17:30:15 +0000931** This is the callback routine that the SQLite library
932** invokes for each row of a query result.
933*/
934static int callback(void *pArg, int nArg, char **azArg, char **azCol){
935 /* since we don't have type info, call the shell_callback with a NULL value */
936 return shell_callback(pArg, nArg, azArg, azCol, NULL);
937}
938
939/*
drhdcd87a92014-08-18 13:45:42 +0000940** Set the destination table field of the ShellState structure to
drh33048c02001-10-01 14:29:22 +0000941** the name of the table given. Escape any quote characters in the
942** table name.
943*/
drhdcd87a92014-08-18 13:45:42 +0000944static void set_table_name(ShellState *p, const char *zName){
drh33048c02001-10-01 14:29:22 +0000945 int i, n;
946 int needQuote;
947 char *z;
948
949 if( p->zDestTable ){
950 free(p->zDestTable);
951 p->zDestTable = 0;
952 }
953 if( zName==0 ) return;
drh4c755c02004-08-08 20:22:17 +0000954 needQuote = !isalpha((unsigned char)*zName) && *zName!='_';
drh33048c02001-10-01 14:29:22 +0000955 for(i=n=0; zName[i]; i++, n++){
drh4c755c02004-08-08 20:22:17 +0000956 if( !isalnum((unsigned char)zName[i]) && zName[i]!='_' ){
drh33048c02001-10-01 14:29:22 +0000957 needQuote = 1;
958 if( zName[i]=='\'' ) n++;
959 }
960 }
961 if( needQuote ) n += 2;
962 z = p->zDestTable = malloc( n+1 );
963 if( z==0 ){
shane86f5bdb2009-10-24 02:00:07 +0000964 fprintf(stderr,"Error: out of memory\n");
drh33048c02001-10-01 14:29:22 +0000965 exit(1);
966 }
967 n = 0;
968 if( needQuote ) z[n++] = '\'';
969 for(i=0; zName[i]; i++){
970 z[n++] = zName[i];
971 if( zName[i]=='\'' ) z[n++] = '\'';
972 }
973 if( needQuote ) z[n++] = '\'';
974 z[n] = 0;
975}
976
danielk19772a02e332004-06-05 08:04:36 +0000977/* zIn is either a pointer to a NULL-terminated string in memory obtained
978** from malloc(), or a NULL pointer. The string pointed to by zAppend is
979** added to zIn, and the result returned in memory obtained from malloc().
980** zIn, if it was not NULL, is freed.
981**
982** If the third argument, quote, is not '\0', then it is used as a
983** quote character for zAppend.
984*/
drhc28490c2006-10-26 14:25:58 +0000985static char *appendText(char *zIn, char const *zAppend, char quote){
danielk19772a02e332004-06-05 08:04:36 +0000986 int len;
987 int i;
drh4f21c4a2008-12-10 22:15:00 +0000988 int nAppend = strlen30(zAppend);
989 int nIn = (zIn?strlen30(zIn):0);
danielk19772a02e332004-06-05 08:04:36 +0000990
991 len = nAppend+nIn+1;
992 if( quote ){
993 len += 2;
994 for(i=0; i<nAppend; i++){
995 if( zAppend[i]==quote ) len++;
996 }
997 }
998
999 zIn = (char *)realloc(zIn, len);
1000 if( !zIn ){
1001 return 0;
1002 }
1003
1004 if( quote ){
1005 char *zCsr = &zIn[nIn];
1006 *zCsr++ = quote;
1007 for(i=0; i<nAppend; i++){
1008 *zCsr++ = zAppend[i];
1009 if( zAppend[i]==quote ) *zCsr++ = quote;
1010 }
1011 *zCsr++ = quote;
1012 *zCsr++ = '\0';
1013 assert( (zCsr-zIn)==len );
1014 }else{
1015 memcpy(&zIn[nIn], zAppend, nAppend);
1016 zIn[len-1] = '\0';
1017 }
1018
1019 return zIn;
1020}
1021
drhdd3d4592004-08-30 01:54:05 +00001022
1023/*
drhb21a8e42012-01-28 21:08:51 +00001024** Execute a query statement that will generate SQL output. Print
1025** the result columns, comma-separated, on a line and then add a
1026** semicolon terminator to the end of that line.
drh45e29d82006-11-20 16:21:10 +00001027**
drhb21a8e42012-01-28 21:08:51 +00001028** If the number of columns is 1 and that column contains text "--"
1029** then write the semicolon on a separate line. That way, if a
1030** "--" comment occurs at the end of the statement, the comment
1031** won't consume the semicolon terminator.
drhdd3d4592004-08-30 01:54:05 +00001032*/
drh157e29a2009-05-21 15:15:00 +00001033static int run_table_dump_query(
drhdcd87a92014-08-18 13:45:42 +00001034 ShellState *p, /* Query context */
drh2f464a02011-10-13 00:41:49 +00001035 const char *zSelect, /* SELECT statement to extract content */
1036 const char *zFirstRow /* Print before first row, if not NULL */
drh157e29a2009-05-21 15:15:00 +00001037){
drhdd3d4592004-08-30 01:54:05 +00001038 sqlite3_stmt *pSelect;
1039 int rc;
drhb21a8e42012-01-28 21:08:51 +00001040 int nResult;
1041 int i;
1042 const char *z;
drhc7181902014-02-27 15:04:13 +00001043 rc = sqlite3_prepare_v2(p->db, zSelect, -1, &pSelect, 0);
drhdd3d4592004-08-30 01:54:05 +00001044 if( rc!=SQLITE_OK || !pSelect ){
drh2f464a02011-10-13 00:41:49 +00001045 fprintf(p->out, "/**** ERROR: (%d) %s *****/\n", rc, sqlite3_errmsg(p->db));
drh4384e982013-10-01 15:30:05 +00001046 if( (rc&0xff)!=SQLITE_CORRUPT ) p->nErr++;
drhdd3d4592004-08-30 01:54:05 +00001047 return rc;
1048 }
1049 rc = sqlite3_step(pSelect);
drhb21a8e42012-01-28 21:08:51 +00001050 nResult = sqlite3_column_count(pSelect);
drhdd3d4592004-08-30 01:54:05 +00001051 while( rc==SQLITE_ROW ){
drh157e29a2009-05-21 15:15:00 +00001052 if( zFirstRow ){
drh2f464a02011-10-13 00:41:49 +00001053 fprintf(p->out, "%s", zFirstRow);
drh157e29a2009-05-21 15:15:00 +00001054 zFirstRow = 0;
1055 }
drhb21a8e42012-01-28 21:08:51 +00001056 z = (const char*)sqlite3_column_text(pSelect, 0);
1057 fprintf(p->out, "%s", z);
1058 for(i=1; i<nResult; i++){
1059 fprintf(p->out, ",%s", sqlite3_column_text(pSelect, i));
1060 }
1061 if( z==0 ) z = "";
1062 while( z[0] && (z[0]!='-' || z[1]!='-') ) z++;
1063 if( z[0] ){
1064 fprintf(p->out, "\n;\n");
1065 }else{
1066 fprintf(p->out, ";\n");
1067 }
drhdd3d4592004-08-30 01:54:05 +00001068 rc = sqlite3_step(pSelect);
1069 }
drh2f464a02011-10-13 00:41:49 +00001070 rc = sqlite3_finalize(pSelect);
1071 if( rc!=SQLITE_OK ){
1072 fprintf(p->out, "/**** ERROR: (%d) %s *****/\n", rc, sqlite3_errmsg(p->db));
drh4384e982013-10-01 15:30:05 +00001073 if( (rc&0xff)!=SQLITE_CORRUPT ) p->nErr++;
drh2f464a02011-10-13 00:41:49 +00001074 }
1075 return rc;
drhdd3d4592004-08-30 01:54:05 +00001076}
1077
shane626a6e42009-10-22 17:30:15 +00001078/*
1079** Allocate space and save off current error string.
1080*/
1081static char *save_err_msg(
1082 sqlite3 *db /* Database to query */
1083){
1084 int nErrMsg = 1+strlen30(sqlite3_errmsg(db));
1085 char *zErrMsg = sqlite3_malloc(nErrMsg);
1086 if( zErrMsg ){
1087 memcpy(zErrMsg, sqlite3_errmsg(db), nErrMsg);
1088 }
1089 return zErrMsg;
1090}
1091
1092/*
shaneh642d8b82010-07-28 16:05:34 +00001093** Display memory stats.
1094*/
1095static int display_stats(
1096 sqlite3 *db, /* Database to query */
drhdcd87a92014-08-18 13:45:42 +00001097 ShellState *pArg, /* Pointer to ShellState */
shaneh642d8b82010-07-28 16:05:34 +00001098 int bReset /* True to reset the stats */
1099){
1100 int iCur;
1101 int iHiwtr;
1102
1103 if( pArg && pArg->out ){
1104
1105 iHiwtr = iCur = -1;
1106 sqlite3_status(SQLITE_STATUS_MEMORY_USED, &iCur, &iHiwtr, bReset);
drh29dfbe32010-07-28 17:01:24 +00001107 fprintf(pArg->out, "Memory Used: %d (max %d) bytes\n", iCur, iHiwtr);
shaneh642d8b82010-07-28 16:05:34 +00001108 iHiwtr = iCur = -1;
1109 sqlite3_status(SQLITE_STATUS_MALLOC_COUNT, &iCur, &iHiwtr, bReset);
drh2a58e9c2010-12-21 21:28:38 +00001110 fprintf(pArg->out, "Number of Outstanding Allocations: %d (max %d)\n", iCur, iHiwtr);
drh44dec872014-08-30 15:49:25 +00001111 if( pArg->shellFlgs & SHFLG_Pagecache ){
1112 iHiwtr = iCur = -1;
1113 sqlite3_status(SQLITE_STATUS_PAGECACHE_USED, &iCur, &iHiwtr, bReset);
1114 fprintf(pArg->out, "Number of Pcache Pages Used: %d (max %d) pages\n", iCur, iHiwtr);
1115 }
shaneh642d8b82010-07-28 16:05:34 +00001116 iHiwtr = iCur = -1;
1117 sqlite3_status(SQLITE_STATUS_PAGECACHE_OVERFLOW, &iCur, &iHiwtr, bReset);
1118 fprintf(pArg->out, "Number of Pcache Overflow Bytes: %d (max %d) bytes\n", iCur, iHiwtr);
drh44dec872014-08-30 15:49:25 +00001119 if( pArg->shellFlgs & SHFLG_Scratch ){
1120 iHiwtr = iCur = -1;
1121 sqlite3_status(SQLITE_STATUS_SCRATCH_USED, &iCur, &iHiwtr, bReset);
1122 fprintf(pArg->out, "Number of Scratch Allocations Used: %d (max %d)\n", iCur, iHiwtr);
1123 }
shaneh642d8b82010-07-28 16:05:34 +00001124 iHiwtr = iCur = -1;
1125 sqlite3_status(SQLITE_STATUS_SCRATCH_OVERFLOW, &iCur, &iHiwtr, bReset);
1126 fprintf(pArg->out, "Number of Scratch Overflow Bytes: %d (max %d) bytes\n", iCur, iHiwtr);
1127 iHiwtr = iCur = -1;
1128 sqlite3_status(SQLITE_STATUS_MALLOC_SIZE, &iCur, &iHiwtr, bReset);
1129 fprintf(pArg->out, "Largest Allocation: %d bytes\n", iHiwtr);
1130 iHiwtr = iCur = -1;
1131 sqlite3_status(SQLITE_STATUS_PAGECACHE_SIZE, &iCur, &iHiwtr, bReset);
1132 fprintf(pArg->out, "Largest Pcache Allocation: %d bytes\n", iHiwtr);
1133 iHiwtr = iCur = -1;
1134 sqlite3_status(SQLITE_STATUS_SCRATCH_SIZE, &iCur, &iHiwtr, bReset);
1135 fprintf(pArg->out, "Largest Scratch Allocation: %d bytes\n", iHiwtr);
1136#ifdef YYTRACKMAXSTACKDEPTH
1137 iHiwtr = iCur = -1;
1138 sqlite3_status(SQLITE_STATUS_PARSER_STACK, &iCur, &iHiwtr, bReset);
1139 fprintf(pArg->out, "Deepest Parser Stack: %d (max %d)\n", iCur, iHiwtr);
1140#endif
1141 }
1142
1143 if( pArg && pArg->out && db ){
drh44dec872014-08-30 15:49:25 +00001144 if( pArg->shellFlgs & SHFLG_Lookaside ){
1145 iHiwtr = iCur = -1;
1146 sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_USED, &iCur, &iHiwtr, bReset);
1147 fprintf(pArg->out, "Lookaside Slots Used: %d (max %d)\n", iCur, iHiwtr);
1148 sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_HIT, &iCur, &iHiwtr, bReset);
1149 fprintf(pArg->out, "Successful lookaside attempts: %d\n", iHiwtr);
1150 sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_MISS_SIZE, &iCur, &iHiwtr, bReset);
1151 fprintf(pArg->out, "Lookaside failures due to size: %d\n", iHiwtr);
1152 sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_MISS_FULL, &iCur, &iHiwtr, bReset);
1153 fprintf(pArg->out, "Lookaside failures due to OOM: %d\n", iHiwtr);
1154 }
shaneh642d8b82010-07-28 16:05:34 +00001155 iHiwtr = iCur = -1;
1156 sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_USED, &iCur, &iHiwtr, bReset);
drhc78e6e42011-09-23 18:58:23 +00001157 fprintf(pArg->out, "Pager Heap Usage: %d bytes\n", iCur); iHiwtr = iCur = -1;
1158 sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_HIT, &iCur, &iHiwtr, 1);
1159 fprintf(pArg->out, "Page cache hits: %d\n", iCur);
1160 iHiwtr = iCur = -1;
1161 sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_MISS, &iCur, &iHiwtr, 1);
1162 fprintf(pArg->out, "Page cache misses: %d\n", iCur);
shaneh642d8b82010-07-28 16:05:34 +00001163 iHiwtr = iCur = -1;
drhfbbcd5d2012-03-24 20:09:33 +00001164 sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_WRITE, &iCur, &iHiwtr, 1);
1165 fprintf(pArg->out, "Page cache writes: %d\n", iCur);
1166 iHiwtr = iCur = -1;
shaneh642d8b82010-07-28 16:05:34 +00001167 sqlite3_db_status(db, SQLITE_DBSTATUS_SCHEMA_USED, &iCur, &iHiwtr, bReset);
1168 fprintf(pArg->out, "Schema Heap Usage: %d bytes\n", iCur);
1169 iHiwtr = iCur = -1;
1170 sqlite3_db_status(db, SQLITE_DBSTATUS_STMT_USED, &iCur, &iHiwtr, bReset);
1171 fprintf(pArg->out, "Statement Heap/Lookaside Usage: %d bytes\n", iCur);
1172 }
1173
1174 if( pArg && pArg->out && db && pArg->pStmt ){
1175 iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_FULLSCAN_STEP, bReset);
1176 fprintf(pArg->out, "Fullscan Steps: %d\n", iCur);
1177 iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_SORT, bReset);
1178 fprintf(pArg->out, "Sort Operations: %d\n", iCur);
1179 iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_AUTOINDEX, bReset);
1180 fprintf(pArg->out, "Autoindex Inserts: %d\n", iCur);
drhbf159fa2013-06-25 22:01:22 +00001181 iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_VM_STEP, bReset);
1182 fprintf(pArg->out, "Virtual Machine Steps: %d\n", iCur);
shaneh642d8b82010-07-28 16:05:34 +00001183 }
1184
1185 return 0;
1186}
1187
1188/*
dana98bf362013-11-13 18:35:01 +00001189** Parameter azArray points to a zero-terminated array of strings. zStr
1190** points to a single nul-terminated string. Return non-zero if zStr
1191** is equal, according to strcmp(), to any of the strings in the array.
1192** Otherwise, return zero.
1193*/
1194static int str_in_array(const char *zStr, const char **azArray){
1195 int i;
1196 for(i=0; azArray[i]; i++){
1197 if( 0==strcmp(zStr, azArray[i]) ) return 1;
1198 }
1199 return 0;
1200}
1201
1202/*
1203** If compiled statement pSql appears to be an EXPLAIN statement, allocate
drhdcd87a92014-08-18 13:45:42 +00001204** and populate the ShellState.aiIndent[] array with the number of
dana98bf362013-11-13 18:35:01 +00001205** spaces each opcode should be indented before it is output.
1206**
1207** The indenting rules are:
1208**
1209** * For each "Next", "Prev", "VNext" or "VPrev" instruction, indent
1210** all opcodes that occur between the p2 jump destination and the opcode
1211** itself by 2 spaces.
1212**
drh01752bc2013-11-14 23:59:33 +00001213** * For each "Goto", if the jump destination is earlier in the program
1214** and ends on one of:
drhe73f0592014-01-21 22:25:45 +00001215** Yield SeekGt SeekLt RowSetRead Rewind
drhfe705102014-03-06 13:38:37 +00001216** or if the P1 parameter is one instead of zero,
drh01752bc2013-11-14 23:59:33 +00001217** then indent all opcodes between the earlier instruction
drhd2447442013-11-13 19:01:41 +00001218** and "Goto" by 2 spaces.
dana98bf362013-11-13 18:35:01 +00001219*/
drhdcd87a92014-08-18 13:45:42 +00001220static void explain_data_prepare(ShellState *p, sqlite3_stmt *pSql){
dana98bf362013-11-13 18:35:01 +00001221 const char *zSql; /* The text of the SQL statement */
1222 const char *z; /* Used to check if this is an EXPLAIN */
1223 int *abYield = 0; /* True if op is an OP_Yield */
1224 int nAlloc = 0; /* Allocated size of p->aiIndent[], abYield */
danc4650bb2013-11-18 08:41:06 +00001225 int iOp; /* Index of operation in p->aiIndent[] */
dana98bf362013-11-13 18:35:01 +00001226
drh8ad0de32014-03-20 18:45:27 +00001227 const char *azNext[] = { "Next", "Prev", "VPrev", "VNext", "SorterNext",
1228 "NextIfOpen", "PrevIfOpen", 0 };
drhb463fef2014-05-29 20:17:57 +00001229 const char *azYield[] = { "Yield", "SeekLT", "SeekGT", "RowSetRead", "Rewind", 0 };
dana98bf362013-11-13 18:35:01 +00001230 const char *azGoto[] = { "Goto", 0 };
1231
1232 /* Try to figure out if this is really an EXPLAIN statement. If this
1233 ** cannot be verified, return early. */
1234 zSql = sqlite3_sql(pSql);
1235 if( zSql==0 ) return;
1236 for(z=zSql; *z==' ' || *z=='\t' || *z=='\n' || *z=='\f' || *z=='\r'; z++);
1237 if( sqlite3_strnicmp(z, "explain", 7) ) return;
1238
1239 for(iOp=0; SQLITE_ROW==sqlite3_step(pSql); iOp++){
1240 int i;
danc4650bb2013-11-18 08:41:06 +00001241 int iAddr = sqlite3_column_int(pSql, 0);
dana98bf362013-11-13 18:35:01 +00001242 const char *zOp = (const char*)sqlite3_column_text(pSql, 1);
danc4650bb2013-11-18 08:41:06 +00001243
1244 /* Set p2 to the P2 field of the current opcode. Then, assuming that
1245 ** p2 is an instruction address, set variable p2op to the index of that
1246 ** instruction in the aiIndent[] array. p2 and p2op may be different if
1247 ** the current instruction is part of a sub-program generated by an
1248 ** SQL trigger or foreign key. */
dana98bf362013-11-13 18:35:01 +00001249 int p2 = sqlite3_column_int(pSql, 3);
danc4650bb2013-11-18 08:41:06 +00001250 int p2op = (p2 + (iOp-iAddr));
dana98bf362013-11-13 18:35:01 +00001251
1252 /* Grow the p->aiIndent array as required */
1253 if( iOp>=nAlloc ){
1254 nAlloc += 100;
1255 p->aiIndent = (int*)sqlite3_realloc(p->aiIndent, nAlloc*sizeof(int));
1256 abYield = (int*)sqlite3_realloc(abYield, nAlloc*sizeof(int));
1257 }
1258 abYield[iOp] = str_in_array(zOp, azYield);
1259 p->aiIndent[iOp] = 0;
1260 p->nIndent = iOp+1;
1261
1262 if( str_in_array(zOp, azNext) ){
danc4650bb2013-11-18 08:41:06 +00001263 for(i=p2op; i<iOp; i++) p->aiIndent[i] += 2;
dana98bf362013-11-13 18:35:01 +00001264 }
drhfe705102014-03-06 13:38:37 +00001265 if( str_in_array(zOp, azGoto) && p2op<p->nIndent
1266 && (abYield[p2op] || sqlite3_column_int(pSql, 2))
1267 ){
drhe73f0592014-01-21 22:25:45 +00001268 for(i=p2op+1; i<iOp; i++) p->aiIndent[i] += 2;
dana98bf362013-11-13 18:35:01 +00001269 }
1270 }
1271
danc4650bb2013-11-18 08:41:06 +00001272 p->iIndent = 0;
dana98bf362013-11-13 18:35:01 +00001273 sqlite3_free(abYield);
1274 sqlite3_reset(pSql);
1275}
1276
1277/*
1278** Free the array allocated by explain_data_prepare().
1279*/
drhdcd87a92014-08-18 13:45:42 +00001280static void explain_data_delete(ShellState *p){
dana98bf362013-11-13 18:35:01 +00001281 sqlite3_free(p->aiIndent);
1282 p->aiIndent = 0;
1283 p->nIndent = 0;
danc4650bb2013-11-18 08:41:06 +00001284 p->iIndent = 0;
dana98bf362013-11-13 18:35:01 +00001285}
1286
1287/*
shane626a6e42009-10-22 17:30:15 +00001288** Execute a statement or set of statements. Print
1289** any result rows/columns depending on the current mode
1290** set via the supplied callback.
1291**
1292** This is very similar to SQLite's built-in sqlite3_exec()
1293** function except it takes a slightly different callback
1294** and callback data argument.
1295*/
1296static int shell_exec(
drhdcd87a92014-08-18 13:45:42 +00001297 sqlite3 *db, /* An open database */
1298 const char *zSql, /* SQL to be evaluated */
shane626a6e42009-10-22 17:30:15 +00001299 int (*xCallback)(void*,int,char**,char**,int*), /* Callback function */
drhdcd87a92014-08-18 13:45:42 +00001300 /* (not the same as sqlite3_exec) */
1301 ShellState *pArg, /* Pointer to ShellState */
1302 char **pzErrMsg /* Error msg written here */
shane626a6e42009-10-22 17:30:15 +00001303){
dan4564ced2010-01-05 04:59:56 +00001304 sqlite3_stmt *pStmt = NULL; /* Statement to execute. */
1305 int rc = SQLITE_OK; /* Return Code */
drhb07028f2011-10-14 21:49:18 +00001306 int rc2;
dan4564ced2010-01-05 04:59:56 +00001307 const char *zLeftover; /* Tail of unprocessed SQL */
shane626a6e42009-10-22 17:30:15 +00001308
1309 if( pzErrMsg ){
1310 *pzErrMsg = NULL;
1311 }
1312
shaneb9fc17d2009-10-22 21:23:35 +00001313 while( zSql[0] && (SQLITE_OK == rc) ){
1314 rc = sqlite3_prepare_v2(db, zSql, -1, &pStmt, &zLeftover);
1315 if( SQLITE_OK != rc ){
shane626a6e42009-10-22 17:30:15 +00001316 if( pzErrMsg ){
1317 *pzErrMsg = save_err_msg(db);
1318 }
1319 }else{
shaneb9fc17d2009-10-22 21:23:35 +00001320 if( !pStmt ){
1321 /* this happens for a comment or white-space */
1322 zSql = zLeftover;
drhf0693c82011-10-11 20:41:54 +00001323 while( IsSpace(zSql[0]) ) zSql++;
shaneb9fc17d2009-10-22 21:23:35 +00001324 continue;
1325 }
shane626a6e42009-10-22 17:30:15 +00001326
shaneh642d8b82010-07-28 16:05:34 +00001327 /* save off the prepared statment handle and reset row count */
1328 if( pArg ){
1329 pArg->pStmt = pStmt;
1330 pArg->cnt = 0;
1331 }
1332
shanehb7977c52010-01-18 18:17:10 +00001333 /* echo the sql statement if echo on */
shaneh642d8b82010-07-28 16:05:34 +00001334 if( pArg && pArg->echoOn ){
drha8c62df2010-02-15 15:47:18 +00001335 const char *zStmtSql = sqlite3_sql(pStmt);
shaneh642d8b82010-07-28 16:05:34 +00001336 fprintf(pArg->out, "%s\n", zStmtSql ? zStmtSql : zSql);
drha8c62df2010-02-15 15:47:18 +00001337 }
shanehb7977c52010-01-18 18:17:10 +00001338
drhefbf3b12014-02-28 20:47:24 +00001339 /* Show the EXPLAIN QUERY PLAN if .eqp is on */
1340 if( pArg && pArg->autoEQP ){
1341 sqlite3_stmt *pExplain;
1342 char *zEQP = sqlite3_mprintf("EXPLAIN QUERY PLAN %s", sqlite3_sql(pStmt));
1343 rc = sqlite3_prepare_v2(db, zEQP, -1, &pExplain, 0);
1344 if( rc==SQLITE_OK ){
1345 while( sqlite3_step(pExplain)==SQLITE_ROW ){
1346 fprintf(pArg->out,"--EQP-- %d,", sqlite3_column_int(pExplain, 0));
1347 fprintf(pArg->out,"%d,", sqlite3_column_int(pExplain, 1));
1348 fprintf(pArg->out,"%d,", sqlite3_column_int(pExplain, 2));
1349 fprintf(pArg->out,"%s\n", sqlite3_column_text(pExplain, 3));
1350 }
1351 }
1352 sqlite3_finalize(pExplain);
1353 sqlite3_free(zEQP);
1354 }
1355
drh7e02e5e2011-12-06 19:44:51 +00001356 /* Output TESTCTRL_EXPLAIN text of requested */
1357 if( pArg && pArg->mode==MODE_Explain ){
1358 const char *zExplain = 0;
1359 sqlite3_test_control(SQLITE_TESTCTRL_EXPLAIN_STMT, pStmt, &zExplain);
1360 if( zExplain && zExplain[0] ){
1361 fprintf(pArg->out, "%s", zExplain);
1362 }
1363 }
1364
dana98bf362013-11-13 18:35:01 +00001365 /* If the shell is currently in ".explain" mode, gather the extra
1366 ** data required to add indents to the output.*/
drh0a305922013-11-21 23:37:02 +00001367 if( pArg && pArg->mode==MODE_Explain ){
dana98bf362013-11-13 18:35:01 +00001368 explain_data_prepare(pArg, pStmt);
1369 }
1370
shaneb9fc17d2009-10-22 21:23:35 +00001371 /* perform the first step. this will tell us if we
1372 ** have a result set or not and how wide it is.
1373 */
1374 rc = sqlite3_step(pStmt);
1375 /* if we have a result set... */
1376 if( SQLITE_ROW == rc ){
1377 /* if we have a callback... */
1378 if( xCallback ){
1379 /* allocate space for col name ptr, value ptr, and type */
1380 int nCol = sqlite3_column_count(pStmt);
1381 void *pData = sqlite3_malloc(3*nCol*sizeof(const char*) + 1);
1382 if( !pData ){
1383 rc = SQLITE_NOMEM;
1384 }else{
1385 char **azCols = (char **)pData; /* Names of result columns */
1386 char **azVals = &azCols[nCol]; /* Results */
1387 int *aiTypes = (int *)&azVals[nCol]; /* Result types */
drh55a1b302013-09-04 16:08:50 +00001388 int i, x;
shaneb9fc17d2009-10-22 21:23:35 +00001389 assert(sizeof(int) <= sizeof(char *));
1390 /* save off ptrs to column names */
1391 for(i=0; i<nCol; i++){
1392 azCols[i] = (char *)sqlite3_column_name(pStmt, i);
1393 }
shaneb9fc17d2009-10-22 21:23:35 +00001394 do{
1395 /* extract the data and data types */
1396 for(i=0; i<nCol; i++){
drh55a1b302013-09-04 16:08:50 +00001397 aiTypes[i] = x = sqlite3_column_type(pStmt, i);
drh3432daa2013-10-11 16:35:49 +00001398 if( x==SQLITE_BLOB && pArg && pArg->mode==MODE_Insert ){
drh55a1b302013-09-04 16:08:50 +00001399 azVals[i] = "";
1400 }else{
1401 azVals[i] = (char*)sqlite3_column_text(pStmt, i);
1402 }
shaneb9fc17d2009-10-22 21:23:35 +00001403 if( !azVals[i] && (aiTypes[i]!=SQLITE_NULL) ){
1404 rc = SQLITE_NOMEM;
1405 break; /* from for */
1406 }
1407 } /* end for */
1408
1409 /* if data and types extracted successfully... */
1410 if( SQLITE_ROW == rc ){
1411 /* call the supplied callback with the result row data */
1412 if( xCallback(pArg, nCol, azVals, azCols, aiTypes) ){
1413 rc = SQLITE_ABORT;
1414 }else{
1415 rc = sqlite3_step(pStmt);
1416 }
1417 }
1418 } while( SQLITE_ROW == rc );
1419 sqlite3_free(pData);
shaneb9fc17d2009-10-22 21:23:35 +00001420 }
1421 }else{
1422 do{
1423 rc = sqlite3_step(pStmt);
1424 } while( rc == SQLITE_ROW );
1425 }
1426 }
1427
dana98bf362013-11-13 18:35:01 +00001428 explain_data_delete(pArg);
1429
shaneh642d8b82010-07-28 16:05:34 +00001430 /* print usage stats if stats on */
1431 if( pArg && pArg->statsOn ){
1432 display_stats(db, pArg, 0);
1433 }
1434
dan4564ced2010-01-05 04:59:56 +00001435 /* Finalize the statement just executed. If this fails, save a
1436 ** copy of the error message. Otherwise, set zSql to point to the
1437 ** next statement to execute. */
drhb07028f2011-10-14 21:49:18 +00001438 rc2 = sqlite3_finalize(pStmt);
1439 if( rc!=SQLITE_NOMEM ) rc = rc2;
dan4564ced2010-01-05 04:59:56 +00001440 if( rc==SQLITE_OK ){
shaneb9fc17d2009-10-22 21:23:35 +00001441 zSql = zLeftover;
drhf0693c82011-10-11 20:41:54 +00001442 while( IsSpace(zSql[0]) ) zSql++;
dan4564ced2010-01-05 04:59:56 +00001443 }else if( pzErrMsg ){
1444 *pzErrMsg = save_err_msg(db);
shane626a6e42009-10-22 17:30:15 +00001445 }
shaneh642d8b82010-07-28 16:05:34 +00001446
1447 /* clear saved stmt handle */
1448 if( pArg ){
1449 pArg->pStmt = NULL;
1450 }
shane626a6e42009-10-22 17:30:15 +00001451 }
shaneb9fc17d2009-10-22 21:23:35 +00001452 } /* end while */
shane626a6e42009-10-22 17:30:15 +00001453
1454 return rc;
1455}
1456
drhdd3d4592004-08-30 01:54:05 +00001457
drh33048c02001-10-01 14:29:22 +00001458/*
drh4c653a02000-06-07 01:27:47 +00001459** This is a different callback routine used for dumping the database.
1460** Each row received by this callback consists of a table name,
1461** the table type ("index" or "table") and SQL to create the table.
1462** This routine should print text sufficient to recreate the table.
1463*/
1464static int dump_callback(void *pArg, int nArg, char **azArg, char **azCol){
danielk19772a02e332004-06-05 08:04:36 +00001465 int rc;
1466 const char *zTable;
1467 const char *zType;
1468 const char *zSql;
drh157e29a2009-05-21 15:15:00 +00001469 const char *zPrepStmt = 0;
drhdcd87a92014-08-18 13:45:42 +00001470 ShellState *p = (ShellState *)pArg;
danielk19772a02e332004-06-05 08:04:36 +00001471
drh902b9ee2008-12-05 17:17:07 +00001472 UNUSED_PARAMETER(azCol);
drh4c653a02000-06-07 01:27:47 +00001473 if( nArg!=3 ) return 1;
danielk19772a02e332004-06-05 08:04:36 +00001474 zTable = azArg[0];
1475 zType = azArg[1];
1476 zSql = azArg[2];
1477
drh00b950d2005-09-11 02:03:03 +00001478 if( strcmp(zTable, "sqlite_sequence")==0 ){
drh157e29a2009-05-21 15:15:00 +00001479 zPrepStmt = "DELETE FROM sqlite_sequence;\n";
drh7ed10322013-08-07 16:04:27 +00001480 }else if( sqlite3_strglob("sqlite_stat?", zTable)==0 ){
drh00b950d2005-09-11 02:03:03 +00001481 fprintf(p->out, "ANALYZE sqlite_master;\n");
1482 }else if( strncmp(zTable, "sqlite_", 7)==0 ){
1483 return 0;
drh45e29d82006-11-20 16:21:10 +00001484 }else if( strncmp(zSql, "CREATE VIRTUAL TABLE", 20)==0 ){
1485 char *zIns;
1486 if( !p->writableSchema ){
1487 fprintf(p->out, "PRAGMA writable_schema=ON;\n");
1488 p->writableSchema = 1;
1489 }
1490 zIns = sqlite3_mprintf(
1491 "INSERT INTO sqlite_master(type,name,tbl_name,rootpage,sql)"
1492 "VALUES('table','%q','%q',0,'%q');",
1493 zTable, zTable, zSql);
1494 fprintf(p->out, "%s\n", zIns);
1495 sqlite3_free(zIns);
1496 return 0;
drh00b950d2005-09-11 02:03:03 +00001497 }else{
1498 fprintf(p->out, "%s;\n", zSql);
drhf8eb96a2005-02-03 00:42:34 +00001499 }
danielk19772a02e332004-06-05 08:04:36 +00001500
1501 if( strcmp(zType, "table")==0 ){
1502 sqlite3_stmt *pTableInfo = 0;
danielk19772a02e332004-06-05 08:04:36 +00001503 char *zSelect = 0;
1504 char *zTableInfo = 0;
1505 char *zTmp = 0;
drh157e29a2009-05-21 15:15:00 +00001506 int nRow = 0;
danielk19772a02e332004-06-05 08:04:36 +00001507
1508 zTableInfo = appendText(zTableInfo, "PRAGMA table_info(", 0);
1509 zTableInfo = appendText(zTableInfo, zTable, '"');
1510 zTableInfo = appendText(zTableInfo, ");", 0);
1511
drhc7181902014-02-27 15:04:13 +00001512 rc = sqlite3_prepare_v2(p->db, zTableInfo, -1, &pTableInfo, 0);
drh157e29a2009-05-21 15:15:00 +00001513 free(zTableInfo);
danielk19772a02e332004-06-05 08:04:36 +00001514 if( rc!=SQLITE_OK || !pTableInfo ){
1515 return 1;
1516 }
1517
1518 zSelect = appendText(zSelect, "SELECT 'INSERT INTO ' || ", 0);
drhbf92ec02012-03-22 12:50:34 +00001519 /* Always quote the table name, even if it appears to be pure ascii,
1520 ** in case it is a keyword. Ex: INSERT INTO "table" ... */
1521 zTmp = appendText(zTmp, zTable, '"');
danielk19772a02e332004-06-05 08:04:36 +00001522 if( zTmp ){
1523 zSelect = appendText(zSelect, zTmp, '\'');
drh85e72432012-04-11 11:38:53 +00001524 free(zTmp);
danielk19772a02e332004-06-05 08:04:36 +00001525 }
1526 zSelect = appendText(zSelect, " || ' VALUES(' || ", 0);
1527 rc = sqlite3_step(pTableInfo);
1528 while( rc==SQLITE_ROW ){
danielk19772e588c72005-12-09 14:25:08 +00001529 const char *zText = (const char *)sqlite3_column_text(pTableInfo, 1);
danielk19773f41e972004-06-08 00:39:01 +00001530 zSelect = appendText(zSelect, "quote(", 0);
danielk19772e588c72005-12-09 14:25:08 +00001531 zSelect = appendText(zSelect, zText, '"');
danielk19772a02e332004-06-05 08:04:36 +00001532 rc = sqlite3_step(pTableInfo);
1533 if( rc==SQLITE_ROW ){
drhb21a8e42012-01-28 21:08:51 +00001534 zSelect = appendText(zSelect, "), ", 0);
danielk19772a02e332004-06-05 08:04:36 +00001535 }else{
1536 zSelect = appendText(zSelect, ") ", 0);
1537 }
drh157e29a2009-05-21 15:15:00 +00001538 nRow++;
danielk19772a02e332004-06-05 08:04:36 +00001539 }
1540 rc = sqlite3_finalize(pTableInfo);
drh157e29a2009-05-21 15:15:00 +00001541 if( rc!=SQLITE_OK || nRow==0 ){
1542 free(zSelect);
danielk19772a02e332004-06-05 08:04:36 +00001543 return 1;
1544 }
1545 zSelect = appendText(zSelect, "|| ')' FROM ", 0);
1546 zSelect = appendText(zSelect, zTable, '"');
1547
drh2f464a02011-10-13 00:41:49 +00001548 rc = run_table_dump_query(p, zSelect, zPrepStmt);
drhdd3d4592004-08-30 01:54:05 +00001549 if( rc==SQLITE_CORRUPT ){
1550 zSelect = appendText(zSelect, " ORDER BY rowid DESC", 0);
drh2f464a02011-10-13 00:41:49 +00001551 run_table_dump_query(p, zSelect, 0);
drhdd3d4592004-08-30 01:54:05 +00001552 }
drh85e72432012-04-11 11:38:53 +00001553 free(zSelect);
drh4c653a02000-06-07 01:27:47 +00001554 }
drh4c653a02000-06-07 01:27:47 +00001555 return 0;
1556}
1557
1558/*
drh45e29d82006-11-20 16:21:10 +00001559** Run zQuery. Use dump_callback() as the callback routine so that
1560** the contents of the query are output as SQL statements.
1561**
drhdd3d4592004-08-30 01:54:05 +00001562** If we get a SQLITE_CORRUPT error, rerun the query after appending
1563** "ORDER BY rowid DESC" to the end.
1564*/
1565static int run_schema_dump_query(
drhdcd87a92014-08-18 13:45:42 +00001566 ShellState *p,
drh2f464a02011-10-13 00:41:49 +00001567 const char *zQuery
drhdd3d4592004-08-30 01:54:05 +00001568){
1569 int rc;
drh2f464a02011-10-13 00:41:49 +00001570 char *zErr = 0;
1571 rc = sqlite3_exec(p->db, zQuery, dump_callback, p, &zErr);
drhdd3d4592004-08-30 01:54:05 +00001572 if( rc==SQLITE_CORRUPT ){
1573 char *zQ2;
drh4f21c4a2008-12-10 22:15:00 +00001574 int len = strlen30(zQuery);
drh2f464a02011-10-13 00:41:49 +00001575 fprintf(p->out, "/****** CORRUPTION ERROR *******/\n");
1576 if( zErr ){
1577 fprintf(p->out, "/****** %s ******/\n", zErr);
1578 sqlite3_free(zErr);
1579 zErr = 0;
1580 }
drhdd3d4592004-08-30 01:54:05 +00001581 zQ2 = malloc( len+100 );
1582 if( zQ2==0 ) return rc;
drh8c5058b2012-04-16 17:22:30 +00001583 sqlite3_snprintf(len+100, zQ2, "%s ORDER BY rowid DESC", zQuery);
drh2f464a02011-10-13 00:41:49 +00001584 rc = sqlite3_exec(p->db, zQ2, dump_callback, p, &zErr);
1585 if( rc ){
1586 fprintf(p->out, "/****** ERROR: %s ******/\n", zErr);
1587 }else{
1588 rc = SQLITE_CORRUPT;
1589 }
1590 sqlite3_free(zErr);
drhdd3d4592004-08-30 01:54:05 +00001591 free(zQ2);
1592 }
1593 return rc;
1594}
1595
1596/*
drh75897232000-05-29 14:26:00 +00001597** Text of a help message
1598*/
persicom1d0b8722002-04-18 02:53:04 +00001599static char zHelp[] =
drh9ff849f2009-02-04 20:55:57 +00001600 ".backup ?DB? FILE Backup DB (default \"main\") to FILE\n"
drhc2ce0be2014-05-29 12:36:14 +00001601 ".bail on|off Stop after hitting an error. Default OFF\n"
drh4bbcf102014-02-06 02:46:08 +00001602 ".clone NEWDB Clone data into NEWDB from the existing database\n"
jplyon6a65bb32003-05-04 07:25:57 +00001603 ".databases List names and files of attached databases\n"
drhb860bc92004-08-04 15:16:55 +00001604 ".dump ?TABLE? ... Dump the database in an SQL text format\n"
shane86f5bdb2009-10-24 02:00:07 +00001605 " If TABLE specified, only dump tables matching\n"
1606 " LIKE pattern TABLE.\n"
drhc2ce0be2014-05-29 12:36:14 +00001607 ".echo on|off Turn command echo on or off\n"
drh6d36ffe2014-06-16 15:01:37 +00001608 ".eqp on|off Enable or disable automatic EXPLAIN QUERY PLAN\n"
drh75897232000-05-29 14:26:00 +00001609 ".exit Exit this program\n"
drhc2ce0be2014-05-29 12:36:14 +00001610 ".explain ?on|off? Turn output mode suitable for EXPLAIN on or off.\n"
shanehe2aa9d72009-11-06 17:20:17 +00001611 " With no args, it turns EXPLAIN on.\n"
drhc1971542014-06-23 23:28:13 +00001612 ".fullschema Show schema and the content of sqlite_stat tables\n"
drhc2ce0be2014-05-29 12:36:14 +00001613 ".headers on|off Turn display of headers on or off\n"
drh75897232000-05-29 14:26:00 +00001614 ".help Show this message\n"
drhb860bc92004-08-04 15:16:55 +00001615 ".import FILE TABLE Import data from FILE into TABLE\n"
shane86f5bdb2009-10-24 02:00:07 +00001616 ".indices ?TABLE? Show names of all indices\n"
1617 " If TABLE specified, only show indices for tables\n"
1618 " matching LIKE pattern TABLE.\n"
drhae5e4452007-05-03 17:18:36 +00001619#ifdef SQLITE_ENABLE_IOTRACE
1620 ".iotrace FILE Enable I/O diagnostic logging to FILE\n"
1621#endif
drh70df4fe2006-06-13 15:12:21 +00001622#ifndef SQLITE_OMIT_LOAD_EXTENSION
drh1e397f82006-06-08 15:28:43 +00001623 ".load FILE ?ENTRY? Load an extension library\n"
drh70df4fe2006-06-13 15:12:21 +00001624#endif
drh127f9d72010-02-23 01:47:00 +00001625 ".log FILE|off Turn logging on or off. FILE can be stderr/stdout\n"
danielk19776b77a362005-01-13 11:10:25 +00001626 ".mode MODE ?TABLE? Set output mode where MODE is one of:\n"
drh3b584fa2004-09-24 12:50:03 +00001627 " csv Comma-separated values\n"
drhb860bc92004-08-04 15:16:55 +00001628 " column Left-aligned columns. (See .width)\n"
1629 " html HTML <table> code\n"
1630 " insert SQL insert statements for TABLE\n"
1631 " line One value per line\n"
1632 " list Values delimited by .separator string\n"
1633 " tabs Tab-separated values\n"
1634 " tcl TCL list elements\n"
drh078b1fd2012-09-21 13:40:02 +00001635 ".nullvalue STRING Use STRING in place of NULL values\n"
drhc2ce0be2014-05-29 12:36:14 +00001636 ".once FILENAME Output for the next SQL command only to FILENAME\n"
drh05782482013-10-24 15:20:20 +00001637 ".open ?FILENAME? Close existing database and reopen FILENAME\n"
drhc2ce0be2014-05-29 12:36:14 +00001638 ".output ?FILENAME? Send output to FILENAME or stdout\n"
drh078b1fd2012-09-21 13:40:02 +00001639 ".print STRING... Print literal STRING\n"
persicom7e2dfdd2002-04-18 02:46:52 +00001640 ".prompt MAIN CONTINUE Replace the standard prompts\n"
persicom7e2dfdd2002-04-18 02:46:52 +00001641 ".quit Exit this program\n"
drhdaffd0e2001-04-11 14:28:42 +00001642 ".read FILENAME Execute SQL in FILENAME\n"
drh9ff849f2009-02-04 20:55:57 +00001643 ".restore ?DB? FILE Restore content of DB (default \"main\") from FILE\n"
drh5c7976f2014-02-10 19:59:27 +00001644 ".save FILE Write in-memory database into FILE\n"
drh75897232000-05-29 14:26:00 +00001645 ".schema ?TABLE? Show the CREATE statements\n"
shane86f5bdb2009-10-24 02:00:07 +00001646 " If TABLE specified, only show tables matching\n"
1647 " LIKE pattern TABLE.\n"
drh6976c212014-07-24 12:09:47 +00001648 ".separator STRING ?NL? Change separator used by output mode and .import\n"
1649 " NL is the end-of-line mark for CSV\n"
drh62cdde52014-05-28 20:22:28 +00001650 ".shell CMD ARGS... Run CMD ARGS... in a system shell\n"
drhdd45df82002-04-18 12:39:03 +00001651 ".show Show the current values for various settings\n"
drhc2ce0be2014-05-29 12:36:14 +00001652 ".stats on|off Turn stats on or off\n"
drh62cdde52014-05-28 20:22:28 +00001653 ".system CMD ARGS... Run CMD ARGS... in a system shell\n"
shane86f5bdb2009-10-24 02:00:07 +00001654 ".tables ?TABLE? List names of tables\n"
1655 " If TABLE specified, only list tables matching\n"
1656 " LIKE pattern TABLE.\n"
drh2dfbbca2000-07-28 14:32:48 +00001657 ".timeout MS Try opening locked tables for MS milliseconds\n"
drhc2ce0be2014-05-29 12:36:14 +00001658 ".timer on|off Turn SQL timer on or off\n"
drh42f64e52012-04-04 16:56:23 +00001659 ".trace FILE|off Output each SQL statement as it is run\n"
drhde60fc22011-12-14 17:53:36 +00001660 ".vfsname ?AUX? Print the name of the VFS stack\n"
shanehe2aa9d72009-11-06 17:20:17 +00001661 ".width NUM1 NUM2 ... Set column widths for \"column\" mode\n"
drh62cdde52014-05-28 20:22:28 +00001662 " Negative values right-justify\n"
drh75897232000-05-29 14:26:00 +00001663;
1664
drhdaffd0e2001-04-11 14:28:42 +00001665/* Forward reference */
drhdcd87a92014-08-18 13:45:42 +00001666static int process_input(ShellState *p, FILE *in);
drhba5b0932014-07-24 12:39:59 +00001667/*
1668** Implementation of the "readfile(X)" SQL function. The entire content
1669** of the file named X is read and returned as a BLOB. NULL is returned
1670** if the file does not exist or is unreadable.
1671*/
1672static void readfileFunc(
1673 sqlite3_context *context,
1674 int argc,
1675 sqlite3_value **argv
1676){
1677 const char *zName;
1678 FILE *in;
1679 long nIn;
1680 void *pBuf;
1681
1682 zName = (const char*)sqlite3_value_text(argv[0]);
1683 if( zName==0 ) return;
1684 in = fopen(zName, "rb");
1685 if( in==0 ) return;
1686 fseek(in, 0, SEEK_END);
1687 nIn = ftell(in);
1688 rewind(in);
1689 pBuf = sqlite3_malloc( nIn );
1690 if( pBuf && 1==fread(pBuf, nIn, 1, in) ){
1691 sqlite3_result_blob(context, pBuf, nIn, sqlite3_free);
1692 }else{
1693 sqlite3_free(pBuf);
1694 }
1695 fclose(in);
1696}
1697
1698/*
1699** Implementation of the "writefile(X,Y)" SQL function. The argument Y
1700** is written into file X. The number of bytes written is returned. Or
1701** NULL is returned if something goes wrong, such as being unable to open
1702** file X for writing.
1703*/
1704static void writefileFunc(
1705 sqlite3_context *context,
1706 int argc,
1707 sqlite3_value **argv
1708){
1709 FILE *out;
1710 const char *z;
drhba5b0932014-07-24 12:39:59 +00001711 sqlite3_int64 rc;
1712 const char *zFile;
1713
1714 zFile = (const char*)sqlite3_value_text(argv[0]);
1715 if( zFile==0 ) return;
1716 out = fopen(zFile, "wb");
1717 if( out==0 ) return;
1718 z = (const char*)sqlite3_value_blob(argv[1]);
1719 if( z==0 ){
drhba5b0932014-07-24 12:39:59 +00001720 rc = 0;
1721 }else{
drh490fe862014-08-11 14:21:32 +00001722 rc = fwrite(z, 1, sqlite3_value_bytes(argv[1]), out);
drhba5b0932014-07-24 12:39:59 +00001723 }
1724 fclose(out);
1725 sqlite3_result_int64(context, rc);
1726}
drhdaffd0e2001-04-11 14:28:42 +00001727
drh75897232000-05-29 14:26:00 +00001728/*
drh44c2eb12003-04-30 11:38:26 +00001729** Make sure the database is open. If it is not, then open it. If
1730** the database fails to open, print an error message and exit.
1731*/
drhdcd87a92014-08-18 13:45:42 +00001732static void open_db(ShellState *p, int keepAlive){
drh44c2eb12003-04-30 11:38:26 +00001733 if( p->db==0 ){
drhbbb0be82012-06-27 16:12:27 +00001734 sqlite3_initialize();
danielk19774f057f92004-06-08 00:02:33 +00001735 sqlite3_open(p->zDbFilename, &p->db);
danielk197780290862004-05-22 09:21:21 +00001736 db = p->db;
drh4cea5ba2008-05-05 16:27:24 +00001737 if( db && sqlite3_errcode(db)==SQLITE_OK ){
1738 sqlite3_create_function(db, "shellstatic", 0, SQLITE_UTF8, 0,
1739 shellstaticFunc, 0, 0);
1740 }
1741 if( db==0 || SQLITE_OK!=sqlite3_errcode(db) ){
shane86f5bdb2009-10-24 02:00:07 +00001742 fprintf(stderr,"Error: unable to open database \"%s\": %s\n",
danielk197780290862004-05-22 09:21:21 +00001743 p->zDbFilename, sqlite3_errmsg(db));
drh05782482013-10-24 15:20:20 +00001744 if( keepAlive ) return;
drh22fbcb82004-02-01 01:22:50 +00001745 exit(1);
drh44c2eb12003-04-30 11:38:26 +00001746 }
drhc2e87a32006-06-27 15:16:14 +00001747#ifndef SQLITE_OMIT_LOAD_EXTENSION
1748 sqlite3_enable_load_extension(p->db, 1);
1749#endif
drhba5b0932014-07-24 12:39:59 +00001750 sqlite3_create_function(db, "readfile", 1, SQLITE_UTF8, 0,
1751 readfileFunc, 0, 0);
1752 sqlite3_create_function(db, "writefile", 2, SQLITE_UTF8, 0,
1753 writefileFunc, 0, 0);
drh44c2eb12003-04-30 11:38:26 +00001754 }
1755}
1756
1757/*
drhfeac5f82004-08-01 00:10:45 +00001758** Do C-language style dequoting.
1759**
1760** \t -> tab
1761** \n -> newline
1762** \r -> carriage return
drh4c56b992013-06-27 13:26:55 +00001763** \" -> "
drhfeac5f82004-08-01 00:10:45 +00001764** \NNN -> ascii character NNN in octal
1765** \\ -> backslash
1766*/
1767static void resolve_backslashes(char *z){
shane7d3846a2008-12-11 02:58:26 +00001768 int i, j;
1769 char c;
drhc2ce0be2014-05-29 12:36:14 +00001770 while( *z && *z!='\\' ) z++;
drhfeac5f82004-08-01 00:10:45 +00001771 for(i=j=0; (c = z[i])!=0; i++, j++){
1772 if( c=='\\' ){
1773 c = z[++i];
1774 if( c=='n' ){
1775 c = '\n';
1776 }else if( c=='t' ){
1777 c = '\t';
1778 }else if( c=='r' ){
1779 c = '\r';
drh4c56b992013-06-27 13:26:55 +00001780 }else if( c=='\\' ){
1781 c = '\\';
drhfeac5f82004-08-01 00:10:45 +00001782 }else if( c>='0' && c<='7' ){
drhaa816082005-12-29 12:53:09 +00001783 c -= '0';
drhfeac5f82004-08-01 00:10:45 +00001784 if( z[i+1]>='0' && z[i+1]<='7' ){
1785 i++;
1786 c = (c<<3) + z[i] - '0';
1787 if( z[i+1]>='0' && z[i+1]<='7' ){
1788 i++;
1789 c = (c<<3) + z[i] - '0';
1790 }
1791 }
1792 }
1793 }
1794 z[j] = c;
1795 }
drhc2ce0be2014-05-29 12:36:14 +00001796 if( j<i ) z[j] = 0;
drhfeac5f82004-08-01 00:10:45 +00001797}
1798
1799/*
drh348d19c2013-06-03 12:47:43 +00001800** Return the value of a hexadecimal digit. Return -1 if the input
1801** is not a hex digit.
drhc28490c2006-10-26 14:25:58 +00001802*/
drh348d19c2013-06-03 12:47:43 +00001803static int hexDigitValue(char c){
1804 if( c>='0' && c<='9' ) return c - '0';
1805 if( c>='a' && c<='f' ) return c - 'a' + 10;
1806 if( c>='A' && c<='F' ) return c - 'A' + 10;
1807 return -1;
drhc28490c2006-10-26 14:25:58 +00001808}
1809
1810/*
drh7d9f3942013-04-03 01:26:54 +00001811** Interpret zArg as an integer value, possibly with suffixes.
1812*/
1813static sqlite3_int64 integerValue(const char *zArg){
1814 sqlite3_int64 v = 0;
1815 static const struct { char *zSuffix; int iMult; } aMult[] = {
1816 { "KiB", 1024 },
1817 { "MiB", 1024*1024 },
1818 { "GiB", 1024*1024*1024 },
1819 { "KB", 1000 },
1820 { "MB", 1000000 },
1821 { "GB", 1000000000 },
1822 { "K", 1000 },
1823 { "M", 1000000 },
1824 { "G", 1000000000 },
1825 };
1826 int i;
1827 int isNeg = 0;
1828 if( zArg[0]=='-' ){
1829 isNeg = 1;
1830 zArg++;
1831 }else if( zArg[0]=='+' ){
1832 zArg++;
1833 }
drh348d19c2013-06-03 12:47:43 +00001834 if( zArg[0]=='0' && zArg[1]=='x' ){
1835 int x;
1836 zArg += 2;
1837 while( (x = hexDigitValue(zArg[0]))>=0 ){
1838 v = (v<<4) + x;
1839 zArg++;
1840 }
1841 }else{
1842 while( IsDigit(zArg[0]) ){
1843 v = v*10 + zArg[0] - '0';
1844 zArg++;
1845 }
drh7d9f3942013-04-03 01:26:54 +00001846 }
drhc2bed0a2013-05-24 11:57:50 +00001847 for(i=0; i<ArraySize(aMult); i++){
drh7d9f3942013-04-03 01:26:54 +00001848 if( sqlite3_stricmp(aMult[i].zSuffix, zArg)==0 ){
1849 v *= aMult[i].iMult;
1850 break;
1851 }
1852 }
1853 return isNeg? -v : v;
1854}
1855
1856/*
drh348d19c2013-06-03 12:47:43 +00001857** Interpret zArg as either an integer or a boolean value. Return 1 or 0
1858** for TRUE and FALSE. Return the integer value if appropriate.
1859*/
1860static int booleanValue(char *zArg){
1861 int i;
1862 if( zArg[0]=='0' && zArg[1]=='x' ){
1863 for(i=2; hexDigitValue(zArg[i])>=0; i++){}
1864 }else{
1865 for(i=0; zArg[i]>='0' && zArg[i]<='9'; i++){}
1866 }
1867 if( i>0 && zArg[i]==0 ) return (int)(integerValue(zArg) & 0xffffffff);
1868 if( sqlite3_stricmp(zArg, "on")==0 || sqlite3_stricmp(zArg,"yes")==0 ){
1869 return 1;
1870 }
1871 if( sqlite3_stricmp(zArg, "off")==0 || sqlite3_stricmp(zArg,"no")==0 ){
1872 return 0;
1873 }
1874 fprintf(stderr, "ERROR: Not a boolean value: \"%s\". Assuming \"no\".\n",
1875 zArg);
1876 return 0;
1877}
1878
1879/*
drh42f64e52012-04-04 16:56:23 +00001880** Close an output file, assuming it is not stderr or stdout
1881*/
1882static void output_file_close(FILE *f){
1883 if( f && f!=stdout && f!=stderr ) fclose(f);
1884}
1885
1886/*
1887** Try to open an output file. The names "stdout" and "stderr" are
1888** recognized and do the right thing. NULL is returned if the output
1889** filename is "off".
1890*/
1891static FILE *output_file_open(const char *zFile){
1892 FILE *f;
1893 if( strcmp(zFile,"stdout")==0 ){
1894 f = stdout;
1895 }else if( strcmp(zFile, "stderr")==0 ){
1896 f = stderr;
1897 }else if( strcmp(zFile, "off")==0 ){
1898 f = 0;
1899 }else{
1900 f = fopen(zFile, "wb");
1901 if( f==0 ){
1902 fprintf(stderr, "Error: cannot open \"%s\"\n", zFile);
1903 }
1904 }
1905 return f;
1906}
1907
1908/*
1909** A routine for handling output from sqlite3_trace().
1910*/
1911static void sql_trace_callback(void *pArg, const char *z){
1912 FILE *f = (FILE*)pArg;
drh4b2590e2014-08-19 19:28:00 +00001913 if( f ){
1914 int i = (int)strlen(z);
1915 while( i>0 && z[i-1]==';' ){ i--; }
1916 fprintf(f, "%.*s;\n", i, z);
1917 }
drh42f64e52012-04-04 16:56:23 +00001918}
1919
1920/*
drhd8621b92012-04-17 09:09:33 +00001921** A no-op routine that runs with the ".breakpoint" doc-command. This is
1922** a useful spot to set a debugger breakpoint.
1923*/
1924static void test_breakpoint(void){
1925 static int nCall = 0;
1926 nCall++;
1927}
1928
1929/*
drhdb95f682013-06-26 22:46:00 +00001930** An object used to read a CSV file
1931*/
1932typedef struct CSVReader CSVReader;
1933struct CSVReader {
1934 const char *zFile; /* Name of the input file */
1935 FILE *in; /* Read the CSV text from this input stream */
1936 char *z; /* Accumulated text for a field */
1937 int n; /* Number of bytes in z */
1938 int nAlloc; /* Space allocated for z[] */
1939 int nLine; /* Current line number */
1940 int cTerm; /* Character that terminated the most recent field */
1941 int cSeparator; /* The separator character. (Usually ",") */
1942};
1943
1944/* Append a single byte to z[] */
1945static void csv_append_char(CSVReader *p, int c){
1946 if( p->n+1>=p->nAlloc ){
1947 p->nAlloc += p->nAlloc + 100;
1948 p->z = sqlite3_realloc(p->z, p->nAlloc);
1949 if( p->z==0 ){
1950 fprintf(stderr, "out of memory\n");
1951 exit(1);
1952 }
1953 }
1954 p->z[p->n++] = (char)c;
1955}
1956
1957/* Read a single field of CSV text. Compatible with rfc4180 and extended
1958** with the option of having a separator other than ",".
1959**
1960** + Input comes from p->in.
1961** + Store results in p->z of length p->n. Space to hold p->z comes
1962** from sqlite3_malloc().
1963** + Use p->cSep as the separator. The default is ",".
1964** + Keep track of the line number in p->nLine.
1965** + Store the character that terminates the field in p->cTerm. Store
1966** EOF on end-of-file.
1967** + Report syntax errors on stderr
1968*/
1969static char *csv_read_one_field(CSVReader *p){
drha81ad172013-12-11 14:00:04 +00001970 int c, pc, ppc;
drhdb95f682013-06-26 22:46:00 +00001971 int cSep = p->cSeparator;
1972 p->n = 0;
1973 c = fgetc(p->in);
1974 if( c==EOF || seenInterrupt ){
1975 p->cTerm = EOF;
1976 return 0;
1977 }
1978 if( c=='"' ){
1979 int startLine = p->nLine;
1980 int cQuote = c;
drha81ad172013-12-11 14:00:04 +00001981 pc = ppc = 0;
drhdb95f682013-06-26 22:46:00 +00001982 while( 1 ){
1983 c = fgetc(p->in);
1984 if( c=='\n' ) p->nLine++;
1985 if( c==cQuote ){
1986 if( pc==cQuote ){
1987 pc = 0;
1988 continue;
1989 }
1990 }
1991 if( (c==cSep && pc==cQuote)
1992 || (c=='\n' && pc==cQuote)
drha81ad172013-12-11 14:00:04 +00001993 || (c=='\n' && pc=='\r' && ppc==cQuote)
drhdb95f682013-06-26 22:46:00 +00001994 || (c==EOF && pc==cQuote)
1995 ){
1996 do{ p->n--; }while( p->z[p->n]!=cQuote );
drhdb95f682013-06-26 22:46:00 +00001997 p->cTerm = c;
1998 break;
1999 }
2000 if( pc==cQuote && c!='\r' ){
2001 fprintf(stderr, "%s:%d: unescaped %c character\n",
2002 p->zFile, p->nLine, cQuote);
2003 }
2004 if( c==EOF ){
2005 fprintf(stderr, "%s:%d: unterminated %c-quoted field\n",
2006 p->zFile, startLine, cQuote);
drhdb95f682013-06-26 22:46:00 +00002007 p->cTerm = EOF;
2008 break;
2009 }
2010 csv_append_char(p, c);
drha81ad172013-12-11 14:00:04 +00002011 ppc = pc;
drhdb95f682013-06-26 22:46:00 +00002012 pc = c;
drhd0a64dc2013-06-30 20:24:26 +00002013 }
drhdb95f682013-06-26 22:46:00 +00002014 }else{
drhd0a64dc2013-06-30 20:24:26 +00002015 while( c!=EOF && c!=cSep && c!='\n' ){
drhdb95f682013-06-26 22:46:00 +00002016 csv_append_char(p, c);
drhd0a64dc2013-06-30 20:24:26 +00002017 c = fgetc(p->in);
drhdb95f682013-06-26 22:46:00 +00002018 }
2019 if( c=='\n' ){
2020 p->nLine++;
drh3852b682014-02-26 13:53:34 +00002021 if( p->n>0 && p->z[p->n-1]=='\r' ) p->n--;
drhdb95f682013-06-26 22:46:00 +00002022 }
drhdb95f682013-06-26 22:46:00 +00002023 p->cTerm = c;
2024 }
drh8dd675e2013-07-12 21:09:24 +00002025 if( p->z ) p->z[p->n] = 0;
drhdb95f682013-06-26 22:46:00 +00002026 return p->z;
2027}
2028
2029/*
drh4bbcf102014-02-06 02:46:08 +00002030** Try to transfer data for table zTable. If an error is seen while
2031** moving forward, try to go backwards. The backwards movement won't
2032** work for WITHOUT ROWID tables.
drh3350ce92014-02-06 00:49:12 +00002033*/
mistachkine31ae902014-02-06 01:15:29 +00002034static void tryToCloneData(
drhdcd87a92014-08-18 13:45:42 +00002035 ShellState *p,
drh3350ce92014-02-06 00:49:12 +00002036 sqlite3 *newDb,
2037 const char *zTable
2038){
2039 sqlite3_stmt *pQuery = 0;
2040 sqlite3_stmt *pInsert = 0;
2041 char *zQuery = 0;
2042 char *zInsert = 0;
2043 int rc;
2044 int i, j, n;
2045 int nTable = (int)strlen(zTable);
2046 int k = 0;
drh4bbcf102014-02-06 02:46:08 +00002047 int cnt = 0;
2048 const int spinRate = 10000;
drh3350ce92014-02-06 00:49:12 +00002049
2050 zQuery = sqlite3_mprintf("SELECT * FROM \"%w\"", zTable);
2051 rc = sqlite3_prepare_v2(p->db, zQuery, -1, &pQuery, 0);
2052 if( rc ){
drh4bbcf102014-02-06 02:46:08 +00002053 fprintf(stderr, "Error %d: %s on [%s]\n",
drh3350ce92014-02-06 00:49:12 +00002054 sqlite3_extended_errcode(p->db), sqlite3_errmsg(p->db),
2055 zQuery);
2056 goto end_data_xfer;
2057 }
2058 n = sqlite3_column_count(pQuery);
2059 zInsert = sqlite3_malloc(200 + nTable + n*3);
2060 if( zInsert==0 ){
2061 fprintf(stderr, "out of memory\n");
2062 goto end_data_xfer;
2063 }
2064 sqlite3_snprintf(200+nTable,zInsert,
2065 "INSERT OR IGNORE INTO \"%s\" VALUES(?", zTable);
2066 i = (int)strlen(zInsert);
2067 for(j=1; j<n; j++){
2068 memcpy(zInsert+i, ",?", 2);
2069 i += 2;
2070 }
2071 memcpy(zInsert+i, ");", 3);
2072 rc = sqlite3_prepare_v2(newDb, zInsert, -1, &pInsert, 0);
2073 if( rc ){
drh4bbcf102014-02-06 02:46:08 +00002074 fprintf(stderr, "Error %d: %s on [%s]\n",
drh3350ce92014-02-06 00:49:12 +00002075 sqlite3_extended_errcode(newDb), sqlite3_errmsg(newDb),
2076 zQuery);
2077 goto end_data_xfer;
2078 }
2079 for(k=0; k<2; k++){
2080 while( (rc = sqlite3_step(pQuery))==SQLITE_ROW ){
2081 for(i=0; i<n; i++){
2082 switch( sqlite3_column_type(pQuery, i) ){
2083 case SQLITE_NULL: {
2084 sqlite3_bind_null(pInsert, i+1);
2085 break;
2086 }
2087 case SQLITE_INTEGER: {
2088 sqlite3_bind_int64(pInsert, i+1, sqlite3_column_int64(pQuery,i));
2089 break;
2090 }
2091 case SQLITE_FLOAT: {
2092 sqlite3_bind_double(pInsert, i+1, sqlite3_column_double(pQuery,i));
2093 break;
2094 }
2095 case SQLITE_TEXT: {
2096 sqlite3_bind_text(pInsert, i+1,
2097 (const char*)sqlite3_column_text(pQuery,i),
2098 -1, SQLITE_STATIC);
2099 break;
2100 }
2101 case SQLITE_BLOB: {
2102 sqlite3_bind_blob(pInsert, i+1, sqlite3_column_blob(pQuery,i),
2103 sqlite3_column_bytes(pQuery,i),
2104 SQLITE_STATIC);
2105 break;
2106 }
2107 }
2108 } /* End for */
drh4bbcf102014-02-06 02:46:08 +00002109 rc = sqlite3_step(pInsert);
2110 if( rc!=SQLITE_OK && rc!=SQLITE_ROW && rc!=SQLITE_DONE ){
2111 fprintf(stderr, "Error %d: %s\n", sqlite3_extended_errcode(newDb),
2112 sqlite3_errmsg(newDb));
2113 }
drh3350ce92014-02-06 00:49:12 +00002114 sqlite3_reset(pInsert);
drh4bbcf102014-02-06 02:46:08 +00002115 cnt++;
2116 if( (cnt%spinRate)==0 ){
2117 printf("%c\b", "|/-\\"[(cnt/spinRate)%4]);
2118 fflush(stdout);
2119 }
drh3350ce92014-02-06 00:49:12 +00002120 } /* End while */
2121 if( rc==SQLITE_DONE ) break;
2122 sqlite3_finalize(pQuery);
2123 sqlite3_free(zQuery);
2124 zQuery = sqlite3_mprintf("SELECT * FROM \"%w\" ORDER BY rowid DESC;",
2125 zTable);
2126 rc = sqlite3_prepare_v2(p->db, zQuery, -1, &pQuery, 0);
2127 if( rc ){
drh4bbcf102014-02-06 02:46:08 +00002128 fprintf(stderr, "Warning: cannot step \"%s\" backwards", zTable);
2129 break;
drh3350ce92014-02-06 00:49:12 +00002130 }
2131 } /* End for(k=0...) */
2132
2133end_data_xfer:
2134 sqlite3_finalize(pQuery);
2135 sqlite3_finalize(pInsert);
2136 sqlite3_free(zQuery);
2137 sqlite3_free(zInsert);
2138}
2139
2140
2141/*
2142** Try to transfer all rows of the schema that match zWhere. For
2143** each row, invoke xForEach() on the object defined by that row.
drh4bbcf102014-02-06 02:46:08 +00002144** If an error is encountered while moving forward through the
2145** sqlite_master table, try again moving backwards.
drh3350ce92014-02-06 00:49:12 +00002146*/
mistachkine31ae902014-02-06 01:15:29 +00002147static void tryToCloneSchema(
drhdcd87a92014-08-18 13:45:42 +00002148 ShellState *p,
drh3350ce92014-02-06 00:49:12 +00002149 sqlite3 *newDb,
2150 const char *zWhere,
drhdcd87a92014-08-18 13:45:42 +00002151 void (*xForEach)(ShellState*,sqlite3*,const char*)
drh3350ce92014-02-06 00:49:12 +00002152){
2153 sqlite3_stmt *pQuery = 0;
2154 char *zQuery = 0;
2155 int rc;
2156 const unsigned char *zName;
2157 const unsigned char *zSql;
drh4bbcf102014-02-06 02:46:08 +00002158 char *zErrMsg = 0;
drh3350ce92014-02-06 00:49:12 +00002159
2160 zQuery = sqlite3_mprintf("SELECT name, sql FROM sqlite_master"
2161 " WHERE %s", zWhere);
2162 rc = sqlite3_prepare_v2(p->db, zQuery, -1, &pQuery, 0);
2163 if( rc ){
2164 fprintf(stderr, "Error: (%d) %s on [%s]\n",
2165 sqlite3_extended_errcode(p->db), sqlite3_errmsg(p->db),
2166 zQuery);
2167 goto end_schema_xfer;
2168 }
2169 while( (rc = sqlite3_step(pQuery))==SQLITE_ROW ){
2170 zName = sqlite3_column_text(pQuery, 0);
2171 zSql = sqlite3_column_text(pQuery, 1);
2172 printf("%s... ", zName); fflush(stdout);
drh4bbcf102014-02-06 02:46:08 +00002173 sqlite3_exec(newDb, (const char*)zSql, 0, 0, &zErrMsg);
2174 if( zErrMsg ){
2175 fprintf(stderr, "Error: %s\nSQL: [%s]\n", zErrMsg, zSql);
2176 sqlite3_free(zErrMsg);
2177 zErrMsg = 0;
2178 }
drh3350ce92014-02-06 00:49:12 +00002179 if( xForEach ){
2180 xForEach(p, newDb, (const char*)zName);
2181 }
2182 printf("done\n");
2183 }
2184 if( rc!=SQLITE_DONE ){
2185 sqlite3_finalize(pQuery);
2186 sqlite3_free(zQuery);
2187 zQuery = sqlite3_mprintf("SELECT name, sql FROM sqlite_master"
2188 " WHERE %s ORDER BY rowid DESC", zWhere);
2189 rc = sqlite3_prepare_v2(p->db, zQuery, -1, &pQuery, 0);
2190 if( rc ){
2191 fprintf(stderr, "Error: (%d) %s on [%s]\n",
2192 sqlite3_extended_errcode(p->db), sqlite3_errmsg(p->db),
2193 zQuery);
2194 goto end_schema_xfer;
2195 }
2196 while( (rc = sqlite3_step(pQuery))==SQLITE_ROW ){
2197 zName = sqlite3_column_text(pQuery, 0);
2198 zSql = sqlite3_column_text(pQuery, 1);
2199 printf("%s... ", zName); fflush(stdout);
drh4bbcf102014-02-06 02:46:08 +00002200 sqlite3_exec(newDb, (const char*)zSql, 0, 0, &zErrMsg);
2201 if( zErrMsg ){
2202 fprintf(stderr, "Error: %s\nSQL: [%s]\n", zErrMsg, zSql);
2203 sqlite3_free(zErrMsg);
2204 zErrMsg = 0;
2205 }
drh3350ce92014-02-06 00:49:12 +00002206 if( xForEach ){
2207 xForEach(p, newDb, (const char*)zName);
2208 }
2209 printf("done\n");
2210 }
2211 }
2212end_schema_xfer:
2213 sqlite3_finalize(pQuery);
2214 sqlite3_free(zQuery);
2215}
2216
2217/*
2218** Open a new database file named "zNewDb". Try to recover as much information
2219** as possible out of the main database (which might be corrupt) and write it
2220** into zNewDb.
2221*/
drhdcd87a92014-08-18 13:45:42 +00002222static void tryToClone(ShellState *p, const char *zNewDb){
drh3350ce92014-02-06 00:49:12 +00002223 int rc;
2224 sqlite3 *newDb = 0;
2225 if( access(zNewDb,0)==0 ){
2226 fprintf(stderr, "File \"%s\" already exists.\n", zNewDb);
2227 return;
2228 }
2229 rc = sqlite3_open(zNewDb, &newDb);
2230 if( rc ){
2231 fprintf(stderr, "Cannot create output database: %s\n",
2232 sqlite3_errmsg(newDb));
2233 }else{
drh54d0d2d2014-04-03 00:32:13 +00002234 sqlite3_exec(p->db, "PRAGMA writable_schema=ON;", 0, 0, 0);
drh3350ce92014-02-06 00:49:12 +00002235 sqlite3_exec(newDb, "BEGIN EXCLUSIVE;", 0, 0, 0);
mistachkine31ae902014-02-06 01:15:29 +00002236 tryToCloneSchema(p, newDb, "type='table'", tryToCloneData);
2237 tryToCloneSchema(p, newDb, "type!='table'", 0);
drh3350ce92014-02-06 00:49:12 +00002238 sqlite3_exec(newDb, "COMMIT;", 0, 0, 0);
drh54d0d2d2014-04-03 00:32:13 +00002239 sqlite3_exec(p->db, "PRAGMA writable_schema=OFF;", 0, 0, 0);
drh3350ce92014-02-06 00:49:12 +00002240 }
2241 sqlite3_close(newDb);
2242}
2243
2244/*
drhc2ce0be2014-05-29 12:36:14 +00002245** Change the output file back to stdout
2246*/
drhdcd87a92014-08-18 13:45:42 +00002247static void output_reset(ShellState *p){
drhc2ce0be2014-05-29 12:36:14 +00002248 if( p->outfile[0]=='|' ){
2249 pclose(p->out);
2250 }else{
2251 output_file_close(p->out);
2252 }
2253 p->outfile[0] = 0;
2254 p->out = stdout;
2255}
2256
2257/*
drh75897232000-05-29 14:26:00 +00002258** If an input line begins with "." then invoke this routine to
2259** process that line.
drh67505e72002-04-19 12:34:06 +00002260**
drh47ad6842006-11-08 12:25:42 +00002261** Return 1 on error, 2 to exit, and 0 otherwise.
drh75897232000-05-29 14:26:00 +00002262*/
drhdcd87a92014-08-18 13:45:42 +00002263static int do_meta_command(char *zLine, ShellState *p){
drh75897232000-05-29 14:26:00 +00002264 int i = 1;
2265 int nArg = 0;
2266 int n, c;
drh67505e72002-04-19 12:34:06 +00002267 int rc = 0;
drh75897232000-05-29 14:26:00 +00002268 char *azArg[50];
2269
2270 /* Parse the input line into tokens.
2271 */
2272 while( zLine[i] && nArg<ArraySize(azArg) ){
drhf0693c82011-10-11 20:41:54 +00002273 while( IsSpace(zLine[i]) ){ i++; }
drh06333682004-03-09 13:37:45 +00002274 if( zLine[i]==0 ) break;
drh75897232000-05-29 14:26:00 +00002275 if( zLine[i]=='\'' || zLine[i]=='"' ){
2276 int delim = zLine[i++];
2277 azArg[nArg++] = &zLine[i];
drh4c56b992013-06-27 13:26:55 +00002278 while( zLine[i] && zLine[i]!=delim ){
2279 if( zLine[i]=='\\' && delim=='"' && zLine[i+1]!=0 ) i++;
2280 i++;
2281 }
drh75897232000-05-29 14:26:00 +00002282 if( zLine[i]==delim ){
2283 zLine[i++] = 0;
2284 }
drhfeac5f82004-08-01 00:10:45 +00002285 if( delim=='"' ) resolve_backslashes(azArg[nArg-1]);
drh75897232000-05-29 14:26:00 +00002286 }else{
2287 azArg[nArg++] = &zLine[i];
drhf0693c82011-10-11 20:41:54 +00002288 while( zLine[i] && !IsSpace(zLine[i]) ){ i++; }
drh75897232000-05-29 14:26:00 +00002289 if( zLine[i] ) zLine[i++] = 0;
drhfeac5f82004-08-01 00:10:45 +00002290 resolve_backslashes(azArg[nArg-1]);
drh75897232000-05-29 14:26:00 +00002291 }
2292 }
2293
2294 /* Process the input line.
2295 */
shane9bd1b442009-10-23 01:27:39 +00002296 if( nArg==0 ) return 0; /* no tokens, no error */
drh4f21c4a2008-12-10 22:15:00 +00002297 n = strlen30(azArg[0]);
drh75897232000-05-29 14:26:00 +00002298 c = azArg[0][0];
drh5c7976f2014-02-10 19:59:27 +00002299 if( (c=='b' && n>=3 && strncmp(azArg[0], "backup", n)==0)
2300 || (c=='s' && n>=3 && strncmp(azArg[0], "save", n)==0)
2301 ){
drhbc46f022013-01-23 18:53:23 +00002302 const char *zDestFile = 0;
2303 const char *zDb = 0;
drh9ff849f2009-02-04 20:55:57 +00002304 sqlite3 *pDest;
2305 sqlite3_backup *pBackup;
drhbc46f022013-01-23 18:53:23 +00002306 int j;
2307 for(j=1; j<nArg; j++){
2308 const char *z = azArg[j];
2309 if( z[0]=='-' ){
2310 while( z[0]=='-' ) z++;
drhaf664332013-07-18 20:28:29 +00002311 /* No options to process at this time */
drhbc46f022013-01-23 18:53:23 +00002312 {
2313 fprintf(stderr, "unknown option: %s\n", azArg[j]);
2314 return 1;
2315 }
2316 }else if( zDestFile==0 ){
2317 zDestFile = azArg[j];
2318 }else if( zDb==0 ){
2319 zDb = zDestFile;
2320 zDestFile = azArg[j];
2321 }else{
2322 fprintf(stderr, "too many arguments to .backup\n");
2323 return 1;
2324 }
drh9ff849f2009-02-04 20:55:57 +00002325 }
drhbc46f022013-01-23 18:53:23 +00002326 if( zDestFile==0 ){
2327 fprintf(stderr, "missing FILENAME argument on .backup\n");
2328 return 1;
2329 }
2330 if( zDb==0 ) zDb = "main";
drh9ff849f2009-02-04 20:55:57 +00002331 rc = sqlite3_open(zDestFile, &pDest);
2332 if( rc!=SQLITE_OK ){
shane9bd1b442009-10-23 01:27:39 +00002333 fprintf(stderr, "Error: cannot open \"%s\"\n", zDestFile);
drh9ff849f2009-02-04 20:55:57 +00002334 sqlite3_close(pDest);
2335 return 1;
2336 }
drh05782482013-10-24 15:20:20 +00002337 open_db(p, 0);
drh9ff849f2009-02-04 20:55:57 +00002338 pBackup = sqlite3_backup_init(pDest, "main", p->db, zDb);
2339 if( pBackup==0 ){
2340 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(pDest));
2341 sqlite3_close(pDest);
2342 return 1;
2343 }
2344 while( (rc = sqlite3_backup_step(pBackup,100))==SQLITE_OK ){}
2345 sqlite3_backup_finish(pBackup);
2346 if( rc==SQLITE_DONE ){
shane9bd1b442009-10-23 01:27:39 +00002347 rc = 0;
drh9ff849f2009-02-04 20:55:57 +00002348 }else{
2349 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(pDest));
shane9bd1b442009-10-23 01:27:39 +00002350 rc = 1;
drh9ff849f2009-02-04 20:55:57 +00002351 }
2352 sqlite3_close(pDest);
2353 }else
2354
drhc2ce0be2014-05-29 12:36:14 +00002355 if( c=='b' && n>=3 && strncmp(azArg[0], "bail", n)==0 ){
2356 if( nArg==2 ){
2357 bail_on_error = booleanValue(azArg[1]);
2358 }else{
2359 fprintf(stderr, "Usage: .bail on|off\n");
2360 rc = 1;
2361 }
drhc49f44e2006-10-26 18:15:42 +00002362 }else
2363
drhd8621b92012-04-17 09:09:33 +00002364 /* The undocumented ".breakpoint" command causes a call to the no-op
2365 ** routine named test_breakpoint().
2366 */
2367 if( c=='b' && n>=3 && strncmp(azArg[0], "breakpoint", n)==0 ){
2368 test_breakpoint();
2369 }else
2370
drhc2ce0be2014-05-29 12:36:14 +00002371 if( c=='c' && strncmp(azArg[0], "clone", n)==0 ){
2372 if( nArg==2 ){
2373 tryToClone(p, azArg[1]);
2374 }else{
2375 fprintf(stderr, "Usage: .clone FILENAME\n");
2376 rc = 1;
2377 }
mistachkine31ae902014-02-06 01:15:29 +00002378 }else
2379
drhc2ce0be2014-05-29 12:36:14 +00002380 if( c=='d' && n>1 && strncmp(azArg[0], "databases", n)==0 ){
drhdcd87a92014-08-18 13:45:42 +00002381 ShellState data;
jplyon672a1ed2003-05-11 20:07:05 +00002382 char *zErrMsg = 0;
drh05782482013-10-24 15:20:20 +00002383 open_db(p, 0);
jplyon672a1ed2003-05-11 20:07:05 +00002384 memcpy(&data, p, sizeof(data));
drhd8885442004-03-17 23:42:12 +00002385 data.showHeader = 1;
jplyon672a1ed2003-05-11 20:07:05 +00002386 data.mode = MODE_Column;
drhd8885442004-03-17 23:42:12 +00002387 data.colWidth[0] = 3;
2388 data.colWidth[1] = 15;
2389 data.colWidth[2] = 58;
drh0b2110c2004-10-26 00:08:10 +00002390 data.cnt = 0;
danielk19776f8a5032004-05-10 10:34:51 +00002391 sqlite3_exec(p->db, "PRAGMA database_list; ", callback, &data, &zErrMsg);
jplyon672a1ed2003-05-11 20:07:05 +00002392 if( zErrMsg ){
2393 fprintf(stderr,"Error: %s\n", zErrMsg);
drh3f4fedb2004-05-31 19:34:33 +00002394 sqlite3_free(zErrMsg);
shane9bd1b442009-10-23 01:27:39 +00002395 rc = 1;
jplyon6a65bb32003-05-04 07:25:57 +00002396 }
2397 }else
2398
drhc2ce0be2014-05-29 12:36:14 +00002399 if( c=='d' && strncmp(azArg[0], "dump", n)==0 ){
drh05782482013-10-24 15:20:20 +00002400 open_db(p, 0);
drhf1dfc4f2009-09-23 15:51:35 +00002401 /* When playing back a "dump", the content might appear in an order
2402 ** which causes immediate foreign key constraints to be violated.
2403 ** So disable foreign-key constraint enforcement to prevent problems. */
drhc2ce0be2014-05-29 12:36:14 +00002404 if( nArg!=1 && nArg!=2 ){
2405 fprintf(stderr, "Usage: .dump ?LIKE-PATTERN?\n");
2406 rc = 1;
2407 goto meta_command_exit;
2408 }
drhf1dfc4f2009-09-23 15:51:35 +00002409 fprintf(p->out, "PRAGMA foreign_keys=OFF;\n");
drh33048c02001-10-01 14:29:22 +00002410 fprintf(p->out, "BEGIN TRANSACTION;\n");
drh45e29d82006-11-20 16:21:10 +00002411 p->writableSchema = 0;
drh56197952011-10-13 16:30:13 +00002412 sqlite3_exec(p->db, "SAVEPOINT dump; PRAGMA writable_schema=ON", 0, 0, 0);
drh2f464a02011-10-13 00:41:49 +00002413 p->nErr = 0;
drh4c653a02000-06-07 01:27:47 +00002414 if( nArg==1 ){
drhdd3d4592004-08-30 01:54:05 +00002415 run_schema_dump_query(p,
drha18c5682000-10-08 22:20:57 +00002416 "SELECT name, type, sql FROM sqlite_master "
drh2f464a02011-10-13 00:41:49 +00002417 "WHERE sql NOT NULL AND type=='table' AND name!='sqlite_sequence'"
drh4f324762009-05-21 14:51:03 +00002418 );
2419 run_schema_dump_query(p,
2420 "SELECT name, type, sql FROM sqlite_master "
drh2f464a02011-10-13 00:41:49 +00002421 "WHERE name=='sqlite_sequence'"
drh0b9a5942006-09-13 20:22:02 +00002422 );
drh2f464a02011-10-13 00:41:49 +00002423 run_table_dump_query(p,
drh0b9a5942006-09-13 20:22:02 +00002424 "SELECT sql FROM sqlite_master "
drh157e29a2009-05-21 15:15:00 +00002425 "WHERE sql NOT NULL AND type IN ('index','trigger','view')", 0
drha18c5682000-10-08 22:20:57 +00002426 );
drh4c653a02000-06-07 01:27:47 +00002427 }else{
2428 int i;
drhdd3d4592004-08-30 01:54:05 +00002429 for(i=1; i<nArg; i++){
danielk1977bc6ada42004-06-30 08:20:16 +00002430 zShellStatic = azArg[i];
drhdd3d4592004-08-30 01:54:05 +00002431 run_schema_dump_query(p,
drha18c5682000-10-08 22:20:57 +00002432 "SELECT name, type, sql FROM sqlite_master "
drhdd3d4592004-08-30 01:54:05 +00002433 "WHERE tbl_name LIKE shellstatic() AND type=='table'"
drh2f464a02011-10-13 00:41:49 +00002434 " AND sql NOT NULL");
2435 run_table_dump_query(p,
drh0b9a5942006-09-13 20:22:02 +00002436 "SELECT sql FROM sqlite_master "
drh45e29d82006-11-20 16:21:10 +00002437 "WHERE sql NOT NULL"
2438 " AND type IN ('index','trigger','view')"
drh157e29a2009-05-21 15:15:00 +00002439 " AND tbl_name LIKE shellstatic()", 0
drh0b9a5942006-09-13 20:22:02 +00002440 );
danielk1977bc6ada42004-06-30 08:20:16 +00002441 zShellStatic = 0;
drh4c653a02000-06-07 01:27:47 +00002442 }
2443 }
drh45e29d82006-11-20 16:21:10 +00002444 if( p->writableSchema ){
drh56197952011-10-13 16:30:13 +00002445 fprintf(p->out, "PRAGMA writable_schema=OFF;\n");
drh45e29d82006-11-20 16:21:10 +00002446 p->writableSchema = 0;
2447 }
drh56197952011-10-13 16:30:13 +00002448 sqlite3_exec(p->db, "PRAGMA writable_schema=OFF;", 0, 0, 0);
2449 sqlite3_exec(p->db, "RELEASE dump;", 0, 0, 0);
drh2f464a02011-10-13 00:41:49 +00002450 fprintf(p->out, p->nErr ? "ROLLBACK; -- due to errors\n" : "COMMIT;\n");
drh4c653a02000-06-07 01:27:47 +00002451 }else
drh75897232000-05-29 14:26:00 +00002452
drhc2ce0be2014-05-29 12:36:14 +00002453 if( c=='e' && strncmp(azArg[0], "echo", n)==0 ){
2454 if( nArg==2 ){
2455 p->echoOn = booleanValue(azArg[1]);
2456 }else{
2457 fprintf(stderr, "Usage: .echo on|off\n");
2458 rc = 1;
2459 }
drhdaffd0e2001-04-11 14:28:42 +00002460 }else
2461
drhc2ce0be2014-05-29 12:36:14 +00002462 if( c=='e' && strncmp(azArg[0], "eqp", n)==0 ){
2463 if( nArg==2 ){
2464 p->autoEQP = booleanValue(azArg[1]);
2465 }else{
2466 fprintf(stderr, "Usage: .eqp on|off\n");
2467 rc = 1;
2468 }
drhefbf3b12014-02-28 20:47:24 +00002469 }else
2470
drhd3ac7d92013-01-25 18:33:43 +00002471 if( c=='e' && strncmp(azArg[0], "exit", n)==0 ){
drh348d19c2013-06-03 12:47:43 +00002472 if( nArg>1 && (rc = (int)integerValue(azArg[1]))!=0 ) exit(rc);
drh47ad6842006-11-08 12:25:42 +00002473 rc = 2;
drh75897232000-05-29 14:26:00 +00002474 }else
2475
drhc2ce0be2014-05-29 12:36:14 +00002476 if( c=='e' && strncmp(azArg[0], "explain", n)==0 ){
drhc28490c2006-10-26 14:25:58 +00002477 int val = nArg>=2 ? booleanValue(azArg[1]) : 1;
persicom7e2dfdd2002-04-18 02:46:52 +00002478 if(val == 1) {
drhdcd87a92014-08-18 13:45:42 +00002479 if(!p->normalMode.valid) {
2480 p->normalMode.valid = 1;
2481 p->normalMode.mode = p->mode;
2482 p->normalMode.showHeader = p->showHeader;
2483 memcpy(p->normalMode.colWidth,p->colWidth,sizeof(p->colWidth));
persicom7e2dfdd2002-04-18 02:46:52 +00002484 }
2485 /* We could put this code under the !p->explainValid
2486 ** condition so that it does not execute if we are already in
2487 ** explain mode. However, always executing it allows us an easy
2488 ** was to reset to explain mode in case the user previously
2489 ** did an .explain followed by a .width, .mode or .header
2490 ** command.
2491 */
danielk19770d78bae2008-01-03 07:09:48 +00002492 p->mode = MODE_Explain;
persicom7e2dfdd2002-04-18 02:46:52 +00002493 p->showHeader = 1;
drhac68ced2013-11-27 13:24:18 +00002494 memset(p->colWidth,0,sizeof(p->colWidth));
danielk19770d78bae2008-01-03 07:09:48 +00002495 p->colWidth[0] = 4; /* addr */
drh60a713c2008-01-21 16:22:45 +00002496 p->colWidth[1] = 13; /* opcode */
2497 p->colWidth[2] = 4; /* P1 */
2498 p->colWidth[3] = 4; /* P2 */
2499 p->colWidth[4] = 4; /* P3 */
2500 p->colWidth[5] = 13; /* P4 */
danielk19770d78bae2008-01-03 07:09:48 +00002501 p->colWidth[6] = 2; /* P5 */
drh60a713c2008-01-21 16:22:45 +00002502 p->colWidth[7] = 13; /* Comment */
drhdcd87a92014-08-18 13:45:42 +00002503 }else if (p->normalMode.valid) {
2504 p->normalMode.valid = 0;
2505 p->mode = p->normalMode.mode;
2506 p->showHeader = p->normalMode.showHeader;
2507 memcpy(p->colWidth,p->normalMode.colWidth,sizeof(p->colWidth));
persicom7e2dfdd2002-04-18 02:46:52 +00002508 }
drh75897232000-05-29 14:26:00 +00002509 }else
2510
drhc1971542014-06-23 23:28:13 +00002511 if( c=='f' && strncmp(azArg[0], "fullschema", n)==0 ){
drhdcd87a92014-08-18 13:45:42 +00002512 ShellState data;
drhc1971542014-06-23 23:28:13 +00002513 char *zErrMsg = 0;
drh56f674c2014-07-18 14:43:29 +00002514 int doStats = 0;
drhc1971542014-06-23 23:28:13 +00002515 if( nArg!=1 ){
2516 fprintf(stderr, "Usage: .fullschema\n");
2517 rc = 1;
2518 goto meta_command_exit;
2519 }
2520 open_db(p, 0);
2521 memcpy(&data, p, sizeof(data));
2522 data.showHeader = 0;
2523 data.mode = MODE_Semi;
2524 rc = sqlite3_exec(p->db,
2525 "SELECT sql FROM"
2526 " (SELECT sql sql, type type, tbl_name tbl_name, name name, rowid x"
2527 " FROM sqlite_master UNION ALL"
2528 " SELECT sql, type, tbl_name, name, rowid FROM sqlite_temp_master) "
drh4b2590e2014-08-19 19:28:00 +00002529 "WHERE type!='meta' AND sql NOTNULL AND name NOT LIKE 'sqlite_%' "
drhc1971542014-06-23 23:28:13 +00002530 "ORDER BY rowid",
2531 callback, &data, &zErrMsg
2532 );
drh56f674c2014-07-18 14:43:29 +00002533 if( rc==SQLITE_OK ){
2534 sqlite3_stmt *pStmt;
2535 rc = sqlite3_prepare_v2(p->db,
2536 "SELECT rowid FROM sqlite_master"
2537 " WHERE name GLOB 'sqlite_stat[134]'",
2538 -1, &pStmt, 0);
2539 doStats = sqlite3_step(pStmt)==SQLITE_ROW;
2540 sqlite3_finalize(pStmt);
2541 }
2542 if( doStats==0 ){
2543 fprintf(p->out, "/* No STAT tables available */\n");
2544 }else{
2545 fprintf(p->out, "ANALYZE sqlite_master;\n");
2546 sqlite3_exec(p->db, "SELECT 'ANALYZE sqlite_master'",
2547 callback, &data, &zErrMsg);
2548 data.mode = MODE_Insert;
2549 data.zDestTable = "sqlite_stat1";
2550 shell_exec(p->db, "SELECT * FROM sqlite_stat1",
2551 shell_callback, &data,&zErrMsg);
2552 data.zDestTable = "sqlite_stat3";
2553 shell_exec(p->db, "SELECT * FROM sqlite_stat3",
2554 shell_callback, &data,&zErrMsg);
2555 data.zDestTable = "sqlite_stat4";
2556 shell_exec(p->db, "SELECT * FROM sqlite_stat4",
2557 shell_callback, &data, &zErrMsg);
2558 fprintf(p->out, "ANALYZE sqlite_master;\n");
2559 }
drhc1971542014-06-23 23:28:13 +00002560 }else
2561
drhc2ce0be2014-05-29 12:36:14 +00002562 if( c=='h' && strncmp(azArg[0], "headers", n)==0 ){
2563 if( nArg==2 ){
2564 p->showHeader = booleanValue(azArg[1]);
2565 }else{
2566 fprintf(stderr, "Usage: .headers on|off\n");
2567 rc = 1;
shaneb320ccd2009-10-21 03:42:58 +00002568 }
drh75897232000-05-29 14:26:00 +00002569 }else
2570
drhc2ce0be2014-05-29 12:36:14 +00002571 if( c=='h' && strncmp(azArg[0], "help", n)==0 ){
2572 fprintf(p->out, "%s", zHelp);
2573 }else
2574
2575 if( c=='i' && strncmp(azArg[0], "import", n)==0 ){
drh01f37542014-05-31 15:43:33 +00002576 char *zTable; /* Insert data into this table */
2577 char *zFile; /* Name of file to extra content from */
shane916f9612009-10-23 00:37:15 +00002578 sqlite3_stmt *pStmt = NULL; /* A statement */
drhfeac5f82004-08-01 00:10:45 +00002579 int nCol; /* Number of columns in the table */
2580 int nByte; /* Number of bytes in an SQL string */
2581 int i, j; /* Loop counters */
drh2d463112013-08-06 14:36:36 +00002582 int needCommit; /* True to COMMIT or ROLLBACK at end */
drhfeac5f82004-08-01 00:10:45 +00002583 int nSep; /* Number of bytes in p->separator[] */
2584 char *zSql; /* An SQL statement */
drhdb95f682013-06-26 22:46:00 +00002585 CSVReader sCsv; /* Reader context */
drh5bde8162013-06-27 14:07:53 +00002586 int (*xCloser)(FILE*); /* Procedure to close th3 connection */
drhfeac5f82004-08-01 00:10:45 +00002587
drhc2ce0be2014-05-29 12:36:14 +00002588 if( nArg!=3 ){
2589 fprintf(stderr, "Usage: .import FILE TABLE\n");
2590 goto meta_command_exit;
2591 }
drh01f37542014-05-31 15:43:33 +00002592 zFile = azArg[1];
2593 zTable = azArg[2];
drhdb95f682013-06-26 22:46:00 +00002594 seenInterrupt = 0;
2595 memset(&sCsv, 0, sizeof(sCsv));
drh05782482013-10-24 15:20:20 +00002596 open_db(p, 0);
drh4f21c4a2008-12-10 22:15:00 +00002597 nSep = strlen30(p->separator);
drhfeac5f82004-08-01 00:10:45 +00002598 if( nSep==0 ){
shane916f9612009-10-23 00:37:15 +00002599 fprintf(stderr, "Error: non-null separator required for import\n");
2600 return 1;
drhfeac5f82004-08-01 00:10:45 +00002601 }
drhdb95f682013-06-26 22:46:00 +00002602 if( nSep>1 ){
2603 fprintf(stderr, "Error: multi-character separators not allowed"
2604 " for import\n");
2605 return 1;
2606 }
drh5bde8162013-06-27 14:07:53 +00002607 sCsv.zFile = zFile;
2608 sCsv.nLine = 1;
2609 if( sCsv.zFile[0]=='|' ){
2610 sCsv.in = popen(sCsv.zFile+1, "r");
2611 sCsv.zFile = "<pipe>";
2612 xCloser = pclose;
2613 }else{
2614 sCsv.in = fopen(sCsv.zFile, "rb");
2615 xCloser = fclose;
2616 }
drhdb95f682013-06-26 22:46:00 +00002617 if( sCsv.in==0 ){
drh5bde8162013-06-27 14:07:53 +00002618 fprintf(stderr, "Error: cannot open \"%s\"\n", zFile);
drhdb95f682013-06-26 22:46:00 +00002619 return 1;
2620 }
2621 sCsv.cSeparator = p->separator[0];
drh7b075e32011-09-28 01:10:00 +00002622 zSql = sqlite3_mprintf("SELECT * FROM %s", zTable);
shane916f9612009-10-23 00:37:15 +00002623 if( zSql==0 ){
2624 fprintf(stderr, "Error: out of memory\n");
drh5bde8162013-06-27 14:07:53 +00002625 xCloser(sCsv.in);
shane916f9612009-10-23 00:37:15 +00002626 return 1;
2627 }
drh4f21c4a2008-12-10 22:15:00 +00002628 nByte = strlen30(zSql);
drhc7181902014-02-27 15:04:13 +00002629 rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
dan6a8ac852014-05-26 18:27:12 +00002630 csv_append_char(&sCsv, 0); /* To ensure sCsv.z is allocated */
drhdb95f682013-06-26 22:46:00 +00002631 if( rc && sqlite3_strglob("no such table: *", sqlite3_errmsg(db))==0 ){
2632 char *zCreate = sqlite3_mprintf("CREATE TABLE %s", zTable);
2633 char cSep = '(';
2634 while( csv_read_one_field(&sCsv) ){
2635 zCreate = sqlite3_mprintf("%z%c\n \"%s\" TEXT", zCreate, cSep, sCsv.z);
2636 cSep = ',';
2637 if( sCsv.cTerm!=sCsv.cSeparator ) break;
2638 }
drh5bde8162013-06-27 14:07:53 +00002639 if( cSep=='(' ){
2640 sqlite3_free(zCreate);
2641 sqlite3_free(sCsv.z);
2642 xCloser(sCsv.in);
2643 fprintf(stderr,"%s: empty file\n", sCsv.zFile);
2644 return 1;
2645 }
drhdb95f682013-06-26 22:46:00 +00002646 zCreate = sqlite3_mprintf("%z\n)", zCreate);
2647 rc = sqlite3_exec(p->db, zCreate, 0, 0, 0);
2648 sqlite3_free(zCreate);
2649 if( rc ){
2650 fprintf(stderr, "CREATE TABLE %s(...) failed: %s\n", zTable,
2651 sqlite3_errmsg(db));
2652 sqlite3_free(sCsv.z);
drh5bde8162013-06-27 14:07:53 +00002653 xCloser(sCsv.in);
drhdb95f682013-06-26 22:46:00 +00002654 return 1;
2655 }
drhc7181902014-02-27 15:04:13 +00002656 rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
drhdb95f682013-06-26 22:46:00 +00002657 }
drhfeac5f82004-08-01 00:10:45 +00002658 sqlite3_free(zSql);
2659 if( rc ){
shane916f9612009-10-23 00:37:15 +00002660 if (pStmt) sqlite3_finalize(pStmt);
drhfeac5f82004-08-01 00:10:45 +00002661 fprintf(stderr,"Error: %s\n", sqlite3_errmsg(db));
drh5bde8162013-06-27 14:07:53 +00002662 xCloser(sCsv.in);
shane916f9612009-10-23 00:37:15 +00002663 return 1;
drhfeac5f82004-08-01 00:10:45 +00002664 }
shane916f9612009-10-23 00:37:15 +00002665 nCol = sqlite3_column_count(pStmt);
drhfeac5f82004-08-01 00:10:45 +00002666 sqlite3_finalize(pStmt);
shane916f9612009-10-23 00:37:15 +00002667 pStmt = 0;
shane9bd1b442009-10-23 01:27:39 +00002668 if( nCol==0 ) return 0; /* no columns, no error */
drhdb95f682013-06-26 22:46:00 +00002669 zSql = sqlite3_malloc( nByte*2 + 20 + nCol*2 );
shane916f9612009-10-23 00:37:15 +00002670 if( zSql==0 ){
2671 fprintf(stderr, "Error: out of memory\n");
drh5bde8162013-06-27 14:07:53 +00002672 xCloser(sCsv.in);
shane916f9612009-10-23 00:37:15 +00002673 return 1;
2674 }
drhdb95f682013-06-26 22:46:00 +00002675 sqlite3_snprintf(nByte+20, zSql, "INSERT INTO \"%w\" VALUES(?", zTable);
drh4f21c4a2008-12-10 22:15:00 +00002676 j = strlen30(zSql);
drhfeac5f82004-08-01 00:10:45 +00002677 for(i=1; i<nCol; i++){
2678 zSql[j++] = ',';
2679 zSql[j++] = '?';
2680 }
2681 zSql[j++] = ')';
2682 zSql[j] = 0;
drhc7181902014-02-27 15:04:13 +00002683 rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
drhdb95f682013-06-26 22:46:00 +00002684 sqlite3_free(zSql);
drhfeac5f82004-08-01 00:10:45 +00002685 if( rc ){
2686 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(db));
shane916f9612009-10-23 00:37:15 +00002687 if (pStmt) sqlite3_finalize(pStmt);
drh5bde8162013-06-27 14:07:53 +00002688 xCloser(sCsv.in);
drh47ad6842006-11-08 12:25:42 +00002689 return 1;
drhfeac5f82004-08-01 00:10:45 +00002690 }
drh2d463112013-08-06 14:36:36 +00002691 needCommit = sqlite3_get_autocommit(db);
2692 if( needCommit ) sqlite3_exec(db, "BEGIN", 0, 0, 0);
drhdb95f682013-06-26 22:46:00 +00002693 do{
2694 int startLine = sCsv.nLine;
drhfeac5f82004-08-01 00:10:45 +00002695 for(i=0; i<nCol; i++){
drhdb95f682013-06-26 22:46:00 +00002696 char *z = csv_read_one_field(&sCsv);
2697 if( z==0 && i==0 ) break;
2698 sqlite3_bind_text(pStmt, i+1, z, -1, SQLITE_TRANSIENT);
2699 if( i<nCol-1 && sCsv.cTerm!=sCsv.cSeparator ){
2700 fprintf(stderr, "%s:%d: expected %d columns but found %d - "
2701 "filling the rest with NULL\n",
2702 sCsv.zFile, startLine, nCol, i+1);
2703 i++;
mistachkin6fe03382014-06-16 22:45:28 +00002704 while( i<=nCol ){ sqlite3_bind_null(pStmt, i); i++; }
drh18f52e02012-01-16 16:56:31 +00002705 }
drhfeac5f82004-08-01 00:10:45 +00002706 }
drhdb95f682013-06-26 22:46:00 +00002707 if( sCsv.cTerm==sCsv.cSeparator ){
2708 do{
2709 csv_read_one_field(&sCsv);
2710 i++;
2711 }while( sCsv.cTerm==sCsv.cSeparator );
2712 fprintf(stderr, "%s:%d: expected %d columns but found %d - "
2713 "extras ignored\n",
2714 sCsv.zFile, startLine, nCol, i);
drhfeac5f82004-08-01 00:10:45 +00002715 }
drhdb95f682013-06-26 22:46:00 +00002716 if( i>=nCol ){
2717 sqlite3_step(pStmt);
2718 rc = sqlite3_reset(pStmt);
2719 if( rc!=SQLITE_OK ){
2720 fprintf(stderr, "%s:%d: INSERT failed: %s\n", sCsv.zFile, startLine,
2721 sqlite3_errmsg(db));
2722 }
2723 }
2724 }while( sCsv.cTerm!=EOF );
2725
drh5bde8162013-06-27 14:07:53 +00002726 xCloser(sCsv.in);
drhdb95f682013-06-26 22:46:00 +00002727 sqlite3_free(sCsv.z);
drhfeac5f82004-08-01 00:10:45 +00002728 sqlite3_finalize(pStmt);
drh2d463112013-08-06 14:36:36 +00002729 if( needCommit ) sqlite3_exec(db, "COMMIT", 0, 0, 0);
drhfeac5f82004-08-01 00:10:45 +00002730 }else
2731
drhc2ce0be2014-05-29 12:36:14 +00002732 if( c=='i' && strncmp(azArg[0], "indices", n)==0 ){
drhdcd87a92014-08-18 13:45:42 +00002733 ShellState data;
drh75897232000-05-29 14:26:00 +00002734 char *zErrMsg = 0;
drh05782482013-10-24 15:20:20 +00002735 open_db(p, 0);
drh75897232000-05-29 14:26:00 +00002736 memcpy(&data, p, sizeof(data));
2737 data.showHeader = 0;
2738 data.mode = MODE_List;
shane86f5bdb2009-10-24 02:00:07 +00002739 if( nArg==1 ){
2740 rc = sqlite3_exec(p->db,
2741 "SELECT name FROM sqlite_master "
2742 "WHERE type='index' AND name NOT LIKE 'sqlite_%' "
2743 "UNION ALL "
2744 "SELECT name FROM sqlite_temp_master "
2745 "WHERE type='index' "
2746 "ORDER BY 1",
2747 callback, &data, &zErrMsg
2748 );
drhc2ce0be2014-05-29 12:36:14 +00002749 }else if( nArg==2 ){
shane86f5bdb2009-10-24 02:00:07 +00002750 zShellStatic = azArg[1];
2751 rc = sqlite3_exec(p->db,
2752 "SELECT name FROM sqlite_master "
2753 "WHERE type='index' AND tbl_name LIKE shellstatic() "
2754 "UNION ALL "
2755 "SELECT name FROM sqlite_temp_master "
2756 "WHERE type='index' AND tbl_name LIKE shellstatic() "
2757 "ORDER BY 1",
2758 callback, &data, &zErrMsg
2759 );
2760 zShellStatic = 0;
drhc2ce0be2014-05-29 12:36:14 +00002761 }else{
2762 fprintf(stderr, "Usage: .indices ?LIKE-PATTERN?\n");
2763 rc = 1;
2764 goto meta_command_exit;
shane86f5bdb2009-10-24 02:00:07 +00002765 }
drh75897232000-05-29 14:26:00 +00002766 if( zErrMsg ){
2767 fprintf(stderr,"Error: %s\n", zErrMsg);
drh3f4fedb2004-05-31 19:34:33 +00002768 sqlite3_free(zErrMsg);
shane9bd1b442009-10-23 01:27:39 +00002769 rc = 1;
shane86f5bdb2009-10-24 02:00:07 +00002770 }else if( rc != SQLITE_OK ){
2771 fprintf(stderr,"Error: querying sqlite_master and sqlite_temp_master\n");
2772 rc = 1;
drh75897232000-05-29 14:26:00 +00002773 }
2774 }else
2775
drhae5e4452007-05-03 17:18:36 +00002776#ifdef SQLITE_ENABLE_IOTRACE
drhb0603412007-02-28 04:47:26 +00002777 if( c=='i' && strncmp(azArg[0], "iotrace", n)==0 ){
mlcreech3a00f902008-03-04 17:45:01 +00002778 extern void (*sqlite3IoTrace)(const char*, ...);
drhb0603412007-02-28 04:47:26 +00002779 if( iotrace && iotrace!=stdout ) fclose(iotrace);
2780 iotrace = 0;
2781 if( nArg<2 ){
mlcreech3a00f902008-03-04 17:45:01 +00002782 sqlite3IoTrace = 0;
drhb0603412007-02-28 04:47:26 +00002783 }else if( strcmp(azArg[1], "-")==0 ){
mlcreech3a00f902008-03-04 17:45:01 +00002784 sqlite3IoTrace = iotracePrintf;
drhb0603412007-02-28 04:47:26 +00002785 iotrace = stdout;
2786 }else{
2787 iotrace = fopen(azArg[1], "w");
2788 if( iotrace==0 ){
shane9bd1b442009-10-23 01:27:39 +00002789 fprintf(stderr, "Error: cannot open \"%s\"\n", azArg[1]);
mlcreech3a00f902008-03-04 17:45:01 +00002790 sqlite3IoTrace = 0;
shane9bd1b442009-10-23 01:27:39 +00002791 rc = 1;
drhb0603412007-02-28 04:47:26 +00002792 }else{
mlcreech3a00f902008-03-04 17:45:01 +00002793 sqlite3IoTrace = iotracePrintf;
drhb0603412007-02-28 04:47:26 +00002794 }
2795 }
2796 }else
drhae5e4452007-05-03 17:18:36 +00002797#endif
drhb0603412007-02-28 04:47:26 +00002798
drh70df4fe2006-06-13 15:12:21 +00002799#ifndef SQLITE_OMIT_LOAD_EXTENSION
drhc2ce0be2014-05-29 12:36:14 +00002800 if( c=='l' && strncmp(azArg[0], "load", n)==0 ){
drh1e397f82006-06-08 15:28:43 +00002801 const char *zFile, *zProc;
2802 char *zErrMsg = 0;
drhc2ce0be2014-05-29 12:36:14 +00002803 if( nArg<2 ){
2804 fprintf(stderr, "Usage: .load FILE ?ENTRYPOINT?\n");
2805 rc = 1;
2806 goto meta_command_exit;
2807 }
drh1e397f82006-06-08 15:28:43 +00002808 zFile = azArg[1];
2809 zProc = nArg>=3 ? azArg[2] : 0;
drh05782482013-10-24 15:20:20 +00002810 open_db(p, 0);
drh1e397f82006-06-08 15:28:43 +00002811 rc = sqlite3_load_extension(p->db, zFile, zProc, &zErrMsg);
2812 if( rc!=SQLITE_OK ){
shane9bd1b442009-10-23 01:27:39 +00002813 fprintf(stderr, "Error: %s\n", zErrMsg);
drh1e397f82006-06-08 15:28:43 +00002814 sqlite3_free(zErrMsg);
drh47ad6842006-11-08 12:25:42 +00002815 rc = 1;
drh1e397f82006-06-08 15:28:43 +00002816 }
2817 }else
drh70df4fe2006-06-13 15:12:21 +00002818#endif
drh1e397f82006-06-08 15:28:43 +00002819
drhc2ce0be2014-05-29 12:36:14 +00002820 if( c=='l' && strncmp(azArg[0], "log", n)==0 ){
2821 if( nArg!=2 ){
2822 fprintf(stderr, "Usage: .log FILENAME\n");
2823 rc = 1;
2824 }else{
2825 const char *zFile = azArg[1];
2826 output_file_close(p->pLog);
2827 p->pLog = output_file_open(zFile);
2828 }
drh127f9d72010-02-23 01:47:00 +00002829 }else
2830
drhc2ce0be2014-05-29 12:36:14 +00002831 if( c=='m' && strncmp(azArg[0], "mode", n)==0 ){
2832 const char *zMode = nArg>=2 ? azArg[1] : "";
2833 int n2 = (int)strlen(zMode);
2834 int c2 = zMode[0];
2835 if( c2=='l' && n2>2 && strncmp(azArg[1],"lines",n2)==0 ){
drh75897232000-05-29 14:26:00 +00002836 p->mode = MODE_Line;
drhc2ce0be2014-05-29 12:36:14 +00002837 }else if( c2=='c' && strncmp(azArg[1],"columns",n2)==0 ){
drh75897232000-05-29 14:26:00 +00002838 p->mode = MODE_Column;
drhc2ce0be2014-05-29 12:36:14 +00002839 }else if( c2=='l' && n2>2 && strncmp(azArg[1],"list",n2)==0 ){
drh75897232000-05-29 14:26:00 +00002840 p->mode = MODE_List;
drhc2ce0be2014-05-29 12:36:14 +00002841 }else if( c2=='h' && strncmp(azArg[1],"html",n2)==0 ){
drh1e5d0e92000-05-31 23:33:17 +00002842 p->mode = MODE_Html;
drhc2ce0be2014-05-29 12:36:14 +00002843 }else if( c2=='t' && strncmp(azArg[1],"tcl",n2)==0 ){
drhfeac5f82004-08-01 00:10:45 +00002844 p->mode = MODE_Tcl;
mistachkin585dcb22012-12-04 00:23:43 +00002845 sqlite3_snprintf(sizeof(p->separator), p->separator, " ");
drhc2ce0be2014-05-29 12:36:14 +00002846 }else if( c2=='c' && strncmp(azArg[1],"csv",n2)==0 ){
drh8e64d1c2004-10-07 00:32:39 +00002847 p->mode = MODE_Csv;
drh5bb3eb92007-05-04 13:15:55 +00002848 sqlite3_snprintf(sizeof(p->separator), p->separator, ",");
drh6976c212014-07-24 12:09:47 +00002849 sqlite3_snprintf(sizeof(p->newline), p->newline, "\r\n");
drhc2ce0be2014-05-29 12:36:14 +00002850 }else if( c2=='t' && strncmp(azArg[1],"tabs",n2)==0 ){
drhfeac5f82004-08-01 00:10:45 +00002851 p->mode = MODE_List;
drh5bb3eb92007-05-04 13:15:55 +00002852 sqlite3_snprintf(sizeof(p->separator), p->separator, "\t");
drhc2ce0be2014-05-29 12:36:14 +00002853 }else if( c2=='i' && strncmp(azArg[1],"insert",n2)==0 ){
drh28bd4bc2000-06-15 15:57:22 +00002854 p->mode = MODE_Insert;
drhc2ce0be2014-05-29 12:36:14 +00002855 set_table_name(p, nArg>=3 ? azArg[2] : "table");
drhdaffd0e2001-04-11 14:28:42 +00002856 }else {
shane9bd1b442009-10-23 01:27:39 +00002857 fprintf(stderr,"Error: mode should be one of: "
drhfeac5f82004-08-01 00:10:45 +00002858 "column csv html insert line list tabs tcl\n");
shane9bd1b442009-10-23 01:27:39 +00002859 rc = 1;
drh75897232000-05-29 14:26:00 +00002860 }
2861 }else
2862
drhc2ce0be2014-05-29 12:36:14 +00002863 if( c=='n' && strncmp(azArg[0], "nullvalue", n)==0 ){
2864 if( nArg==2 ){
2865 sqlite3_snprintf(sizeof(p->nullvalue), p->nullvalue,
2866 "%.*s", (int)ArraySize(p->nullvalue)-1, azArg[1]);
2867 }else{
2868 fprintf(stderr, "Usage: .nullvalue STRING\n");
shanehe2aa9d72009-11-06 17:20:17 +00002869 rc = 1;
2870 }
2871 }else
2872
drh05782482013-10-24 15:20:20 +00002873 if( c=='o' && strncmp(azArg[0], "open", n)==0 && n>=2 ){
2874 sqlite3 *savedDb = p->db;
2875 const char *zSavedFilename = p->zDbFilename;
2876 char *zNewFilename = 0;
2877 p->db = 0;
2878 if( nArg>=2 ){
2879 p->zDbFilename = zNewFilename = sqlite3_mprintf("%s", azArg[1]);
2880 }
2881 open_db(p, 1);
2882 if( p->db!=0 ){
2883 sqlite3_close(savedDb);
2884 sqlite3_free(p->zFreeOnClose);
2885 p->zFreeOnClose = zNewFilename;
2886 }else{
2887 sqlite3_free(zNewFilename);
2888 p->db = savedDb;
2889 p->zDbFilename = zSavedFilename;
2890 }
2891 }else
2892
drhc2ce0be2014-05-29 12:36:14 +00002893 if( c=='o'
2894 && (strncmp(azArg[0], "output", n)==0 || strncmp(azArg[0], "once", n)==0)
2895 ){
2896 const char *zFile = nArg>=2 ? azArg[1] : "stdout";
2897 if( nArg>2 ){
2898 fprintf(stderr, "Usage: .%s FILE\n", azArg[0]);
2899 rc = 1;
2900 goto meta_command_exit;
drh75897232000-05-29 14:26:00 +00002901 }
drhc2ce0be2014-05-29 12:36:14 +00002902 if( n>1 && strncmp(azArg[0], "once", n)==0 ){
2903 if( nArg<2 ){
2904 fprintf(stderr, "Usage: .once FILE\n");
2905 rc = 1;
2906 goto meta_command_exit;
2907 }
2908 p->outCount = 2;
2909 }else{
2910 p->outCount = 0;
2911 }
2912 output_reset(p);
2913 if( zFile[0]=='|' ){
2914 p->out = popen(zFile + 1, "w");
drhe1da8fa2012-03-30 00:05:57 +00002915 if( p->out==0 ){
drhc2ce0be2014-05-29 12:36:14 +00002916 fprintf(stderr,"Error: cannot open pipe \"%s\"\n", zFile + 1);
drhe1da8fa2012-03-30 00:05:57 +00002917 p->out = stdout;
2918 rc = 1;
2919 }else{
drhc2ce0be2014-05-29 12:36:14 +00002920 sqlite3_snprintf(sizeof(p->outfile), p->outfile, "%s", zFile);
drhe1da8fa2012-03-30 00:05:57 +00002921 }
drh75897232000-05-29 14:26:00 +00002922 }else{
drhc2ce0be2014-05-29 12:36:14 +00002923 p->out = output_file_open(zFile);
drh75897232000-05-29 14:26:00 +00002924 if( p->out==0 ){
drhc2ce0be2014-05-29 12:36:14 +00002925 if( strcmp(zFile,"off")!=0 ){
2926 fprintf(stderr,"Error: cannot write to \"%s\"\n", zFile);
drh42f64e52012-04-04 16:56:23 +00002927 }
drh75897232000-05-29 14:26:00 +00002928 p->out = stdout;
shane9bd1b442009-10-23 01:27:39 +00002929 rc = 1;
persicom7e2dfdd2002-04-18 02:46:52 +00002930 } else {
drhc2ce0be2014-05-29 12:36:14 +00002931 sqlite3_snprintf(sizeof(p->outfile), p->outfile, "%s", zFile);
drh75897232000-05-29 14:26:00 +00002932 }
2933 }
2934 }else
2935
drh078b1fd2012-09-21 13:40:02 +00002936 if( c=='p' && n>=3 && strncmp(azArg[0], "print", n)==0 ){
2937 int i;
2938 for(i=1; i<nArg; i++){
2939 if( i>1 ) fprintf(p->out, " ");
2940 fprintf(p->out, "%s", azArg[i]);
2941 }
2942 fprintf(p->out, "\n");
2943 }else
2944
drhc2ce0be2014-05-29 12:36:14 +00002945 if( c=='p' && strncmp(azArg[0], "prompt", n)==0 ){
persicom7e2dfdd2002-04-18 02:46:52 +00002946 if( nArg >= 2) {
2947 strncpy(mainPrompt,azArg[1],(int)ArraySize(mainPrompt)-1);
2948 }
2949 if( nArg >= 3) {
2950 strncpy(continuePrompt,azArg[2],(int)ArraySize(continuePrompt)-1);
2951 }
2952 }else
2953
drhc2ce0be2014-05-29 12:36:14 +00002954 if( c=='q' && strncmp(azArg[0], "quit", n)==0 ){
drh47ad6842006-11-08 12:25:42 +00002955 rc = 2;
persicom7e2dfdd2002-04-18 02:46:52 +00002956 }else
2957
drhc2ce0be2014-05-29 12:36:14 +00002958 if( c=='r' && n>=3 && strncmp(azArg[0], "read", n)==0 ){
2959 FILE *alt;
2960 if( nArg!=2 ){
2961 fprintf(stderr, "Usage: .read FILE\n");
2962 rc = 1;
2963 goto meta_command_exit;
2964 }
2965 alt = fopen(azArg[1], "rb");
drhdaffd0e2001-04-11 14:28:42 +00002966 if( alt==0 ){
shane9bd1b442009-10-23 01:27:39 +00002967 fprintf(stderr,"Error: cannot open \"%s\"\n", azArg[1]);
2968 rc = 1;
drhdaffd0e2001-04-11 14:28:42 +00002969 }else{
shane9bd1b442009-10-23 01:27:39 +00002970 rc = process_input(p, alt);
drhdaffd0e2001-04-11 14:28:42 +00002971 fclose(alt);
2972 }
2973 }else
2974
drhc2ce0be2014-05-29 12:36:14 +00002975 if( c=='r' && n>=3 && strncmp(azArg[0], "restore", n)==0 ){
drh9ff849f2009-02-04 20:55:57 +00002976 const char *zSrcFile;
2977 const char *zDb;
2978 sqlite3 *pSrc;
2979 sqlite3_backup *pBackup;
drhdc2c4912009-02-04 22:46:47 +00002980 int nTimeout = 0;
2981
drh9ff849f2009-02-04 20:55:57 +00002982 if( nArg==2 ){
2983 zSrcFile = azArg[1];
2984 zDb = "main";
drhc2ce0be2014-05-29 12:36:14 +00002985 }else if( nArg==3 ){
drh9ff849f2009-02-04 20:55:57 +00002986 zSrcFile = azArg[2];
2987 zDb = azArg[1];
drhc2ce0be2014-05-29 12:36:14 +00002988 }else{
2989 fprintf(stderr, "Usage: .restore ?DB? FILE\n");
2990 rc = 1;
2991 goto meta_command_exit;
drh9ff849f2009-02-04 20:55:57 +00002992 }
2993 rc = sqlite3_open(zSrcFile, &pSrc);
2994 if( rc!=SQLITE_OK ){
shane9bd1b442009-10-23 01:27:39 +00002995 fprintf(stderr, "Error: cannot open \"%s\"\n", zSrcFile);
drh9ff849f2009-02-04 20:55:57 +00002996 sqlite3_close(pSrc);
2997 return 1;
2998 }
drh05782482013-10-24 15:20:20 +00002999 open_db(p, 0);
drh9ff849f2009-02-04 20:55:57 +00003000 pBackup = sqlite3_backup_init(p->db, zDb, pSrc, "main");
3001 if( pBackup==0 ){
3002 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(p->db));
3003 sqlite3_close(pSrc);
3004 return 1;
3005 }
drhdc2c4912009-02-04 22:46:47 +00003006 while( (rc = sqlite3_backup_step(pBackup,100))==SQLITE_OK
3007 || rc==SQLITE_BUSY ){
3008 if( rc==SQLITE_BUSY ){
3009 if( nTimeout++ >= 3 ) break;
3010 sqlite3_sleep(100);
drh9ff849f2009-02-04 20:55:57 +00003011 }
3012 }
3013 sqlite3_backup_finish(pBackup);
3014 if( rc==SQLITE_DONE ){
shane9bd1b442009-10-23 01:27:39 +00003015 rc = 0;
drhdc2c4912009-02-04 22:46:47 +00003016 }else if( rc==SQLITE_BUSY || rc==SQLITE_LOCKED ){
shane9bd1b442009-10-23 01:27:39 +00003017 fprintf(stderr, "Error: source database is busy\n");
3018 rc = 1;
drh9ff849f2009-02-04 20:55:57 +00003019 }else{
3020 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(p->db));
shane9bd1b442009-10-23 01:27:39 +00003021 rc = 1;
drh9ff849f2009-02-04 20:55:57 +00003022 }
3023 sqlite3_close(pSrc);
3024 }else
3025
drhc2ce0be2014-05-29 12:36:14 +00003026 if( c=='s' && strncmp(azArg[0], "schema", n)==0 ){
drhdcd87a92014-08-18 13:45:42 +00003027 ShellState data;
drh75897232000-05-29 14:26:00 +00003028 char *zErrMsg = 0;
drh05782482013-10-24 15:20:20 +00003029 open_db(p, 0);
drh75897232000-05-29 14:26:00 +00003030 memcpy(&data, p, sizeof(data));
3031 data.showHeader = 0;
drhe3710332000-09-29 13:30:53 +00003032 data.mode = MODE_Semi;
drhc2ce0be2014-05-29 12:36:14 +00003033 if( nArg==2 ){
drhc8d74412004-08-31 23:41:26 +00003034 int i;
drhf0693c82011-10-11 20:41:54 +00003035 for(i=0; azArg[1][i]; i++) azArg[1][i] = ToLower(azArg[1][i]);
drhc8d74412004-08-31 23:41:26 +00003036 if( strcmp(azArg[1],"sqlite_master")==0 ){
drha18c5682000-10-08 22:20:57 +00003037 char *new_argv[2], *new_colv[2];
3038 new_argv[0] = "CREATE TABLE sqlite_master (\n"
3039 " type text,\n"
3040 " name text,\n"
3041 " tbl_name text,\n"
drhadbca9c2001-09-27 15:11:53 +00003042 " rootpage integer,\n"
drha18c5682000-10-08 22:20:57 +00003043 " sql text\n"
3044 ")";
3045 new_argv[1] = 0;
3046 new_colv[0] = "sql";
3047 new_colv[1] = 0;
3048 callback(&data, 1, new_argv, new_colv);
shane9bd1b442009-10-23 01:27:39 +00003049 rc = SQLITE_OK;
drhc8d74412004-08-31 23:41:26 +00003050 }else if( strcmp(azArg[1],"sqlite_temp_master")==0 ){
drhe0bc4042002-06-25 01:09:11 +00003051 char *new_argv[2], *new_colv[2];
3052 new_argv[0] = "CREATE TEMP TABLE sqlite_temp_master (\n"
3053 " type text,\n"
3054 " name text,\n"
3055 " tbl_name text,\n"
3056 " rootpage integer,\n"
3057 " sql text\n"
3058 ")";
3059 new_argv[1] = 0;
3060 new_colv[0] = "sql";
3061 new_colv[1] = 0;
3062 callback(&data, 1, new_argv, new_colv);
shane9bd1b442009-10-23 01:27:39 +00003063 rc = SQLITE_OK;
drha18c5682000-10-08 22:20:57 +00003064 }else{
danielk1977bc6ada42004-06-30 08:20:16 +00003065 zShellStatic = azArg[1];
shane9bd1b442009-10-23 01:27:39 +00003066 rc = sqlite3_exec(p->db,
drhe0bc4042002-06-25 01:09:11 +00003067 "SELECT sql FROM "
drhac43e982012-05-21 03:15:06 +00003068 " (SELECT sql sql, type type, tbl_name tbl_name, name name, rowid x"
drh8f800a72009-01-14 23:17:55 +00003069 " FROM sqlite_master UNION ALL"
drhac43e982012-05-21 03:15:06 +00003070 " SELECT sql, type, tbl_name, name, rowid FROM sqlite_temp_master) "
drh6ac7a582011-11-04 00:35:56 +00003071 "WHERE lower(tbl_name) LIKE shellstatic()"
3072 " AND type!='meta' AND sql NOTNULL "
drh1ba00292013-05-06 21:01:06 +00003073 "ORDER BY rowid",
danielk1977bc6ada42004-06-30 08:20:16 +00003074 callback, &data, &zErrMsg);
3075 zShellStatic = 0;
drha18c5682000-10-08 22:20:57 +00003076 }
drhc2ce0be2014-05-29 12:36:14 +00003077 }else if( nArg==1 ){
shane9bd1b442009-10-23 01:27:39 +00003078 rc = sqlite3_exec(p->db,
drhe0bc4042002-06-25 01:09:11 +00003079 "SELECT sql FROM "
drhac43e982012-05-21 03:15:06 +00003080 " (SELECT sql sql, type type, tbl_name tbl_name, name name, rowid x"
drh8f800a72009-01-14 23:17:55 +00003081 " FROM sqlite_master UNION ALL"
drhac43e982012-05-21 03:15:06 +00003082 " SELECT sql, type, tbl_name, name, rowid FROM sqlite_temp_master) "
drh4b2590e2014-08-19 19:28:00 +00003083 "WHERE type!='meta' AND sql NOTNULL AND name NOT LIKE 'sqlite_%' "
drh1ba00292013-05-06 21:01:06 +00003084 "ORDER BY rowid",
drha18c5682000-10-08 22:20:57 +00003085 callback, &data, &zErrMsg
3086 );
drhc2ce0be2014-05-29 12:36:14 +00003087 }else{
3088 fprintf(stderr, "Usage: .schema ?LIKE-PATTERN?\n");
3089 rc = 1;
3090 goto meta_command_exit;
drh75897232000-05-29 14:26:00 +00003091 }
drh75897232000-05-29 14:26:00 +00003092 if( zErrMsg ){
3093 fprintf(stderr,"Error: %s\n", zErrMsg);
drh3f4fedb2004-05-31 19:34:33 +00003094 sqlite3_free(zErrMsg);
shane9bd1b442009-10-23 01:27:39 +00003095 rc = 1;
3096 }else if( rc != SQLITE_OK ){
3097 fprintf(stderr,"Error: querying schema information\n");
3098 rc = 1;
3099 }else{
3100 rc = 0;
drh75897232000-05-29 14:26:00 +00003101 }
3102 }else
3103
drh340f5822013-06-27 13:01:21 +00003104#ifdef SQLITE_DEBUG
drh348d19c2013-06-03 12:47:43 +00003105 /* Undocumented commands for internal testing. Subject to change
3106 ** without notice. */
3107 if( c=='s' && n>=10 && strncmp(azArg[0], "selftest-", 9)==0 ){
3108 if( strncmp(azArg[0]+9, "boolean", n-9)==0 ){
3109 int i, v;
3110 for(i=1; i<nArg; i++){
3111 v = booleanValue(azArg[i]);
3112 fprintf(p->out, "%s: %d 0x%x\n", azArg[i], v, v);
3113 }
3114 }
3115 if( strncmp(azArg[0]+9, "integer", n-9)==0 ){
3116 int i; sqlite3_int64 v;
3117 for(i=1; i<nArg; i++){
drh340f5822013-06-27 13:01:21 +00003118 char zBuf[200];
drh348d19c2013-06-03 12:47:43 +00003119 v = integerValue(azArg[i]);
drhc2ce0be2014-05-29 12:36:14 +00003120 sqlite3_snprintf(sizeof(zBuf),zBuf,"%s: %lld 0x%llx\n", azArg[i],v,v);
drh340f5822013-06-27 13:01:21 +00003121 fprintf(p->out, "%s", zBuf);
drh348d19c2013-06-03 12:47:43 +00003122 }
3123 }
3124 }else
drh340f5822013-06-27 13:01:21 +00003125#endif
drh348d19c2013-06-03 12:47:43 +00003126
drhc2ce0be2014-05-29 12:36:14 +00003127 if( c=='s' && strncmp(azArg[0], "separator", n)==0 ){
drh6976c212014-07-24 12:09:47 +00003128 if( nArg<2 || nArg>3 ){
3129 fprintf(stderr, "Usage: .separator SEPARATOR ?NEWLINE?\n");
drhc2ce0be2014-05-29 12:36:14 +00003130 rc = 1;
3131 }
drh6976c212014-07-24 12:09:47 +00003132 if( nArg>=2 ){
3133 sqlite3_snprintf(sizeof(p->separator), p->separator, azArg[1]);
3134 }
3135 if( nArg>=3 ){
3136 sqlite3_snprintf(sizeof(p->newline), p->newline, azArg[2]);
3137 }
drh75897232000-05-29 14:26:00 +00003138 }else
3139
drh62cdde52014-05-28 20:22:28 +00003140 if( c=='s'
3141 && (strncmp(azArg[0], "shell", n)==0 || strncmp(azArg[0],"system",n)==0)
drh62cdde52014-05-28 20:22:28 +00003142 ){
3143 char *zCmd;
drh54027102014-08-06 14:36:53 +00003144 int i, x;
drhc2ce0be2014-05-29 12:36:14 +00003145 if( nArg<2 ){
3146 fprintf(stderr, "Usage: .system COMMAND\n");
3147 rc = 1;
3148 goto meta_command_exit;
3149 }
drhdcb3e3d2014-05-29 03:17:29 +00003150 zCmd = sqlite3_mprintf(strchr(azArg[1],' ')==0?"%s":"\"%s\"", azArg[1]);
drh62cdde52014-05-28 20:22:28 +00003151 for(i=2; i<nArg; i++){
drhdcb3e3d2014-05-29 03:17:29 +00003152 zCmd = sqlite3_mprintf(strchr(azArg[i],' ')==0?"%z %s":"%z \"%s\"",
3153 zCmd, azArg[i]);
drh62cdde52014-05-28 20:22:28 +00003154 }
drh54027102014-08-06 14:36:53 +00003155 x = system(zCmd);
drh62cdde52014-05-28 20:22:28 +00003156 sqlite3_free(zCmd);
drh54027102014-08-06 14:36:53 +00003157 if( x ) fprintf(stderr, "System command returns %d\n", x);
drh62cdde52014-05-28 20:22:28 +00003158 }else
3159
drhc2ce0be2014-05-29 12:36:14 +00003160 if( c=='s' && strncmp(azArg[0], "show", n)==0 ){
persicom7e2dfdd2002-04-18 02:46:52 +00003161 int i;
drhc2ce0be2014-05-29 12:36:14 +00003162 if( nArg!=1 ){
3163 fprintf(stderr, "Usage: .show\n");
3164 rc = 1;
3165 goto meta_command_exit;
3166 }
persicom7e2dfdd2002-04-18 02:46:52 +00003167 fprintf(p->out,"%9.9s: %s\n","echo", p->echoOn ? "on" : "off");
drhefbf3b12014-02-28 20:47:24 +00003168 fprintf(p->out,"%9.9s: %s\n","eqp", p->autoEQP ? "on" : "off");
drhdcd87a92014-08-18 13:45:42 +00003169 fprintf(p->out,"%9.9s: %s\n","explain", p->normalMode.valid ? "on" :"off");
drhdd45df82002-04-18 12:39:03 +00003170 fprintf(p->out,"%9.9s: %s\n","headers", p->showHeader ? "on" : "off");
persicom7e2dfdd2002-04-18 02:46:52 +00003171 fprintf(p->out,"%9.9s: %s\n","mode", modeDescr[p->mode]);
drhfeac5f82004-08-01 00:10:45 +00003172 fprintf(p->out,"%9.9s: ", "nullvalue");
3173 output_c_string(p->out, p->nullvalue);
3174 fprintf(p->out, "\n");
drh67505e72002-04-19 12:34:06 +00003175 fprintf(p->out,"%9.9s: %s\n","output",
drh4f21c4a2008-12-10 22:15:00 +00003176 strlen30(p->outfile) ? p->outfile : "stdout");
drhfeac5f82004-08-01 00:10:45 +00003177 fprintf(p->out,"%9.9s: ", "separator");
3178 output_c_string(p->out, p->separator);
drh6976c212014-07-24 12:09:47 +00003179 fprintf(p->out," ");
3180 output_c_string(p->out, p->newline);
drhfeac5f82004-08-01 00:10:45 +00003181 fprintf(p->out, "\n");
shaneh642d8b82010-07-28 16:05:34 +00003182 fprintf(p->out,"%9.9s: %s\n","stats", p->statsOn ? "on" : "off");
persicom7e2dfdd2002-04-18 02:46:52 +00003183 fprintf(p->out,"%9.9s: ","width");
3184 for (i=0;i<(int)ArraySize(p->colWidth) && p->colWidth[i] != 0;i++) {
drhfeac5f82004-08-01 00:10:45 +00003185 fprintf(p->out,"%d ",p->colWidth[i]);
persicom7e2dfdd2002-04-18 02:46:52 +00003186 }
drhfeac5f82004-08-01 00:10:45 +00003187 fprintf(p->out,"\n");
persicom7e2dfdd2002-04-18 02:46:52 +00003188 }else
3189
drhc2ce0be2014-05-29 12:36:14 +00003190 if( c=='s' && strncmp(azArg[0], "stats", n)==0 ){
3191 if( nArg==2 ){
3192 p->statsOn = booleanValue(azArg[1]);
3193 }else{
3194 fprintf(stderr, "Usage: .stats on|off\n");
3195 rc = 1;
3196 }
shaneh642d8b82010-07-28 16:05:34 +00003197 }else
3198
drhc2ce0be2014-05-29 12:36:14 +00003199 if( c=='t' && n>1 && strncmp(azArg[0], "tables", n)==0 ){
drh98781232012-04-23 12:38:05 +00003200 sqlite3_stmt *pStmt;
drhe3710332000-09-29 13:30:53 +00003201 char **azResult;
drh98781232012-04-23 12:38:05 +00003202 int nRow, nAlloc;
3203 char *zSql = 0;
3204 int ii;
drh05782482013-10-24 15:20:20 +00003205 open_db(p, 0);
drh98781232012-04-23 12:38:05 +00003206 rc = sqlite3_prepare_v2(p->db, "PRAGMA database_list", -1, &pStmt, 0);
3207 if( rc ) return rc;
3208 zSql = sqlite3_mprintf(
3209 "SELECT name FROM sqlite_master"
3210 " WHERE type IN ('table','view')"
3211 " AND name NOT LIKE 'sqlite_%%'"
3212 " AND name LIKE ?1");
3213 while( sqlite3_step(pStmt)==SQLITE_ROW ){
3214 const char *zDbName = (const char*)sqlite3_column_text(pStmt, 1);
3215 if( zDbName==0 || strcmp(zDbName,"main")==0 ) continue;
3216 if( strcmp(zDbName,"temp")==0 ){
3217 zSql = sqlite3_mprintf(
3218 "%z UNION ALL "
3219 "SELECT 'temp.' || name FROM sqlite_temp_master"
3220 " WHERE type IN ('table','view')"
3221 " AND name NOT LIKE 'sqlite_%%'"
3222 " AND name LIKE ?1", zSql);
3223 }else{
3224 zSql = sqlite3_mprintf(
3225 "%z UNION ALL "
3226 "SELECT '%q.' || name FROM \"%w\".sqlite_master"
3227 " WHERE type IN ('table','view')"
3228 " AND name NOT LIKE 'sqlite_%%'"
3229 " AND name LIKE ?1", zSql, zDbName, zDbName);
3230 }
drha50da102000-08-08 20:19:09 +00003231 }
drh98781232012-04-23 12:38:05 +00003232 sqlite3_finalize(pStmt);
3233 zSql = sqlite3_mprintf("%z ORDER BY 1", zSql);
3234 rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
3235 sqlite3_free(zSql);
3236 if( rc ) return rc;
3237 nRow = nAlloc = 0;
3238 azResult = 0;
3239 if( nArg>1 ){
3240 sqlite3_bind_text(pStmt, 1, azArg[1], -1, SQLITE_TRANSIENT);
shane9bd1b442009-10-23 01:27:39 +00003241 }else{
drh98781232012-04-23 12:38:05 +00003242 sqlite3_bind_text(pStmt, 1, "%", -1, SQLITE_STATIC);
3243 }
3244 while( sqlite3_step(pStmt)==SQLITE_ROW ){
3245 if( nRow>=nAlloc ){
3246 char **azNew;
3247 int n = nAlloc*2 + 10;
3248 azNew = sqlite3_realloc(azResult, sizeof(azResult[0])*n);
3249 if( azNew==0 ){
3250 fprintf(stderr, "Error: out of memory\n");
3251 break;
3252 }
3253 nAlloc = n;
3254 azResult = azNew;
3255 }
3256 azResult[nRow] = sqlite3_mprintf("%s", sqlite3_column_text(pStmt, 0));
3257 if( azResult[nRow] ) nRow++;
3258 }
3259 sqlite3_finalize(pStmt);
3260 if( nRow>0 ){
drhe3710332000-09-29 13:30:53 +00003261 int len, maxlen = 0;
3262 int i, j;
3263 int nPrintCol, nPrintRow;
drh98781232012-04-23 12:38:05 +00003264 for(i=0; i<nRow; i++){
drh4f21c4a2008-12-10 22:15:00 +00003265 len = strlen30(azResult[i]);
drhe3710332000-09-29 13:30:53 +00003266 if( len>maxlen ) maxlen = len;
3267 }
3268 nPrintCol = 80/(maxlen+2);
3269 if( nPrintCol<1 ) nPrintCol = 1;
3270 nPrintRow = (nRow + nPrintCol - 1)/nPrintCol;
3271 for(i=0; i<nPrintRow; i++){
drh98781232012-04-23 12:38:05 +00003272 for(j=i; j<nRow; j+=nPrintRow){
3273 char *zSp = j<nPrintRow ? "" : " ";
drh151b7d52013-05-06 20:28:54 +00003274 fprintf(p->out, "%s%-*s", zSp, maxlen, azResult[j] ? azResult[j] : "");
drhe3710332000-09-29 13:30:53 +00003275 }
drh151b7d52013-05-06 20:28:54 +00003276 fprintf(p->out, "\n");
drhe3710332000-09-29 13:30:53 +00003277 }
3278 }
drh98781232012-04-23 12:38:05 +00003279 for(ii=0; ii<nRow; ii++) sqlite3_free(azResult[ii]);
3280 sqlite3_free(azResult);
drh75897232000-05-29 14:26:00 +00003281 }else
3282
shaneh96887e12011-02-10 21:08:58 +00003283 if( c=='t' && n>=8 && strncmp(azArg[0], "testctrl", n)==0 && nArg>=2 ){
drhd416fe72011-03-17 16:45:50 +00003284 static const struct {
3285 const char *zCtrlName; /* Name of a test-control option */
3286 int ctrlCode; /* Integer code for that option */
3287 } aCtrl[] = {
3288 { "prng_save", SQLITE_TESTCTRL_PRNG_SAVE },
3289 { "prng_restore", SQLITE_TESTCTRL_PRNG_RESTORE },
3290 { "prng_reset", SQLITE_TESTCTRL_PRNG_RESET },
3291 { "bitvec_test", SQLITE_TESTCTRL_BITVEC_TEST },
3292 { "fault_install", SQLITE_TESTCTRL_FAULT_INSTALL },
3293 { "benign_malloc_hooks", SQLITE_TESTCTRL_BENIGN_MALLOC_HOOKS },
3294 { "pending_byte", SQLITE_TESTCTRL_PENDING_BYTE },
3295 { "assert", SQLITE_TESTCTRL_ASSERT },
3296 { "always", SQLITE_TESTCTRL_ALWAYS },
3297 { "reserve", SQLITE_TESTCTRL_RESERVE },
3298 { "optimizations", SQLITE_TESTCTRL_OPTIMIZATIONS },
3299 { "iskeyword", SQLITE_TESTCTRL_ISKEYWORD },
drhd416fe72011-03-17 16:45:50 +00003300 { "scratchmalloc", SQLITE_TESTCTRL_SCRATCHMALLOC },
drh2cf4acb2014-04-18 00:06:02 +00003301 { "byteorder", SQLITE_TESTCTRL_BYTEORDER },
drhd416fe72011-03-17 16:45:50 +00003302 };
shaneh96887e12011-02-10 21:08:58 +00003303 int testctrl = -1;
3304 int rc = 0;
drhd416fe72011-03-17 16:45:50 +00003305 int i, n;
drh05782482013-10-24 15:20:20 +00003306 open_db(p, 0);
shaneh96887e12011-02-10 21:08:58 +00003307
drhd416fe72011-03-17 16:45:50 +00003308 /* convert testctrl text option to value. allow any unique prefix
3309 ** of the option name, or a numerical value. */
shanehcef83682011-04-07 03:41:01 +00003310 n = strlen30(azArg[1]);
drhfcd71b62011-04-05 22:08:24 +00003311 for(i=0; i<(int)(sizeof(aCtrl)/sizeof(aCtrl[0])); i++){
drhd416fe72011-03-17 16:45:50 +00003312 if( strncmp(azArg[1], aCtrl[i].zCtrlName, n)==0 ){
3313 if( testctrl<0 ){
3314 testctrl = aCtrl[i].ctrlCode;
3315 }else{
drhb07028f2011-10-14 21:49:18 +00003316 fprintf(stderr, "ambiguous option name: \"%s\"\n", azArg[1]);
drhd416fe72011-03-17 16:45:50 +00003317 testctrl = -1;
3318 break;
3319 }
3320 }
3321 }
drh348d19c2013-06-03 12:47:43 +00003322 if( testctrl<0 ) testctrl = (int)integerValue(azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003323 if( (testctrl<SQLITE_TESTCTRL_FIRST) || (testctrl>SQLITE_TESTCTRL_LAST) ){
3324 fprintf(stderr,"Error: invalid testctrl option: %s\n", azArg[1]);
3325 }else{
3326 switch(testctrl){
3327
3328 /* sqlite3_test_control(int, db, int) */
3329 case SQLITE_TESTCTRL_OPTIMIZATIONS:
3330 case SQLITE_TESTCTRL_RESERVE:
3331 if( nArg==3 ){
3332 int opt = (int)strtol(azArg[2], 0, 0);
3333 rc = sqlite3_test_control(testctrl, p->db, opt);
drh151b7d52013-05-06 20:28:54 +00003334 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003335 } else {
drhd416fe72011-03-17 16:45:50 +00003336 fprintf(stderr,"Error: testctrl %s takes a single int option\n",
3337 azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003338 }
3339 break;
3340
3341 /* sqlite3_test_control(int) */
drh2cf4acb2014-04-18 00:06:02 +00003342 case SQLITE_TESTCTRL_PRNG_SAVE:
3343 case SQLITE_TESTCTRL_PRNG_RESTORE:
shaneh96887e12011-02-10 21:08:58 +00003344 case SQLITE_TESTCTRL_PRNG_RESET:
drh2cf4acb2014-04-18 00:06:02 +00003345 case SQLITE_TESTCTRL_BYTEORDER:
shaneh96887e12011-02-10 21:08:58 +00003346 if( nArg==2 ){
3347 rc = sqlite3_test_control(testctrl);
drh151b7d52013-05-06 20:28:54 +00003348 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003349 } else {
3350 fprintf(stderr,"Error: testctrl %s takes no options\n", azArg[1]);
3351 }
3352 break;
3353
3354 /* sqlite3_test_control(int, uint) */
3355 case SQLITE_TESTCTRL_PENDING_BYTE:
3356 if( nArg==3 ){
drhaf664332013-07-18 20:28:29 +00003357 unsigned int opt = (unsigned int)integerValue(azArg[2]);
shaneh96887e12011-02-10 21:08:58 +00003358 rc = sqlite3_test_control(testctrl, opt);
drh151b7d52013-05-06 20:28:54 +00003359 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003360 } else {
drhd416fe72011-03-17 16:45:50 +00003361 fprintf(stderr,"Error: testctrl %s takes a single unsigned"
3362 " int option\n", azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003363 }
3364 break;
3365
3366 /* sqlite3_test_control(int, int) */
3367 case SQLITE_TESTCTRL_ASSERT:
3368 case SQLITE_TESTCTRL_ALWAYS:
3369 if( nArg==3 ){
drh348d19c2013-06-03 12:47:43 +00003370 int opt = booleanValue(azArg[2]);
shaneh96887e12011-02-10 21:08:58 +00003371 rc = sqlite3_test_control(testctrl, opt);
drh151b7d52013-05-06 20:28:54 +00003372 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003373 } else {
drhd416fe72011-03-17 16:45:50 +00003374 fprintf(stderr,"Error: testctrl %s takes a single int option\n",
3375 azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003376 }
3377 break;
3378
3379 /* sqlite3_test_control(int, char *) */
3380#ifdef SQLITE_N_KEYWORD
3381 case SQLITE_TESTCTRL_ISKEYWORD:
3382 if( nArg==3 ){
3383 const char *opt = azArg[2];
3384 rc = sqlite3_test_control(testctrl, opt);
drh151b7d52013-05-06 20:28:54 +00003385 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003386 } else {
drhd416fe72011-03-17 16:45:50 +00003387 fprintf(stderr,"Error: testctrl %s takes a single char * option\n",
3388 azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003389 }
3390 break;
3391#endif
3392
3393 case SQLITE_TESTCTRL_BITVEC_TEST:
3394 case SQLITE_TESTCTRL_FAULT_INSTALL:
3395 case SQLITE_TESTCTRL_BENIGN_MALLOC_HOOKS:
3396 case SQLITE_TESTCTRL_SCRATCHMALLOC:
3397 default:
drhd416fe72011-03-17 16:45:50 +00003398 fprintf(stderr,"Error: CLI support for testctrl %s not implemented\n",
3399 azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003400 break;
3401 }
3402 }
3403 }else
3404
drhc2ce0be2014-05-29 12:36:14 +00003405 if( c=='t' && n>4 && strncmp(azArg[0], "timeout", n)==0 ){
drh05782482013-10-24 15:20:20 +00003406 open_db(p, 0);
drhc2ce0be2014-05-29 12:36:14 +00003407 sqlite3_busy_timeout(p->db, nArg>=2 ? (int)integerValue(azArg[1]) : 0);
shanehe2aa9d72009-11-06 17:20:17 +00003408 }else
3409
drhc2ce0be2014-05-29 12:36:14 +00003410 if( c=='t' && n>=5 && strncmp(azArg[0], "timer", n)==0 ){
3411 if( nArg==2 ){
3412 enableTimer = booleanValue(azArg[1]);
3413 if( enableTimer && !HAS_TIMER ){
3414 fprintf(stderr, "Error: timer not available on this system.\n");
3415 enableTimer = 0;
3416 }
3417 }else{
3418 fprintf(stderr, "Usage: .timer on|off\n");
3419 rc = 1;
3420 }
shanehe2aa9d72009-11-06 17:20:17 +00003421 }else
3422
drhc2ce0be2014-05-29 12:36:14 +00003423 if( c=='t' && strncmp(azArg[0], "trace", n)==0 ){
drh05782482013-10-24 15:20:20 +00003424 open_db(p, 0);
drh42f64e52012-04-04 16:56:23 +00003425 output_file_close(p->traceOut);
drhc2ce0be2014-05-29 12:36:14 +00003426 if( nArg!=2 ){
3427 fprintf(stderr, "Usage: .trace FILE|off\n");
3428 rc = 1;
3429 goto meta_command_exit;
3430 }
drh42f64e52012-04-04 16:56:23 +00003431 p->traceOut = output_file_open(azArg[1]);
drhbbb0be82012-06-27 16:12:27 +00003432#if !defined(SQLITE_OMIT_TRACE) && !defined(SQLITE_OMIT_FLOATING_POINT)
drh42f64e52012-04-04 16:56:23 +00003433 if( p->traceOut==0 ){
3434 sqlite3_trace(p->db, 0, 0);
3435 }else{
3436 sqlite3_trace(p->db, sql_trace_callback, p->traceOut);
3437 }
3438#endif
3439 }else
3440
drhf442e332014-09-10 19:01:14 +00003441#if SQLITE_USER_AUTHENTICATION
3442 if( c=='u' && strncmp(azArg[0], "user", n)==0 ){
3443 if( nArg<2 ){
3444 fprintf(stderr, "Usage: .user SUBCOMMAND ...\n");
3445 rc = 1;
3446 goto meta_command_exit;
3447 }
drh7883ecf2014-09-11 16:19:31 +00003448 open_db(p, 0);
drhf442e332014-09-10 19:01:14 +00003449 if( strcmp(azArg[1],"login")==0 ){
3450 if( nArg!=4 ){
3451 fprintf(stderr, "Usage: .user login USER PASSWORD\n");
3452 rc = 1;
3453 goto meta_command_exit;
3454 }
drhd39c40f2014-09-11 00:27:53 +00003455 rc = sqlite3_user_authenticate(p->db, azArg[2], azArg[3],
3456 (int)strlen(azArg[3]));
drhf442e332014-09-10 19:01:14 +00003457 if( rc ){
3458 fprintf(stderr, "Authentication failed for user %s\n", azArg[2]);
3459 rc = 1;
3460 }
3461 }else if( strcmp(azArg[1],"add")==0 ){
3462 if( nArg!=5 ){
drhd39c40f2014-09-11 00:27:53 +00003463 fprintf(stderr, "Usage: .user add USER PASSWORD ISADMIN\n");
drhf442e332014-09-10 19:01:14 +00003464 rc = 1;
3465 goto meta_command_exit;
3466 }
drhd39c40f2014-09-11 00:27:53 +00003467 rc = sqlite3_user_add(p->db, azArg[2],
3468 azArg[3], (int)strlen(azArg[3]),
3469 booleanValue(azArg[4]));
drhf442e332014-09-10 19:01:14 +00003470 if( rc ){
3471 fprintf(stderr, "User-Add failed: %d\n", rc);
3472 rc = 1;
3473 }
3474 }else if( strcmp(azArg[1],"edit")==0 ){
3475 if( nArg!=5 ){
drhd39c40f2014-09-11 00:27:53 +00003476 fprintf(stderr, "Usage: .user edit USER PASSWORD ISADMIN\n");
drhf442e332014-09-10 19:01:14 +00003477 rc = 1;
3478 goto meta_command_exit;
3479 }
drhd39c40f2014-09-11 00:27:53 +00003480 rc = sqlite3_user_change(p->db, azArg[2],
3481 azArg[3], (int)strlen(azArg[3]),
3482 booleanValue(azArg[4]));
drhf442e332014-09-10 19:01:14 +00003483 if( rc ){
3484 fprintf(stderr, "User-Edit failed: %d\n", rc);
3485 rc = 1;
3486 }
3487 }else if( strcmp(azArg[1],"delete")==0 ){
3488 if( nArg!=3 ){
3489 fprintf(stderr, "Usage: .user delete USER\n");
3490 rc = 1;
3491 goto meta_command_exit;
3492 }
3493 rc = sqlite3_user_delete(p->db, azArg[2]);
3494 if( rc ){
3495 fprintf(stderr, "User-Delete failed: %d\n", rc);
3496 rc = 1;
3497 }
3498 }else{
3499 fprintf(stderr, "Usage: .user login|add|edit|delete ...\n");
3500 rc = 1;
3501 goto meta_command_exit;
3502 }
3503 }else
3504#endif /* SQLITE_USER_AUTHENTICATION */
3505
drh9fd301b2011-06-03 13:28:22 +00003506 if( c=='v' && strncmp(azArg[0], "version", n)==0 ){
drh151b7d52013-05-06 20:28:54 +00003507 fprintf(p->out, "SQLite %s %s\n" /*extra-version-info*/,
drh9fd301b2011-06-03 13:28:22 +00003508 sqlite3_libversion(), sqlite3_sourceid());
3509 }else
3510
drhde60fc22011-12-14 17:53:36 +00003511 if( c=='v' && strncmp(azArg[0], "vfsname", n)==0 ){
3512 const char *zDbName = nArg==2 ? azArg[1] : "main";
3513 char *zVfsName = 0;
3514 if( p->db ){
3515 sqlite3_file_control(p->db, zDbName, SQLITE_FCNTL_VFSNAME, &zVfsName);
3516 if( zVfsName ){
drh151b7d52013-05-06 20:28:54 +00003517 fprintf(p->out, "%s\n", zVfsName);
drhde60fc22011-12-14 17:53:36 +00003518 sqlite3_free(zVfsName);
3519 }
3520 }
3521 }else
3522
drhcef4fc82012-09-21 22:50:45 +00003523#if defined(SQLITE_DEBUG) && defined(SQLITE_ENABLE_WHERETRACE)
3524 if( c=='w' && strncmp(azArg[0], "wheretrace", n)==0 ){
3525 extern int sqlite3WhereTrace;
drhc2ce0be2014-05-29 12:36:14 +00003526 sqlite3WhereTrace = nArg>=2 ? booleanValue(azArg[1]) : 0xff;
drhcef4fc82012-09-21 22:50:45 +00003527 }else
3528#endif
3529
drhc2ce0be2014-05-29 12:36:14 +00003530 if( c=='w' && strncmp(azArg[0], "width", n)==0 ){
drh75897232000-05-29 14:26:00 +00003531 int j;
drh43617e92006-03-06 20:55:46 +00003532 assert( nArg<=ArraySize(azArg) );
drh75897232000-05-29 14:26:00 +00003533 for(j=1; j<nArg && j<ArraySize(p->colWidth); j++){
drh348d19c2013-06-03 12:47:43 +00003534 p->colWidth[j-1] = (int)integerValue(azArg[j]);
drh75897232000-05-29 14:26:00 +00003535 }
3536 }else
3537
3538 {
shane9bd1b442009-10-23 01:27:39 +00003539 fprintf(stderr, "Error: unknown command or invalid arguments: "
drh67505e72002-04-19 12:34:06 +00003540 " \"%s\". Enter \".help\" for help\n", azArg[0]);
shane9bd1b442009-10-23 01:27:39 +00003541 rc = 1;
drh75897232000-05-29 14:26:00 +00003542 }
drh67505e72002-04-19 12:34:06 +00003543
drhc2ce0be2014-05-29 12:36:14 +00003544meta_command_exit:
3545 if( p->outCount ){
3546 p->outCount--;
3547 if( p->outCount==0 ) output_reset(p);
3548 }
drh67505e72002-04-19 12:34:06 +00003549 return rc;
drh75897232000-05-29 14:26:00 +00003550}
3551
drh67505e72002-04-19 12:34:06 +00003552/*
drh91a66392007-09-07 01:12:32 +00003553** Return TRUE if a semicolon occurs anywhere in the first N characters
3554** of string z[].
drh324ccef2003-02-05 14:06:20 +00003555*/
drh9f099fd2013-08-06 14:01:46 +00003556static int line_contains_semicolon(const char *z, int N){
drh91a66392007-09-07 01:12:32 +00003557 int i;
3558 for(i=0; i<N; i++){ if( z[i]==';' ) return 1; }
3559 return 0;
drh324ccef2003-02-05 14:06:20 +00003560}
3561
3562/*
drh70c7a4b2003-04-26 03:03:06 +00003563** Test to see if a line consists entirely of whitespace.
3564*/
3565static int _all_whitespace(const char *z){
3566 for(; *z; z++){
drhf0693c82011-10-11 20:41:54 +00003567 if( IsSpace(z[0]) ) continue;
drh70c7a4b2003-04-26 03:03:06 +00003568 if( *z=='/' && z[1]=='*' ){
3569 z += 2;
3570 while( *z && (*z!='*' || z[1]!='/') ){ z++; }
3571 if( *z==0 ) return 0;
3572 z++;
3573 continue;
3574 }
3575 if( *z=='-' && z[1]=='-' ){
3576 z += 2;
3577 while( *z && *z!='\n' ){ z++; }
3578 if( *z==0 ) return 1;
3579 continue;
3580 }
3581 return 0;
3582 }
3583 return 1;
3584}
3585
3586/*
drha9b17162003-04-29 18:01:28 +00003587** Return TRUE if the line typed in is an SQL command terminator other
3588** than a semi-colon. The SQL Server style "go" command is understood
3589** as is the Oracle "/".
3590*/
drh9f099fd2013-08-06 14:01:46 +00003591static int line_is_command_terminator(const char *zLine){
drhf0693c82011-10-11 20:41:54 +00003592 while( IsSpace(zLine[0]) ){ zLine++; };
drh233a5312008-12-18 22:25:13 +00003593 if( zLine[0]=='/' && _all_whitespace(&zLine[1]) ){
3594 return 1; /* Oracle */
3595 }
drhf0693c82011-10-11 20:41:54 +00003596 if( ToLower(zLine[0])=='g' && ToLower(zLine[1])=='o'
drhc8d74412004-08-31 23:41:26 +00003597 && _all_whitespace(&zLine[2]) ){
drha9b17162003-04-29 18:01:28 +00003598 return 1; /* SQL Server */
3599 }
3600 return 0;
3601}
3602
3603/*
drh233a5312008-12-18 22:25:13 +00003604** Return true if zSql is a complete SQL statement. Return false if it
3605** ends in the middle of a string literal or C-style comment.
3606*/
drh9f099fd2013-08-06 14:01:46 +00003607static int line_is_complete(char *zSql, int nSql){
drh233a5312008-12-18 22:25:13 +00003608 int rc;
3609 if( zSql==0 ) return 1;
3610 zSql[nSql] = ';';
3611 zSql[nSql+1] = 0;
3612 rc = sqlite3_complete(zSql);
3613 zSql[nSql] = 0;
3614 return rc;
3615}
3616
3617/*
drh67505e72002-04-19 12:34:06 +00003618** Read input from *in and process it. If *in==0 then input
3619** is interactive - the user is typing it it. Otherwise, input
3620** is coming from a file or device. A prompt is issued and history
3621** is saved only if input is interactive. An interrupt signal will
3622** cause this routine to exit immediately, unless input is interactive.
drhc28490c2006-10-26 14:25:58 +00003623**
3624** Return the number of errors.
drh67505e72002-04-19 12:34:06 +00003625*/
drhdcd87a92014-08-18 13:45:42 +00003626static int process_input(ShellState *p, FILE *in){
drh9f099fd2013-08-06 14:01:46 +00003627 char *zLine = 0; /* A single input line */
3628 char *zSql = 0; /* Accumulated SQL text */
3629 int nLine; /* Length of current line */
3630 int nSql = 0; /* Bytes of zSql[] used */
3631 int nAlloc = 0; /* Allocated zSql[] space */
3632 int nSqlPrior = 0; /* Bytes of zSql[] used by prior line */
3633 char *zErrMsg; /* Error message returned */
3634 int rc; /* Error code */
3635 int errCnt = 0; /* Number of errors seen */
3636 int lineno = 0; /* Current line number */
3637 int startline = 0; /* Line number for start of current input */
drhc49f44e2006-10-26 18:15:42 +00003638
3639 while( errCnt==0 || !bail_on_error || (in==0 && stdin_is_interactive) ){
3640 fflush(p->out);
drh9f099fd2013-08-06 14:01:46 +00003641 zLine = one_input_line(in, zLine, nSql>0);
drhc49f44e2006-10-26 18:15:42 +00003642 if( zLine==0 ){
drh9b8d3572012-04-21 11:33:39 +00003643 /* End of input */
3644 if( stdin_is_interactive ) printf("\n");
3645 break;
drhc49f44e2006-10-26 18:15:42 +00003646 }
drh67505e72002-04-19 12:34:06 +00003647 if( seenInterrupt ){
3648 if( in!=0 ) break;
3649 seenInterrupt = 0;
3650 }
drhc28490c2006-10-26 14:25:58 +00003651 lineno++;
drh849a9d92013-12-21 15:46:06 +00003652 if( nSql==0 && _all_whitespace(zLine) ){
3653 if( p->echoOn ) printf("%s\n", zLine);
3654 continue;
3655 }
drh2af0b2d2002-02-21 02:25:02 +00003656 if( zLine && zLine[0]=='.' && nSql==0 ){
shaneb9fc17d2009-10-22 21:23:35 +00003657 if( p->echoOn ) printf("%s\n", zLine);
drhc49f44e2006-10-26 18:15:42 +00003658 rc = do_meta_command(zLine, p);
shane916f9612009-10-23 00:37:15 +00003659 if( rc==2 ){ /* exit requested */
drh47ad6842006-11-08 12:25:42 +00003660 break;
3661 }else if( rc ){
drhc49f44e2006-10-26 18:15:42 +00003662 errCnt++;
3663 }
drhdaffd0e2001-04-11 14:28:42 +00003664 continue;
3665 }
drh9f099fd2013-08-06 14:01:46 +00003666 if( line_is_command_terminator(zLine) && line_is_complete(zSql, nSql) ){
drh5bb3eb92007-05-04 13:15:55 +00003667 memcpy(zLine,";",2);
drha9b17162003-04-29 18:01:28 +00003668 }
drh9f099fd2013-08-06 14:01:46 +00003669 nLine = strlen30(zLine);
3670 if( nSql+nLine+2>=nAlloc ){
3671 nAlloc = nSql+nLine+100;
3672 zSql = realloc(zSql, nAlloc);
drhdaffd0e2001-04-11 14:28:42 +00003673 if( zSql==0 ){
drh9f099fd2013-08-06 14:01:46 +00003674 fprintf(stderr, "Error: out of memory\n");
drhdaffd0e2001-04-11 14:28:42 +00003675 exit(1);
3676 }
drhdaffd0e2001-04-11 14:28:42 +00003677 }
drh9f099fd2013-08-06 14:01:46 +00003678 nSqlPrior = nSql;
3679 if( nSql==0 ){
3680 int i;
3681 for(i=0; zLine[i] && IsSpace(zLine[i]); i++){}
drh77dfd5b2013-08-19 11:15:48 +00003682 assert( nAlloc>0 && zSql!=0 );
drh9f099fd2013-08-06 14:01:46 +00003683 memcpy(zSql, zLine+i, nLine+1-i);
3684 startline = lineno;
3685 nSql = nLine-i;
3686 }else{
3687 zSql[nSql++] = '\n';
3688 memcpy(zSql+nSql, zLine, nLine+1);
3689 nSql += nLine;
3690 }
3691 if( nSql && line_contains_semicolon(&zSql[nSqlPrior], nSql-nSqlPrior)
drh91a66392007-09-07 01:12:32 +00003692 && sqlite3_complete(zSql) ){
drhdaffd0e2001-04-11 14:28:42 +00003693 p->cnt = 0;
drh05782482013-10-24 15:20:20 +00003694 open_db(p, 0);
drh3b1a9882007-11-02 12:53:03 +00003695 BEGIN_TIMER;
shane626a6e42009-10-22 17:30:15 +00003696 rc = shell_exec(p->db, zSql, shell_callback, p, &zErrMsg);
drh3b1a9882007-11-02 12:53:03 +00003697 END_TIMER;
drh7f953e22002-07-13 17:33:45 +00003698 if( rc || zErrMsg ){
drhc28490c2006-10-26 14:25:58 +00003699 char zPrefix[100];
3700 if( in!=0 || !stdin_is_interactive ){
drh5bb3eb92007-05-04 13:15:55 +00003701 sqlite3_snprintf(sizeof(zPrefix), zPrefix,
shane9bd1b442009-10-23 01:27:39 +00003702 "Error: near line %d:", startline);
drhc28490c2006-10-26 14:25:58 +00003703 }else{
shane9bd1b442009-10-23 01:27:39 +00003704 sqlite3_snprintf(sizeof(zPrefix), zPrefix, "Error:");
drhc28490c2006-10-26 14:25:58 +00003705 }
drh7f953e22002-07-13 17:33:45 +00003706 if( zErrMsg!=0 ){
shaned2bed1c2009-10-21 03:56:54 +00003707 fprintf(stderr, "%s %s\n", zPrefix, zErrMsg);
drh3f4fedb2004-05-31 19:34:33 +00003708 sqlite3_free(zErrMsg);
drh7f953e22002-07-13 17:33:45 +00003709 zErrMsg = 0;
3710 }else{
shaned2bed1c2009-10-21 03:56:54 +00003711 fprintf(stderr, "%s %s\n", zPrefix, sqlite3_errmsg(p->db));
drh7f953e22002-07-13 17:33:45 +00003712 }
drhc49f44e2006-10-26 18:15:42 +00003713 errCnt++;
drhdaffd0e2001-04-11 14:28:42 +00003714 }
drhdaffd0e2001-04-11 14:28:42 +00003715 nSql = 0;
drhc2ce0be2014-05-29 12:36:14 +00003716 if( p->outCount ){
3717 output_reset(p);
3718 p->outCount = 0;
3719 }
drh9f099fd2013-08-06 14:01:46 +00003720 }else if( nSql && _all_whitespace(zSql) ){
drh849a9d92013-12-21 15:46:06 +00003721 if( p->echoOn ) printf("%s\n", zSql);
drh7a411f42013-04-17 17:33:17 +00003722 nSql = 0;
drhdaffd0e2001-04-11 14:28:42 +00003723 }
3724 }
drh9f099fd2013-08-06 14:01:46 +00003725 if( nSql ){
drhd416fe72011-03-17 16:45:50 +00003726 if( !_all_whitespace(zSql) ){
3727 fprintf(stderr, "Error: incomplete SQL: %s\n", zSql);
3728 }
drhdaffd0e2001-04-11 14:28:42 +00003729 free(zSql);
3730 }
danielk19772ac27622007-07-03 05:31:16 +00003731 free(zLine);
drh4d15a0d2012-12-01 20:21:22 +00003732 return errCnt>0;
drhdaffd0e2001-04-11 14:28:42 +00003733}
3734
drh67505e72002-04-19 12:34:06 +00003735/*
3736** Return a pathname which is the user's home directory. A
drh85e72432012-04-11 11:38:53 +00003737** 0 return indicates an error of some kind.
drh67505e72002-04-19 12:34:06 +00003738*/
3739static char *find_home_dir(void){
drh85e72432012-04-11 11:38:53 +00003740 static char *home_dir = NULL;
3741 if( home_dir ) return home_dir;
persicom7e2dfdd2002-04-18 02:46:52 +00003742
drh83905c92012-06-21 13:00:37 +00003743#if !defined(_WIN32) && !defined(WIN32) && !defined(_WIN32_WCE) && !defined(__RTP__) && !defined(_WRS_KERNEL)
mistachkinc8bde372012-06-18 08:00:56 +00003744 {
3745 struct passwd *pwent;
3746 uid_t uid = getuid();
3747 if( (pwent=getpwuid(uid)) != NULL) {
3748 home_dir = pwent->pw_dir;
3749 }
drh67505e72002-04-19 12:34:06 +00003750 }
3751#endif
3752
chw65d3c132007-11-12 21:09:10 +00003753#if defined(_WIN32_WCE)
3754 /* Windows CE (arm-wince-mingw32ce-gcc) does not provide getenv()
3755 */
drh85e72432012-04-11 11:38:53 +00003756 home_dir = "/";
chw65d3c132007-11-12 21:09:10 +00003757#else
3758
drh83905c92012-06-21 13:00:37 +00003759#if defined(_WIN32) || defined(WIN32)
drh164a1b62006-08-19 11:15:20 +00003760 if (!home_dir) {
3761 home_dir = getenv("USERPROFILE");
3762 }
3763#endif
3764
drh67505e72002-04-19 12:34:06 +00003765 if (!home_dir) {
3766 home_dir = getenv("HOME");
drh67505e72002-04-19 12:34:06 +00003767 }
3768
drh83905c92012-06-21 13:00:37 +00003769#if defined(_WIN32) || defined(WIN32)
drhe98d4fa2002-04-21 19:06:22 +00003770 if (!home_dir) {
drh164a1b62006-08-19 11:15:20 +00003771 char *zDrive, *zPath;
3772 int n;
3773 zDrive = getenv("HOMEDRIVE");
3774 zPath = getenv("HOMEPATH");
3775 if( zDrive && zPath ){
drh4f21c4a2008-12-10 22:15:00 +00003776 n = strlen30(zDrive) + strlen30(zPath) + 1;
drh164a1b62006-08-19 11:15:20 +00003777 home_dir = malloc( n );
3778 if( home_dir==0 ) return 0;
3779 sqlite3_snprintf(n, home_dir, "%s%s", zDrive, zPath);
3780 return home_dir;
3781 }
3782 home_dir = "c:\\";
drhe98d4fa2002-04-21 19:06:22 +00003783 }
3784#endif
3785
chw65d3c132007-11-12 21:09:10 +00003786#endif /* !_WIN32_WCE */
3787
drh67505e72002-04-19 12:34:06 +00003788 if( home_dir ){
drh4f21c4a2008-12-10 22:15:00 +00003789 int n = strlen30(home_dir) + 1;
drh5bb3eb92007-05-04 13:15:55 +00003790 char *z = malloc( n );
3791 if( z ) memcpy(z, home_dir, n);
drh67505e72002-04-19 12:34:06 +00003792 home_dir = z;
3793 }
drhe98d4fa2002-04-21 19:06:22 +00003794
drh67505e72002-04-19 12:34:06 +00003795 return home_dir;
3796}
3797
3798/*
3799** Read input from the file given by sqliterc_override. Or if that
3800** parameter is NULL, take input from ~/.sqliterc
shane9bd1b442009-10-23 01:27:39 +00003801**
3802** Returns the number of errors.
drh67505e72002-04-19 12:34:06 +00003803*/
shane9bd1b442009-10-23 01:27:39 +00003804static int process_sqliterc(
drhdcd87a92014-08-18 13:45:42 +00003805 ShellState *p, /* Configuration data */
drh22fbcb82004-02-01 01:22:50 +00003806 const char *sqliterc_override /* Name of config file. NULL to use default */
3807){
persicom7e2dfdd2002-04-18 02:46:52 +00003808 char *home_dir = NULL;
drh22fbcb82004-02-01 01:22:50 +00003809 const char *sqliterc = sqliterc_override;
drh43617e92006-03-06 20:55:46 +00003810 char *zBuf = 0;
persicom7e2dfdd2002-04-18 02:46:52 +00003811 FILE *in = NULL;
shane9bd1b442009-10-23 01:27:39 +00003812 int rc = 0;
persicom7e2dfdd2002-04-18 02:46:52 +00003813
3814 if (sqliterc == NULL) {
drh67505e72002-04-19 12:34:06 +00003815 home_dir = find_home_dir();
drhe98d4fa2002-04-21 19:06:22 +00003816 if( home_dir==0 ){
chw97185482008-11-17 08:05:31 +00003817#if !defined(__RTP__) && !defined(_WRS_KERNEL)
shane86f5bdb2009-10-24 02:00:07 +00003818 fprintf(stderr,"%s: Error: cannot locate your home directory\n", Argv0);
chw97185482008-11-17 08:05:31 +00003819#endif
shane9bd1b442009-10-23 01:27:39 +00003820 return 1;
drhe98d4fa2002-04-21 19:06:22 +00003821 }
drh2f3de322012-06-27 16:41:31 +00003822 sqlite3_initialize();
drh85e72432012-04-11 11:38:53 +00003823 zBuf = sqlite3_mprintf("%s/.sqliterc",home_dir);
3824 sqliterc = zBuf;
persicom7e2dfdd2002-04-18 02:46:52 +00003825 }
drha1f9b5e2004-02-14 16:31:02 +00003826 in = fopen(sqliterc,"rb");
drh22fbcb82004-02-01 01:22:50 +00003827 if( in ){
drhc28490c2006-10-26 14:25:58 +00003828 if( stdin_is_interactive ){
shane86f5bdb2009-10-24 02:00:07 +00003829 fprintf(stderr,"-- Loading resources from %s\n",sqliterc);
drh22fbcb82004-02-01 01:22:50 +00003830 }
shane9bd1b442009-10-23 01:27:39 +00003831 rc = process_input(p,in);
drhdd45df82002-04-18 12:39:03 +00003832 fclose(in);
persicom7e2dfdd2002-04-18 02:46:52 +00003833 }
drh85e72432012-04-11 11:38:53 +00003834 sqlite3_free(zBuf);
shane9bd1b442009-10-23 01:27:39 +00003835 return rc;
persicom7e2dfdd2002-04-18 02:46:52 +00003836}
3837
drh67505e72002-04-19 12:34:06 +00003838/*
drhe1e38c42003-05-04 18:30:59 +00003839** Show available command line options
3840*/
3841static const char zOptions[] =
drhc49f44e2006-10-26 18:15:42 +00003842 " -bail stop after hitting an error\n"
drhc49f44e2006-10-26 18:15:42 +00003843 " -batch force batch I/O\n"
drhe1e38c42003-05-04 18:30:59 +00003844 " -column set output mode to 'column'\n"
mistachkin6d81d752012-10-25 15:43:28 +00003845 " -cmd COMMAND run \"COMMAND\" before reading stdin\n"
drhc49f44e2006-10-26 18:15:42 +00003846 " -csv set output mode to 'csv'\n"
drhcc3b4f82012-02-07 14:13:50 +00003847 " -echo print commands before execution\n"
mistachkin6d81d752012-10-25 15:43:28 +00003848 " -init FILENAME read/process named file\n"
drhcc3b4f82012-02-07 14:13:50 +00003849 " -[no]header turn headers on or off\n"
drh98d312f2012-10-25 15:23:14 +00003850#if defined(SQLITE_ENABLE_MEMSYS3) || defined(SQLITE_ENABLE_MEMSYS5)
3851 " -heap SIZE Size of heap for memsys3 or memsys5\n"
3852#endif
drhcc3b4f82012-02-07 14:13:50 +00003853 " -help show this message\n"
drhe1e38c42003-05-04 18:30:59 +00003854 " -html set output mode to HTML\n"
drhcc3b4f82012-02-07 14:13:50 +00003855 " -interactive force interactive I/O\n"
drhe1e38c42003-05-04 18:30:59 +00003856 " -line set output mode to 'line'\n"
3857 " -list set output mode to 'list'\n"
drh44dec872014-08-30 15:49:25 +00003858 " -lookaside SIZE N use N entries of SZ bytes for lookaside memory\n"
drh7d9f3942013-04-03 01:26:54 +00003859 " -mmap N default mmap size set to N\n"
drhcc3b4f82012-02-07 14:13:50 +00003860#ifdef SQLITE_ENABLE_MULTIPLEX
3861 " -multiplex enable the multiplexor VFS\n"
3862#endif
drh6976c212014-07-24 12:09:47 +00003863 " -newline SEP set newline character(s) for CSV\n"
drh98d312f2012-10-25 15:23:14 +00003864 " -nullvalue TEXT set text string for NULL values. Default ''\n"
drh44dec872014-08-30 15:49:25 +00003865 " -pagecache SIZE N use N slots of SZ bytes each for page cache memory\n"
3866 " -scratch SIZE N use N slots of SZ bytes each for scratch memory\n"
drh98d312f2012-10-25 15:23:14 +00003867 " -separator SEP set output field separator. Default: '|'\n"
shaneh642d8b82010-07-28 16:05:34 +00003868 " -stats print memory stats before each finalize\n"
drhe1e38c42003-05-04 18:30:59 +00003869 " -version show SQLite version\n"
drha7e61d82011-03-12 17:02:57 +00003870 " -vfs NAME use NAME as the default VFS\n"
drh2b625e22011-03-16 17:05:28 +00003871#ifdef SQLITE_ENABLE_VFSTRACE
3872 " -vfstrace enable tracing of all VFS calls\n"
3873#endif
drhe1e38c42003-05-04 18:30:59 +00003874;
3875static void usage(int showDetail){
drh80e8be92006-08-29 12:04:19 +00003876 fprintf(stderr,
3877 "Usage: %s [OPTIONS] FILENAME [SQL]\n"
3878 "FILENAME is the name of an SQLite database. A new database is created\n"
3879 "if the file does not previously exist.\n", Argv0);
drhe1e38c42003-05-04 18:30:59 +00003880 if( showDetail ){
drh80e8be92006-08-29 12:04:19 +00003881 fprintf(stderr, "OPTIONS include:\n%s", zOptions);
drhe1e38c42003-05-04 18:30:59 +00003882 }else{
3883 fprintf(stderr, "Use the -help option for additional information\n");
3884 }
3885 exit(1);
3886}
3887
3888/*
drh67505e72002-04-19 12:34:06 +00003889** Initialize the state information in data
3890*/
drhdcd87a92014-08-18 13:45:42 +00003891static void main_init(ShellState *data) {
persicom7e2dfdd2002-04-18 02:46:52 +00003892 memset(data, 0, sizeof(*data));
3893 data->mode = MODE_List;
drh5bb3eb92007-05-04 13:15:55 +00003894 memcpy(data->separator,"|", 2);
drh6976c212014-07-24 12:09:47 +00003895 memcpy(data->newline,"\r\n", 3);
persicom7e2dfdd2002-04-18 02:46:52 +00003896 data->showHeader = 0;
drh44dec872014-08-30 15:49:25 +00003897 data->shellFlgs = SHFLG_Lookaside;
drh52784bd2011-05-18 17:15:06 +00003898 sqlite3_config(SQLITE_CONFIG_URI, 1);
drh127f9d72010-02-23 01:47:00 +00003899 sqlite3_config(SQLITE_CONFIG_LOG, shellLog, data);
drh44dec872014-08-30 15:49:25 +00003900 sqlite3_config(SQLITE_CONFIG_MULTITHREAD);
drh5bb3eb92007-05-04 13:15:55 +00003901 sqlite3_snprintf(sizeof(mainPrompt), mainPrompt,"sqlite> ");
3902 sqlite3_snprintf(sizeof(continuePrompt), continuePrompt," ...> ");
persicom7e2dfdd2002-04-18 02:46:52 +00003903}
3904
drh98d312f2012-10-25 15:23:14 +00003905/*
drh5c7976f2014-02-10 19:59:27 +00003906** Output text to the console in a font that attracts extra attention.
drh1247aa42014-02-10 19:27:05 +00003907*/
3908#ifdef _WIN32
drh5c7976f2014-02-10 19:59:27 +00003909static void printBold(const char *zText){
3910 HANDLE out = GetStdHandle(STD_OUTPUT_HANDLE);
3911 CONSOLE_SCREEN_BUFFER_INFO defaultScreenInfo;
3912 GetConsoleScreenBufferInfo(out, &defaultScreenInfo);
3913 SetConsoleTextAttribute(out,
3914 FOREGROUND_RED|FOREGROUND_INTENSITY
3915 );
3916 printf("%s", zText);
3917 SetConsoleTextAttribute(out, defaultScreenInfo.wAttributes);
drh1247aa42014-02-10 19:27:05 +00003918}
3919#else
drh5c7976f2014-02-10 19:59:27 +00003920static void printBold(const char *zText){
3921 printf("\033[1m%s\033[0m", zText);
drh1247aa42014-02-10 19:27:05 +00003922}
3923#endif
3924
3925/*
drh98d312f2012-10-25 15:23:14 +00003926** Get the argument to an --option. Throw an error and die if no argument
3927** is available.
3928*/
3929static char *cmdline_option_value(int argc, char **argv, int i){
3930 if( i==argc ){
3931 fprintf(stderr, "%s: Error: missing argument to %s\n",
3932 argv[0], argv[argc-1]);
3933 exit(1);
3934 }
3935 return argv[i];
3936}
3937
drh75897232000-05-29 14:26:00 +00003938int main(int argc, char **argv){
drh75897232000-05-29 14:26:00 +00003939 char *zErrMsg = 0;
drhdcd87a92014-08-18 13:45:42 +00003940 ShellState data;
drh22fbcb82004-02-01 01:22:50 +00003941 const char *zInitFile = 0;
3942 char *zFirstCmd = 0;
drh44c2eb12003-04-30 11:38:26 +00003943 int i;
drhc28490c2006-10-26 14:25:58 +00003944 int rc = 0;
drhb3735912014-02-10 16:13:42 +00003945 int warnInmemoryDb = 0;
drh75897232000-05-29 14:26:00 +00003946
drh69b30ab2014-02-27 15:11:52 +00003947#if USE_SYSTEM_SQLITE+0!=1
drh52784bd2011-05-18 17:15:06 +00003948 if( strcmp(sqlite3_sourceid(),SQLITE_SOURCE_ID)!=0 ){
3949 fprintf(stderr, "SQLite header and source version mismatch\n%s\n%s\n",
3950 sqlite3_sourceid(), SQLITE_SOURCE_ID);
3951 exit(1);
3952 }
drhc7181902014-02-27 15:04:13 +00003953#endif
drhdaffd0e2001-04-11 14:28:42 +00003954 Argv0 = argv[0];
persicom7e2dfdd2002-04-18 02:46:52 +00003955 main_init(&data);
drhc28490c2006-10-26 14:25:58 +00003956 stdin_is_interactive = isatty(0);
persicom7e2dfdd2002-04-18 02:46:52 +00003957
drh44c2eb12003-04-30 11:38:26 +00003958 /* Make sure we have a valid signal handler early, before anything
3959 ** else is done.
3960 */
drh4c504392000-10-16 22:06:40 +00003961#ifdef SIGINT
3962 signal(SIGINT, interrupt_handler);
3963#endif
drh44c2eb12003-04-30 11:38:26 +00003964
drh22fbcb82004-02-01 01:22:50 +00003965 /* Do an initial pass through the command-line argument to locate
3966 ** the name of the database file, the name of the initialization file,
drh9c88d682010-12-17 14:03:01 +00003967 ** the size of the alternative malloc heap,
drh22fbcb82004-02-01 01:22:50 +00003968 ** and the first command to execute.
drh44c2eb12003-04-30 11:38:26 +00003969 */
drh98d312f2012-10-25 15:23:14 +00003970 for(i=1; i<argc; i++){
drhc28490c2006-10-26 14:25:58 +00003971 char *z;
drhc28490c2006-10-26 14:25:58 +00003972 z = argv[i];
drh98d312f2012-10-25 15:23:14 +00003973 if( z[0]!='-' ){
3974 if( data.zDbFilename==0 ){
3975 data.zDbFilename = z;
3976 continue;
3977 }
3978 if( zFirstCmd==0 ){
3979 zFirstCmd = z;
3980 continue;
3981 }
3982 fprintf(stderr,"%s: Error: too many options: \"%s\"\n", Argv0, argv[i]);
3983 fprintf(stderr,"Use -help for a list of options.\n");
3984 return 1;
3985 }
drhcc3b4f82012-02-07 14:13:50 +00003986 if( z[1]=='-' ) z++;
3987 if( strcmp(z,"-separator")==0
3988 || strcmp(z,"-nullvalue")==0
drh6976c212014-07-24 12:09:47 +00003989 || strcmp(z,"-newline")==0
drhcc3b4f82012-02-07 14:13:50 +00003990 || strcmp(z,"-cmd")==0
3991 ){
drh98d312f2012-10-25 15:23:14 +00003992 (void)cmdline_option_value(argc, argv, ++i);
drhcc3b4f82012-02-07 14:13:50 +00003993 }else if( strcmp(z,"-init")==0 ){
drh98d312f2012-10-25 15:23:14 +00003994 zInitFile = cmdline_option_value(argc, argv, ++i);
drhcc3b4f82012-02-07 14:13:50 +00003995 }else if( strcmp(z,"-batch")==0 ){
drh98d312f2012-10-25 15:23:14 +00003996 /* Need to check for batch mode here to so we can avoid printing
3997 ** informational messages (like from process_sqliterc) before
3998 ** we do the actual processing of arguments later in a second pass.
3999 */
shanef69573d2009-10-24 02:06:14 +00004000 stdin_is_interactive = 0;
drhcc3b4f82012-02-07 14:13:50 +00004001 }else if( strcmp(z,"-heap")==0 ){
drhb07028f2011-10-14 21:49:18 +00004002#if defined(SQLITE_ENABLE_MEMSYS3) || defined(SQLITE_ENABLE_MEMSYS5)
drh9c88d682010-12-17 14:03:01 +00004003 const char *zSize;
4004 sqlite3_int64 szHeap;
4005
drh98d312f2012-10-25 15:23:14 +00004006 zSize = cmdline_option_value(argc, argv, ++i);
drh7d9f3942013-04-03 01:26:54 +00004007 szHeap = integerValue(zSize);
drh9c88d682010-12-17 14:03:01 +00004008 if( szHeap>0x7fff0000 ) szHeap = 0x7fff0000;
drh9c88d682010-12-17 14:03:01 +00004009 sqlite3_config(SQLITE_CONFIG_HEAP, malloc((int)szHeap), (int)szHeap, 64);
4010#endif
drh44dec872014-08-30 15:49:25 +00004011 }else if( strcmp(z,"-scratch")==0 ){
4012 int n, sz;
mistachkin31970cc2014-09-01 01:16:49 +00004013 sz = (int)integerValue(cmdline_option_value(argc,argv,++i));
drh44dec872014-08-30 15:49:25 +00004014 if( sz>400000 ) sz = 400000;
4015 if( sz<2500 ) sz = 2500;
mistachkin31970cc2014-09-01 01:16:49 +00004016 n = (int)integerValue(cmdline_option_value(argc,argv,++i));
drh44dec872014-08-30 15:49:25 +00004017 if( n>10 ) n = 10;
4018 if( n<1 ) n = 1;
4019 sqlite3_config(SQLITE_CONFIG_SCRATCH, malloc(n*sz+1), sz, n);
4020 data.shellFlgs |= SHFLG_Scratch;
4021 }else if( strcmp(z,"-pagecache")==0 ){
4022 int n, sz;
mistachkin31970cc2014-09-01 01:16:49 +00004023 sz = (int)integerValue(cmdline_option_value(argc,argv,++i));
drh44dec872014-08-30 15:49:25 +00004024 if( sz>70000 ) sz = 70000;
4025 if( sz<800 ) sz = 800;
mistachkin31970cc2014-09-01 01:16:49 +00004026 n = (int)integerValue(cmdline_option_value(argc,argv,++i));
drh44dec872014-08-30 15:49:25 +00004027 if( n<10 ) n = 10;
4028 sqlite3_config(SQLITE_CONFIG_PAGECACHE, malloc(n*sz+1), sz, n);
4029 data.shellFlgs |= SHFLG_Pagecache;
4030 }else if( strcmp(z,"-lookaside")==0 ){
4031 int n, sz;
mistachkin31970cc2014-09-01 01:16:49 +00004032 sz = (int)integerValue(cmdline_option_value(argc,argv,++i));
drh44dec872014-08-30 15:49:25 +00004033 if( sz<0 ) sz = 0;
mistachkin31970cc2014-09-01 01:16:49 +00004034 n = (int)integerValue(cmdline_option_value(argc,argv,++i));
drh44dec872014-08-30 15:49:25 +00004035 if( n<0 ) n = 0;
4036 sqlite3_config(SQLITE_CONFIG_LOOKASIDE, sz, n);
4037 if( sz*n==0 ) data.shellFlgs &= ~SHFLG_Lookaside;
drh97ae8ff2011-03-16 16:56:29 +00004038#ifdef SQLITE_ENABLE_VFSTRACE
drhcc3b4f82012-02-07 14:13:50 +00004039 }else if( strcmp(z,"-vfstrace")==0 ){
drh97ae8ff2011-03-16 16:56:29 +00004040 extern int vfstrace_register(
4041 const char *zTraceName,
4042 const char *zOldVfsName,
4043 int (*xOut)(const char*,void*),
4044 void *pOutArg,
4045 int makeDefault
4046 );
drh2b625e22011-03-16 17:05:28 +00004047 vfstrace_register("trace",0,(int(*)(const char*,void*))fputs,stderr,1);
drh97ae8ff2011-03-16 16:56:29 +00004048#endif
drh6f25e892011-07-08 17:02:57 +00004049#ifdef SQLITE_ENABLE_MULTIPLEX
drhcc3b4f82012-02-07 14:13:50 +00004050 }else if( strcmp(z,"-multiplex")==0 ){
drh6f25e892011-07-08 17:02:57 +00004051 extern int sqlite3_multiple_initialize(const char*,int);
4052 sqlite3_multiplex_initialize(0, 1);
4053#endif
drh7d9f3942013-04-03 01:26:54 +00004054 }else if( strcmp(z,"-mmap")==0 ){
drh9b4c59f2013-04-15 17:03:42 +00004055 sqlite3_int64 sz = integerValue(cmdline_option_value(argc,argv,++i));
4056 sqlite3_config(SQLITE_CONFIG_MMAP_SIZE, sz, sz);
drhcc3b4f82012-02-07 14:13:50 +00004057 }else if( strcmp(z,"-vfs")==0 ){
drh98d312f2012-10-25 15:23:14 +00004058 sqlite3_vfs *pVfs = sqlite3_vfs_find(cmdline_option_value(argc,argv,++i));
drha7e61d82011-03-12 17:02:57 +00004059 if( pVfs ){
4060 sqlite3_vfs_register(pVfs, 1);
4061 }else{
4062 fprintf(stderr, "no such VFS: \"%s\"\n", argv[i]);
4063 exit(1);
4064 }
drh44c2eb12003-04-30 11:38:26 +00004065 }
4066 }
drh98d312f2012-10-25 15:23:14 +00004067 if( data.zDbFilename==0 ){
danielk197703aded42004-11-22 05:26:27 +00004068#ifndef SQLITE_OMIT_MEMORYDB
drh22fbcb82004-02-01 01:22:50 +00004069 data.zDbFilename = ":memory:";
drh1247aa42014-02-10 19:27:05 +00004070 warnInmemoryDb = argc==1;
danielk197703aded42004-11-22 05:26:27 +00004071#else
shane86f5bdb2009-10-24 02:00:07 +00004072 fprintf(stderr,"%s: Error: no database filename specified\n", Argv0);
4073 return 1;
drh01b41712005-08-29 23:06:23 +00004074#endif
drhc7181902014-02-27 15:04:13 +00004075#ifdef SQLITE_SHELL_DBNAME_PROC
4076 { extern void SQLITE_SHELL_DBNAME_PROC(const char**);
4077 SQLITE_SHELL_DBNAME_PROC(&data.zDbFilename);
4078 warnInmemoryDb = 0; }
4079#endif
drh98d312f2012-10-25 15:23:14 +00004080 }
4081 data.out = stdout;
drh01b41712005-08-29 23:06:23 +00004082
drh44c2eb12003-04-30 11:38:26 +00004083 /* Go ahead and open the database file if it already exists. If the
4084 ** file does not exist, delay opening it. This prevents empty database
4085 ** files from being created if a user mistypes the database name argument
4086 ** to the sqlite command-line tool.
4087 */
drhc8d74412004-08-31 23:41:26 +00004088 if( access(data.zDbFilename, 0)==0 ){
drh05782482013-10-24 15:20:20 +00004089 open_db(&data, 0);
drh44c2eb12003-04-30 11:38:26 +00004090 }
4091
drh22fbcb82004-02-01 01:22:50 +00004092 /* Process the initialization file if there is one. If no -init option
4093 ** is given on the command line, look for a file named ~/.sqliterc and
4094 ** try to process it.
drh44c2eb12003-04-30 11:38:26 +00004095 */
shane86f5bdb2009-10-24 02:00:07 +00004096 rc = process_sqliterc(&data,zInitFile);
4097 if( rc>0 ){
4098 return rc;
4099 }
drh44c2eb12003-04-30 11:38:26 +00004100
drh22fbcb82004-02-01 01:22:50 +00004101 /* Make a second pass through the command-line argument and set
4102 ** options. This second pass is delayed until after the initialization
4103 ** file is processed so that the command-line arguments will override
4104 ** settings in the initialization file.
drh44c2eb12003-04-30 11:38:26 +00004105 */
drh98d312f2012-10-25 15:23:14 +00004106 for(i=1; i<argc; i++){
drh22fbcb82004-02-01 01:22:50 +00004107 char *z = argv[i];
drh98d312f2012-10-25 15:23:14 +00004108 if( z[0]!='-' ) continue;
drhc28490c2006-10-26 14:25:58 +00004109 if( z[1]=='-' ){ z++; }
drh2e584cd2006-09-25 13:09:22 +00004110 if( strcmp(z,"-init")==0 ){
drh22fbcb82004-02-01 01:22:50 +00004111 i++;
4112 }else if( strcmp(z,"-html")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00004113 data.mode = MODE_Html;
drh22fbcb82004-02-01 01:22:50 +00004114 }else if( strcmp(z,"-list")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00004115 data.mode = MODE_List;
drh22fbcb82004-02-01 01:22:50 +00004116 }else if( strcmp(z,"-line")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00004117 data.mode = MODE_Line;
drh22fbcb82004-02-01 01:22:50 +00004118 }else if( strcmp(z,"-column")==0 ){
drh8b32e172002-04-08 02:42:57 +00004119 data.mode = MODE_Column;
drhc49f44e2006-10-26 18:15:42 +00004120 }else if( strcmp(z,"-csv")==0 ){
4121 data.mode = MODE_Csv;
drh5bb3eb92007-05-04 13:15:55 +00004122 memcpy(data.separator,",",2);
drh22fbcb82004-02-01 01:22:50 +00004123 }else if( strcmp(z,"-separator")==0 ){
drh5bb3eb92007-05-04 13:15:55 +00004124 sqlite3_snprintf(sizeof(data.separator), data.separator,
drh98d312f2012-10-25 15:23:14 +00004125 "%s",cmdline_option_value(argc,argv,++i));
drh6976c212014-07-24 12:09:47 +00004126 }else if( strcmp(z,"-newline")==0 ){
4127 sqlite3_snprintf(sizeof(data.newline), data.newline,
4128 "%s",cmdline_option_value(argc,argv,++i));
drh22fbcb82004-02-01 01:22:50 +00004129 }else if( strcmp(z,"-nullvalue")==0 ){
drh5bb3eb92007-05-04 13:15:55 +00004130 sqlite3_snprintf(sizeof(data.nullvalue), data.nullvalue,
drh98d312f2012-10-25 15:23:14 +00004131 "%s",cmdline_option_value(argc,argv,++i));
drh22fbcb82004-02-01 01:22:50 +00004132 }else if( strcmp(z,"-header")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00004133 data.showHeader = 1;
drh22fbcb82004-02-01 01:22:50 +00004134 }else if( strcmp(z,"-noheader")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00004135 data.showHeader = 0;
drh22fbcb82004-02-01 01:22:50 +00004136 }else if( strcmp(z,"-echo")==0 ){
drhdaffd0e2001-04-11 14:28:42 +00004137 data.echoOn = 1;
drhefbf3b12014-02-28 20:47:24 +00004138 }else if( strcmp(z,"-eqp")==0 ){
4139 data.autoEQP = 1;
shaneh642d8b82010-07-28 16:05:34 +00004140 }else if( strcmp(z,"-stats")==0 ){
4141 data.statsOn = 1;
drhc49f44e2006-10-26 18:15:42 +00004142 }else if( strcmp(z,"-bail")==0 ){
4143 bail_on_error = 1;
drh22fbcb82004-02-01 01:22:50 +00004144 }else if( strcmp(z,"-version")==0 ){
drh9fd301b2011-06-03 13:28:22 +00004145 printf("%s %s\n", sqlite3_libversion(), sqlite3_sourceid());
drh151e3e12006-06-06 12:32:21 +00004146 return 0;
drhc28490c2006-10-26 14:25:58 +00004147 }else if( strcmp(z,"-interactive")==0 ){
4148 stdin_is_interactive = 1;
4149 }else if( strcmp(z,"-batch")==0 ){
4150 stdin_is_interactive = 0;
drh9c88d682010-12-17 14:03:01 +00004151 }else if( strcmp(z,"-heap")==0 ){
4152 i++;
drh44dec872014-08-30 15:49:25 +00004153 }else if( strcmp(z,"-scratch")==0 ){
4154 i+=2;
4155 }else if( strcmp(z,"-pagecache")==0 ){
4156 i+=2;
4157 }else if( strcmp(z,"-lookaside")==0 ){
4158 i+=2;
drh7d9f3942013-04-03 01:26:54 +00004159 }else if( strcmp(z,"-mmap")==0 ){
4160 i++;
drha7e61d82011-03-12 17:02:57 +00004161 }else if( strcmp(z,"-vfs")==0 ){
4162 i++;
drh6f25e892011-07-08 17:02:57 +00004163#ifdef SQLITE_ENABLE_VFSTRACE
drh97ae8ff2011-03-16 16:56:29 +00004164 }else if( strcmp(z,"-vfstrace")==0 ){
4165 i++;
drh6f25e892011-07-08 17:02:57 +00004166#endif
4167#ifdef SQLITE_ENABLE_MULTIPLEX
4168 }else if( strcmp(z,"-multiplex")==0 ){
4169 i++;
4170#endif
drhcc3b4f82012-02-07 14:13:50 +00004171 }else if( strcmp(z,"-help")==0 ){
drhe1e38c42003-05-04 18:30:59 +00004172 usage(1);
drhcc3b4f82012-02-07 14:13:50 +00004173 }else if( strcmp(z,"-cmd")==0 ){
4174 if( i==argc-1 ) break;
drh98d312f2012-10-25 15:23:14 +00004175 z = cmdline_option_value(argc,argv,++i);
drhcc3b4f82012-02-07 14:13:50 +00004176 if( z[0]=='.' ){
4177 rc = do_meta_command(z, &data);
drh99b39082013-04-17 12:19:48 +00004178 if( rc && bail_on_error ) return rc==2 ? 0 : rc;
drhcc3b4f82012-02-07 14:13:50 +00004179 }else{
drh05782482013-10-24 15:20:20 +00004180 open_db(&data, 0);
drhcc3b4f82012-02-07 14:13:50 +00004181 rc = shell_exec(data.db, z, shell_callback, &data, &zErrMsg);
4182 if( zErrMsg!=0 ){
4183 fprintf(stderr,"Error: %s\n", zErrMsg);
4184 if( bail_on_error ) return rc!=0 ? rc : 1;
4185 }else if( rc!=0 ){
4186 fprintf(stderr,"Error: unable to process SQL \"%s\"\n", z);
4187 if( bail_on_error ) return rc;
4188 }
4189 }
drh1e5d0e92000-05-31 23:33:17 +00004190 }else{
shane86f5bdb2009-10-24 02:00:07 +00004191 fprintf(stderr,"%s: Error: unknown option: %s\n", Argv0, z);
drhe1e38c42003-05-04 18:30:59 +00004192 fprintf(stderr,"Use -help for a list of options.\n");
drh1e5d0e92000-05-31 23:33:17 +00004193 return 1;
4194 }
4195 }
drh44c2eb12003-04-30 11:38:26 +00004196
drh22fbcb82004-02-01 01:22:50 +00004197 if( zFirstCmd ){
drh44c2eb12003-04-30 11:38:26 +00004198 /* Run just the command that follows the database name
4199 */
drh22fbcb82004-02-01 01:22:50 +00004200 if( zFirstCmd[0]=='.' ){
shane916f9612009-10-23 00:37:15 +00004201 rc = do_meta_command(zFirstCmd, &data);
drh99b39082013-04-17 12:19:48 +00004202 if( rc==2 ) rc = 0;
drh6ff13852001-11-25 13:18:23 +00004203 }else{
drh05782482013-10-24 15:20:20 +00004204 open_db(&data, 0);
shane626a6e42009-10-22 17:30:15 +00004205 rc = shell_exec(data.db, zFirstCmd, shell_callback, &data, &zErrMsg);
shane86f5bdb2009-10-24 02:00:07 +00004206 if( zErrMsg!=0 ){
4207 fprintf(stderr,"Error: %s\n", zErrMsg);
4208 return rc!=0 ? rc : 1;
4209 }else if( rc!=0 ){
4210 fprintf(stderr,"Error: unable to process SQL \"%s\"\n", zFirstCmd);
4211 return rc;
drh6ff13852001-11-25 13:18:23 +00004212 }
drh75897232000-05-29 14:26:00 +00004213 }
4214 }else{
drh44c2eb12003-04-30 11:38:26 +00004215 /* Run commands received from standard input
4216 */
drhc28490c2006-10-26 14:25:58 +00004217 if( stdin_is_interactive ){
drh67505e72002-04-19 12:34:06 +00004218 char *zHome;
4219 char *zHistory = 0;
drh5bb3eb92007-05-04 13:15:55 +00004220 int nHistory;
drh75897232000-05-29 14:26:00 +00004221 printf(
drh743e0032011-12-12 16:51:50 +00004222 "SQLite version %s %.19s\n" /*extra-version-info*/
drh1247aa42014-02-10 19:27:05 +00004223 "Enter \".help\" for usage hints.\n",
drh9fd301b2011-06-03 13:28:22 +00004224 sqlite3_libversion(), sqlite3_sourceid()
drh75897232000-05-29 14:26:00 +00004225 );
drhb3735912014-02-10 16:13:42 +00004226 if( warnInmemoryDb ){
drh1247aa42014-02-10 19:27:05 +00004227 printf("Connected to a ");
mistachkin378d01a2014-03-06 02:15:42 +00004228 printBold("transient in-memory database");
4229 printf(".\nUse \".open FILENAME\" to reopen on a "
drh1247aa42014-02-10 19:27:05 +00004230 "persistent database.\n");
drhb3735912014-02-10 16:13:42 +00004231 }
drh67505e72002-04-19 12:34:06 +00004232 zHome = find_home_dir();
drhea678832008-12-10 19:26:22 +00004233 if( zHome ){
drh4f21c4a2008-12-10 22:15:00 +00004234 nHistory = strlen30(zHome) + 20;
drhea678832008-12-10 19:26:22 +00004235 if( (zHistory = malloc(nHistory))!=0 ){
4236 sqlite3_snprintf(nHistory, zHistory,"%s/.sqlite_history", zHome);
4237 }
drh67505e72002-04-19 12:34:06 +00004238 }
drhaaa21b42014-02-11 14:37:51 +00004239#if defined(HAVE_READLINE)
drh67505e72002-04-19 12:34:06 +00004240 if( zHistory ) read_history(zHistory);
danielk19774af00c62005-01-23 23:43:21 +00004241#endif
drhc28490c2006-10-26 14:25:58 +00004242 rc = process_input(&data, 0);
drh67505e72002-04-19 12:34:06 +00004243 if( zHistory ){
4244 stifle_history(100);
4245 write_history(zHistory);
adamd0a3daa32006-07-28 20:16:14 +00004246 free(zHistory);
drh67505e72002-04-19 12:34:06 +00004247 }
drhdaffd0e2001-04-11 14:28:42 +00004248 }else{
drhc28490c2006-10-26 14:25:58 +00004249 rc = process_input(&data, stdin);
drh75897232000-05-29 14:26:00 +00004250 }
4251 }
drh33048c02001-10-01 14:29:22 +00004252 set_table_name(&data, 0);
drh72af0772010-05-06 20:19:55 +00004253 if( data.db ){
drhe14cd932010-12-08 03:28:17 +00004254 sqlite3_close(data.db);
adamd0a3daa32006-07-28 20:16:14 +00004255 }
drh05782482013-10-24 15:20:20 +00004256 sqlite3_free(data.zFreeOnClose);
drhc28490c2006-10-26 14:25:58 +00004257 return rc;
drh75897232000-05-29 14:26:00 +00004258}