blob: 78339db8b4e8c302b71e11bf9bb5ce3135e19419 [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"
drh75897232000-05-29 14:26:00 +000036#include <ctype.h>
drhb0603412007-02-28 04:47:26 +000037#include <stdarg.h>
persicom7e2dfdd2002-04-18 02:46:52 +000038
drh83905c92012-06-21 13:00:37 +000039#if !defined(_WIN32) && !defined(WIN32)
drh4c504392000-10-16 22:06:40 +000040# include <signal.h>
chw97185482008-11-17 08:05:31 +000041# if !defined(__RTP__) && !defined(_WRS_KERNEL)
42# include <pwd.h>
43# endif
drhdd45df82002-04-18 12:39:03 +000044# include <unistd.h>
45# include <sys/types.h>
drh4c504392000-10-16 22:06:40 +000046#endif
drh75897232000-05-29 14:26:00 +000047
drhaaa21b42014-02-11 14:37:51 +000048#if defined(HAVE_READLINE) && HAVE_READLINE!=0
drh8e7e7a22000-05-30 18:45:23 +000049# include <readline/readline.h>
50# include <readline/history.h>
drhaaa21b42014-02-11 14:37:51 +000051#else
52# undef HAVE_READLINE
drh81d7fd12010-12-08 00:02:26 +000053#endif
drhaaa21b42014-02-11 14:37:51 +000054#if defined(HAVE_EDITLINE) && !defined(HAVE_READLINE)
55# define HAVE_READLINE 1
56# include <editline/readline.h>
57#endif
58#if !defined(HAVE_READLINE)
persicom1d0b8722002-04-18 02:53:04 +000059# define add_history(X)
drh67505e72002-04-19 12:34:06 +000060# define read_history(X)
61# define write_history(X)
62# define stifle_history(X)
drh75897232000-05-29 14:26:00 +000063#endif
64
adamd2e8464a2006-09-06 21:39:40 +000065#if defined(_WIN32) || defined(WIN32)
66# include <io.h>
drh6976c212014-07-24 12:09:47 +000067# include <fcntl.h>
shane18e526c2008-12-10 22:30:24 +000068#define isatty(h) _isatty(h)
drh07901eb2014-02-28 19:37:45 +000069#ifndef access
70# define access(f,m) _access((f),(m))
71#endif
drh67ceaa62012-08-27 21:19:03 +000072#undef popen
drh53371f92013-07-25 17:07:03 +000073#define popen _popen
drh67ceaa62012-08-27 21:19:03 +000074#undef pclose
drh12cd6cf2013-06-29 15:40:22 +000075#define pclose _pclose
adamd2e8464a2006-09-06 21:39:40 +000076#else
drh4328c8b2003-04-26 02:50:11 +000077/* Make sure isatty() has a prototype.
78*/
drhb2acc3b2011-10-13 16:36:29 +000079extern int isatty(int);
drh4328c8b2003-04-26 02:50:11 +000080
drh53371f92013-07-25 17:07:03 +000081/* popen and pclose are not C89 functions and so are sometimes omitted from
82** the <stdio.h> header */
mistachkinf6418892013-08-28 01:54:12 +000083extern FILE *popen(const char*,const char*);
84extern int pclose(FILE*);
85#endif
drh53371f92013-07-25 17:07:03 +000086
chw65d3c132007-11-12 21:09:10 +000087#if defined(_WIN32_WCE)
88/* Windows CE (arm-wince-mingw32ce-gcc) does not provide isatty()
89 * thus we always assume that we have a console. That can be
90 * overridden with the -batch command line option.
91 */
92#define isatty(x) 1
93#endif
94
drhf0693c82011-10-11 20:41:54 +000095/* ctype macros that work with signed characters */
96#define IsSpace(X) isspace((unsigned char)X)
97#define IsDigit(X) isdigit((unsigned char)X)
98#define ToLower(X) (char)tolower((unsigned char)X)
99
drh43408312013-10-30 12:43:36 +0000100
101/* True if the timer is enabled */
102static int enableTimer = 0;
103
104/* Return the current wall-clock time */
105static sqlite3_int64 timeOfDay(void){
106 static sqlite3_vfs *clockVfs = 0;
107 sqlite3_int64 t;
108 if( clockVfs==0 ) clockVfs = sqlite3_vfs_find(0);
109 if( clockVfs->iVersion>=1 && clockVfs->xCurrentTimeInt64!=0 ){
110 clockVfs->xCurrentTimeInt64(clockVfs, &t);
111 }else{
112 double r;
113 clockVfs->xCurrentTime(clockVfs, &r);
114 t = (sqlite3_int64)(r*86400000.0);
115 }
116 return t;
117}
118
drhd5d0f642013-02-20 00:54:21 +0000119#if !defined(_WIN32) && !defined(WIN32) && !defined(_WRS_KERNEL) \
120 && !defined(__minux)
drh3b1a9882007-11-02 12:53:03 +0000121#include <sys/time.h>
122#include <sys/resource.h>
123
drhda108222009-02-25 19:07:24 +0000124/* Saved resource information for the beginning of an operation */
drh43408312013-10-30 12:43:36 +0000125static struct rusage sBegin; /* CPU time at start */
126static sqlite3_int64 iBegin; /* Wall-clock time at start */
drhda108222009-02-25 19:07:24 +0000127
drhda108222009-02-25 19:07:24 +0000128/*
129** Begin timing an operation
130*/
131static void beginTimer(void){
132 if( enableTimer ){
133 getrusage(RUSAGE_SELF, &sBegin);
drh43408312013-10-30 12:43:36 +0000134 iBegin = timeOfDay();
drhda108222009-02-25 19:07:24 +0000135 }
136}
137
138/* Return the difference of two time_structs in seconds */
139static double timeDiff(struct timeval *pStart, struct timeval *pEnd){
140 return (pEnd->tv_usec - pStart->tv_usec)*0.000001 +
141 (double)(pEnd->tv_sec - pStart->tv_sec);
142}
143
144/*
145** Print the timing results.
146*/
147static void endTimer(void){
148 if( enableTimer ){
149 struct rusage sEnd;
drh43408312013-10-30 12:43:36 +0000150 sqlite3_int64 iEnd = timeOfDay();
drhda108222009-02-25 19:07:24 +0000151 getrusage(RUSAGE_SELF, &sEnd);
drh43408312013-10-30 12:43:36 +0000152 printf("Run Time: real %.3f user %f sys %f\n",
153 (iEnd - iBegin)*0.001,
drhda108222009-02-25 19:07:24 +0000154 timeDiff(&sBegin.ru_utime, &sEnd.ru_utime),
155 timeDiff(&sBegin.ru_stime, &sEnd.ru_stime));
156 }
157}
shaneb320ccd2009-10-21 03:42:58 +0000158
drhda108222009-02-25 19:07:24 +0000159#define BEGIN_TIMER beginTimer()
160#define END_TIMER endTimer()
161#define HAS_TIMER 1
shaneb320ccd2009-10-21 03:42:58 +0000162
163#elif (defined(_WIN32) || defined(WIN32))
164
165#include <windows.h>
166
167/* Saved resource information for the beginning of an operation */
168static HANDLE hProcess;
169static FILETIME ftKernelBegin;
170static FILETIME ftUserBegin;
drh43408312013-10-30 12:43:36 +0000171static sqlite3_int64 ftWallBegin;
shaneb320ccd2009-10-21 03:42:58 +0000172typedef BOOL (WINAPI *GETPROCTIMES)(HANDLE, LPFILETIME, LPFILETIME, LPFILETIME, LPFILETIME);
173static GETPROCTIMES getProcessTimesAddr = NULL;
174
shaneb320ccd2009-10-21 03:42:58 +0000175/*
176** Check to see if we have timer support. Return 1 if necessary
177** support found (or found previously).
178*/
179static int hasTimer(void){
180 if( getProcessTimesAddr ){
181 return 1;
182 } else {
183 /* GetProcessTimes() isn't supported in WIN95 and some other Windows versions.
184 ** See if the version we are running on has it, and if it does, save off
185 ** a pointer to it and the current process handle.
186 */
187 hProcess = GetCurrentProcess();
188 if( hProcess ){
189 HINSTANCE hinstLib = LoadLibrary(TEXT("Kernel32.dll"));
190 if( NULL != hinstLib ){
191 getProcessTimesAddr = (GETPROCTIMES) GetProcAddress(hinstLib, "GetProcessTimes");
192 if( NULL != getProcessTimesAddr ){
193 return 1;
194 }
195 FreeLibrary(hinstLib);
196 }
197 }
198 }
199 return 0;
200}
201
202/*
203** Begin timing an operation
204*/
205static void beginTimer(void){
206 if( enableTimer && getProcessTimesAddr ){
207 FILETIME ftCreation, ftExit;
208 getProcessTimesAddr(hProcess, &ftCreation, &ftExit, &ftKernelBegin, &ftUserBegin);
drh43408312013-10-30 12:43:36 +0000209 ftWallBegin = timeOfDay();
shaneb320ccd2009-10-21 03:42:58 +0000210 }
211}
212
213/* Return the difference of two FILETIME structs in seconds */
214static double timeDiff(FILETIME *pStart, FILETIME *pEnd){
215 sqlite_int64 i64Start = *((sqlite_int64 *) pStart);
216 sqlite_int64 i64End = *((sqlite_int64 *) pEnd);
217 return (double) ((i64End - i64Start) / 10000000.0);
218}
219
220/*
221** Print the timing results.
222*/
223static void endTimer(void){
224 if( enableTimer && getProcessTimesAddr){
225 FILETIME ftCreation, ftExit, ftKernelEnd, ftUserEnd;
drh43408312013-10-30 12:43:36 +0000226 sqlite3_int64 ftWallEnd = timeOfDay();
shaneb320ccd2009-10-21 03:42:58 +0000227 getProcessTimesAddr(hProcess, &ftCreation, &ftExit, &ftKernelEnd, &ftUserEnd);
drh43408312013-10-30 12:43:36 +0000228 printf("Run Time: real %.3f user %f sys %f\n",
229 (ftWallEnd - ftWallBegin)*0.001,
shaneb320ccd2009-10-21 03:42:58 +0000230 timeDiff(&ftUserBegin, &ftUserEnd),
231 timeDiff(&ftKernelBegin, &ftKernelEnd));
232 }
233}
234
235#define BEGIN_TIMER beginTimer()
236#define END_TIMER endTimer()
237#define HAS_TIMER hasTimer()
238
drhda108222009-02-25 19:07:24 +0000239#else
240#define BEGIN_TIMER
241#define END_TIMER
242#define HAS_TIMER 0
243#endif
244
shanec0688ea2009-03-05 03:48:06 +0000245/*
246** Used to prevent warnings about unused parameters
247*/
248#define UNUSED_PARAMETER(x) (void)(x)
249
drhe91d16b2008-12-08 18:27:31 +0000250/*
drhc49f44e2006-10-26 18:15:42 +0000251** If the following flag is set, then command execution stops
252** at an error if we are not interactive.
253*/
254static int bail_on_error = 0;
255
256/*
drhc28490c2006-10-26 14:25:58 +0000257** Threat stdin as an interactive input if the following variable
258** is true. Otherwise, assume stdin is connected to a file or pipe.
259*/
260static int stdin_is_interactive = 1;
261
262/*
drh4c504392000-10-16 22:06:40 +0000263** The following is the open SQLite database. We make a pointer
264** to this database a static variable so that it can be accessed
265** by the SIGINT handler to interrupt database processing.
266*/
danielk197792f9a1b2004-06-19 09:08:16 +0000267static sqlite3 *db = 0;
drh4c504392000-10-16 22:06:40 +0000268
269/*
drh67505e72002-04-19 12:34:06 +0000270** True if an interrupt (Control-C) has been received.
271*/
drh43617e92006-03-06 20:55:46 +0000272static volatile int seenInterrupt = 0;
drh67505e72002-04-19 12:34:06 +0000273
274/*
persicom7e2dfdd2002-04-18 02:46:52 +0000275** This is the name of our program. It is set in main(), used
276** in a number of other places, mostly for error messages.
277*/
278static char *Argv0;
279
280/*
281** Prompt strings. Initialized in main. Settable with
282** .prompt main continue
283*/
284static char mainPrompt[20]; /* First line prompt. default: "sqlite> "*/
285static char continuePrompt[20]; /* Continuation prompt. default: " ...> " */
286
drhb0603412007-02-28 04:47:26 +0000287/*
288** Write I/O traces to the following stream.
289*/
rsebe0a9092007-07-30 18:24:38 +0000290#ifdef SQLITE_ENABLE_IOTRACE
drhb0603412007-02-28 04:47:26 +0000291static FILE *iotrace = 0;
rsebe0a9092007-07-30 18:24:38 +0000292#endif
drhb0603412007-02-28 04:47:26 +0000293
294/*
295** This routine works like printf in that its first argument is a
296** format string and subsequent arguments are values to be substituted
297** in place of % fields. The result of formatting this string
298** is written to iotrace.
299*/
rsebe0a9092007-07-30 18:24:38 +0000300#ifdef SQLITE_ENABLE_IOTRACE
drhb0603412007-02-28 04:47:26 +0000301static void iotracePrintf(const char *zFormat, ...){
302 va_list ap;
drhf075cd02007-02-28 06:14:25 +0000303 char *z;
drhb0603412007-02-28 04:47:26 +0000304 if( iotrace==0 ) return;
305 va_start(ap, zFormat);
drhf075cd02007-02-28 06:14:25 +0000306 z = sqlite3_vmprintf(zFormat, ap);
drhb0603412007-02-28 04:47:26 +0000307 va_end(ap);
drhf075cd02007-02-28 06:14:25 +0000308 fprintf(iotrace, "%s", z);
309 sqlite3_free(z);
drhb0603412007-02-28 04:47:26 +0000310}
rsebe0a9092007-07-30 18:24:38 +0000311#endif
drhb0603412007-02-28 04:47:26 +0000312
drh44c2eb12003-04-30 11:38:26 +0000313
persicom7e2dfdd2002-04-18 02:46:52 +0000314/*
drh83965662003-04-17 02:54:13 +0000315** Determines if a string is a number of not.
316*/
danielk19772e588c72005-12-09 14:25:08 +0000317static int isNumber(const char *z, int *realnum){
drhc8d74412004-08-31 23:41:26 +0000318 if( *z=='-' || *z=='+' ) z++;
drhf0693c82011-10-11 20:41:54 +0000319 if( !IsDigit(*z) ){
drhc8d74412004-08-31 23:41:26 +0000320 return 0;
321 }
322 z++;
323 if( realnum ) *realnum = 0;
drhf0693c82011-10-11 20:41:54 +0000324 while( IsDigit(*z) ){ z++; }
drhc8d74412004-08-31 23:41:26 +0000325 if( *z=='.' ){
326 z++;
drhf0693c82011-10-11 20:41:54 +0000327 if( !IsDigit(*z) ) return 0;
328 while( IsDigit(*z) ){ z++; }
drhc8d74412004-08-31 23:41:26 +0000329 if( realnum ) *realnum = 1;
330 }
331 if( *z=='e' || *z=='E' ){
332 z++;
333 if( *z=='+' || *z=='-' ) z++;
drhf0693c82011-10-11 20:41:54 +0000334 if( !IsDigit(*z) ) return 0;
335 while( IsDigit(*z) ){ z++; }
drhc8d74412004-08-31 23:41:26 +0000336 if( realnum ) *realnum = 1;
337 }
338 return *z==0;
339}
drh83965662003-04-17 02:54:13 +0000340
341/*
danielk1977bc6ada42004-06-30 08:20:16 +0000342** A global char* and an SQL function to access its current value
343** from within an SQL statement. This program used to use the
344** sqlite_exec_printf() API to substitue a string into an SQL statement.
345** The correct way to do this with sqlite3 is to use the bind API, but
346** since the shell is built around the callback paradigm it would be a lot
347** of work. Instead just use this hack, which is quite harmless.
348*/
349static const char *zShellStatic = 0;
350static void shellstaticFunc(
351 sqlite3_context *context,
352 int argc,
353 sqlite3_value **argv
354){
355 assert( 0==argc );
356 assert( zShellStatic );
shaned87897d2009-01-30 05:40:27 +0000357 UNUSED_PARAMETER(argc);
drh902b9ee2008-12-05 17:17:07 +0000358 UNUSED_PARAMETER(argv);
danielk1977bc6ada42004-06-30 08:20:16 +0000359 sqlite3_result_text(context, zShellStatic, -1, SQLITE_STATIC);
360}
361
362
363/*
drhfeac5f82004-08-01 00:10:45 +0000364** This routine reads a line of text from FILE in, stores
drh8e7e7a22000-05-30 18:45:23 +0000365** the text in memory obtained from malloc() and returns a pointer
366** to the text. NULL is returned at end of file, or if malloc()
367** fails.
368**
drh9f099fd2013-08-06 14:01:46 +0000369** If zLine is not NULL then it is a malloced buffer returned from
370** a previous call to this routine that may be reused.
drh8e7e7a22000-05-30 18:45:23 +0000371*/
drh9f099fd2013-08-06 14:01:46 +0000372static char *local_getline(char *zLine, FILE *in){
373 int nLine = zLine==0 ? 0 : 100;
374 int n = 0;
drh8e7e7a22000-05-30 18:45:23 +0000375
drhb07028f2011-10-14 21:49:18 +0000376 while( 1 ){
drh8e7e7a22000-05-30 18:45:23 +0000377 if( n+100>nLine ){
378 nLine = nLine*2 + 100;
379 zLine = realloc(zLine, nLine);
380 if( zLine==0 ) return 0;
381 }
drhdaffd0e2001-04-11 14:28:42 +0000382 if( fgets(&zLine[n], nLine - n, in)==0 ){
drh8e7e7a22000-05-30 18:45:23 +0000383 if( n==0 ){
384 free(zLine);
385 return 0;
386 }
387 zLine[n] = 0;
drh8e7e7a22000-05-30 18:45:23 +0000388 break;
389 }
drh9f099fd2013-08-06 14:01:46 +0000390 while( zLine[n] ) n++;
391 if( n>0 && zLine[n-1]=='\n' ){
drh8e7e7a22000-05-30 18:45:23 +0000392 n--;
shaneh13b36022009-12-17 21:07:15 +0000393 if( n>0 && zLine[n-1]=='\r' ) n--;
drh8e7e7a22000-05-30 18:45:23 +0000394 zLine[n] = 0;
drhb07028f2011-10-14 21:49:18 +0000395 break;
drh8e7e7a22000-05-30 18:45:23 +0000396 }
397 }
drh8e7e7a22000-05-30 18:45:23 +0000398 return zLine;
399}
400
401/*
drhc28490c2006-10-26 14:25:58 +0000402** Retrieve a single line of input text.
drh8e7e7a22000-05-30 18:45:23 +0000403**
drh9f099fd2013-08-06 14:01:46 +0000404** If in==0 then read from standard input and prompt before each line.
405** If isContinuation is true, then a continuation prompt is appropriate.
406** If isContinuation is zero, then the main prompt should be used.
407**
408** If zPrior is not NULL then it is a buffer from a prior call to this
409** routine that can be reused.
410**
411** The result is stored in space obtained from malloc() and must either
412** be freed by the caller or else passed back into this routine via the
413** zPrior argument for reuse.
drh8e7e7a22000-05-30 18:45:23 +0000414*/
drh9f099fd2013-08-06 14:01:46 +0000415static char *one_input_line(FILE *in, char *zPrior, int isContinuation){
drh8e7e7a22000-05-30 18:45:23 +0000416 char *zPrompt;
417 char *zResult;
drhdaffd0e2001-04-11 14:28:42 +0000418 if( in!=0 ){
drh9f099fd2013-08-06 14:01:46 +0000419 zResult = local_getline(zPrior, in);
drh8e7e7a22000-05-30 18:45:23 +0000420 }else{
drh9f099fd2013-08-06 14:01:46 +0000421 zPrompt = isContinuation ? continuePrompt : mainPrompt;
drhaaa21b42014-02-11 14:37:51 +0000422#if defined(HAVE_READLINE)
drh9f099fd2013-08-06 14:01:46 +0000423 free(zPrior);
424 zResult = readline(zPrompt);
425 if( zResult && *zResult ) add_history(zResult);
426#else
427 printf("%s", zPrompt);
428 fflush(stdout);
429 zResult = local_getline(zPrior, stdin);
danielk19774af00c62005-01-23 23:43:21 +0000430#endif
drh9f099fd2013-08-06 14:01:46 +0000431 }
drh8e7e7a22000-05-30 18:45:23 +0000432 return zResult;
433}
434
persicom7e2dfdd2002-04-18 02:46:52 +0000435struct previous_mode_data {
436 int valid; /* Is there legit data in here? */
437 int mode;
438 int showHeader;
439 int colWidth[100];
440};
drh45e29d82006-11-20 16:21:10 +0000441
drh8e7e7a22000-05-30 18:45:23 +0000442/*
drh75897232000-05-29 14:26:00 +0000443** An pointer to an instance of this structure is passed from
444** the main program to the callback. This is used to communicate
445** state and mode information.
446*/
447struct callback_data {
shane626a6e42009-10-22 17:30:15 +0000448 sqlite3 *db; /* The database */
drhdaffd0e2001-04-11 14:28:42 +0000449 int echoOn; /* True to echo input commands */
drhc2ce0be2014-05-29 12:36:14 +0000450 int autoEQP; /* Run EXPLAIN QUERY PLAN prior to seach SQL stmt */
shaneh642d8b82010-07-28 16:05:34 +0000451 int statsOn; /* True to display memory stats before each finalize */
drhc2ce0be2014-05-29 12:36:14 +0000452 int outCount; /* Revert to stdout when reaching zero */
drh28bd4bc2000-06-15 15:57:22 +0000453 int cnt; /* Number of records displayed so far */
454 FILE *out; /* Write results here */
drh42f64e52012-04-04 16:56:23 +0000455 FILE *traceOut; /* Output for sqlite3_trace() */
drh2f464a02011-10-13 00:41:49 +0000456 int nErr; /* Number of errors seen */
drh28bd4bc2000-06-15 15:57:22 +0000457 int mode; /* An output mode setting */
drh45e29d82006-11-20 16:21:10 +0000458 int writableSchema; /* True if PRAGMA writable_schema=ON */
drh28bd4bc2000-06-15 15:57:22 +0000459 int showHeader; /* True to show column names in List or Column mode */
drh33048c02001-10-01 14:29:22 +0000460 char *zDestTable; /* Name of destination table when MODE_Insert */
mistachkin636bf9f2014-07-19 20:15:16 +0000461 char colSeparator[20]; /* Column separator character for several modes */
462 char rowSeparator[20]; /* Row separator character for MODE_Ascii */
drh6976c212014-07-24 12:09:47 +0000463 char newline[20]; /* Record separator in MODE_Csv */
drha0c66f52000-07-29 13:20:21 +0000464 int colWidth[100]; /* Requested width of each column when in column mode*/
465 int actualWidth[100]; /* Actual width of each column */
drh83965662003-04-17 02:54:13 +0000466 char nullvalue[20]; /* The text to print when a NULL comes back from
467 ** the database */
persicom7e2dfdd2002-04-18 02:46:52 +0000468 struct previous_mode_data explainPrev;
drh83965662003-04-17 02:54:13 +0000469 /* Holds the mode information just before
470 ** .explain ON */
drh44c2eb12003-04-30 11:38:26 +0000471 char outfile[FILENAME_MAX]; /* Filename for *out */
472 const char *zDbFilename; /* name of the database file */
drh05782482013-10-24 15:20:20 +0000473 char *zFreeOnClose; /* Filename to free when closing */
drha7e61d82011-03-12 17:02:57 +0000474 const char *zVfs; /* Name of VFS to use */
shane626a6e42009-10-22 17:30:15 +0000475 sqlite3_stmt *pStmt; /* Current statement if any. */
drh127f9d72010-02-23 01:47:00 +0000476 FILE *pLog; /* Write log output here */
dana98bf362013-11-13 18:35:01 +0000477 int *aiIndent; /* Array of indents used in MODE_Explain */
478 int nIndent; /* Size of array aiIndent[] */
danc4650bb2013-11-18 08:41:06 +0000479 int iIndent; /* Index of current op in aiIndent[] */
drh75897232000-05-29 14:26:00 +0000480};
481
482/*
483** These are the allowed modes.
484*/
drh967e8b72000-06-21 13:59:10 +0000485#define MODE_Line 0 /* One column per line. Blank line between records */
drh75897232000-05-29 14:26:00 +0000486#define MODE_Column 1 /* One record per line in neat columns */
487#define MODE_List 2 /* One record per line with a separator */
drhe3710332000-09-29 13:30:53 +0000488#define MODE_Semi 3 /* Same as MODE_List but append ";" to each line */
489#define MODE_Html 4 /* Generate an XHTML table */
490#define MODE_Insert 5 /* Generate SQL "insert" statements */
drhfeac5f82004-08-01 00:10:45 +0000491#define MODE_Tcl 6 /* Generate ANSI-C or TCL quoted elements */
drh8e64d1c2004-10-07 00:32:39 +0000492#define MODE_Csv 7 /* Quote strings, numbers are plain */
drh66ce4d02008-02-15 17:38:06 +0000493#define MODE_Explain 8 /* Like MODE_Column, but do not truncate data */
mistachkin636bf9f2014-07-19 20:15:16 +0000494#define MODE_Ascii 9 /* Use ASCII unit and record separators (0x1F/0x1E) */
persicom7e2dfdd2002-04-18 02:46:52 +0000495
drh66ce4d02008-02-15 17:38:06 +0000496static const char *modeDescr[] = {
persicom7e2dfdd2002-04-18 02:46:52 +0000497 "line",
498 "column",
499 "list",
500 "semi",
501 "html",
drhfeac5f82004-08-01 00:10:45 +0000502 "insert",
503 "tcl",
drh8e64d1c2004-10-07 00:32:39 +0000504 "csv",
drh66ce4d02008-02-15 17:38:06 +0000505 "explain",
mistachkin636bf9f2014-07-19 20:15:16 +0000506 "ascii",
persicom7e2dfdd2002-04-18 02:46:52 +0000507};
drh75897232000-05-29 14:26:00 +0000508
509/*
mistachkinfad42082014-07-24 22:13:12 +0000510** These are the column/row/line separators used by the various
511** import/export modes.
mistachkin636bf9f2014-07-19 20:15:16 +0000512*/
mistachkinfad42082014-07-24 22:13:12 +0000513#define SEP_Column "|"
514#define SEP_Row "\n"
515#define SEP_Tab "\t"
516#define SEP_Space " "
517#define SEP_Comma ","
518#define SEP_CrLf "\r\n"
519#define SEP_Unit "\x1F"
520#define SEP_Record "\x1E"
mistachkin636bf9f2014-07-19 20:15:16 +0000521
522/*
drh75897232000-05-29 14:26:00 +0000523** Number of elements in an array
524*/
drh902b9ee2008-12-05 17:17:07 +0000525#define ArraySize(X) (int)(sizeof(X)/sizeof(X[0]))
drh75897232000-05-29 14:26:00 +0000526
527/*
drhea678832008-12-10 19:26:22 +0000528** Compute a string length that is limited to what can be stored in
529** lower 30 bits of a 32-bit signed integer.
530*/
drh4f21c4a2008-12-10 22:15:00 +0000531static int strlen30(const char *z){
drhea678832008-12-10 19:26:22 +0000532 const char *z2 = z;
533 while( *z2 ){ z2++; }
534 return 0x3fffffff & (int)(z2 - z);
535}
536
537/*
drh127f9d72010-02-23 01:47:00 +0000538** A callback for the sqlite3_log() interface.
539*/
540static void shellLog(void *pArg, int iErrCode, const char *zMsg){
541 struct callback_data *p = (struct callback_data*)pArg;
542 if( p->pLog==0 ) return;
543 fprintf(p->pLog, "(%d) %s\n", iErrCode, zMsg);
544 fflush(p->pLog);
545}
546
547/*
shane626a6e42009-10-22 17:30:15 +0000548** Output the given string as a hex-encoded blob (eg. X'1234' )
549*/
550static void output_hex_blob(FILE *out, const void *pBlob, int nBlob){
551 int i;
552 char *zBlob = (char *)pBlob;
553 fprintf(out,"X'");
drhb202d702012-04-24 12:12:57 +0000554 for(i=0; i<nBlob; i++){ fprintf(out,"%02x",zBlob[i]&0xff); }
shane626a6e42009-10-22 17:30:15 +0000555 fprintf(out,"'");
556}
557
558/*
drh28bd4bc2000-06-15 15:57:22 +0000559** Output the given string as a quoted string using SQL quoting conventions.
560*/
561static void output_quoted_string(FILE *out, const char *z){
562 int i;
563 int nSingle = 0;
drh28bd4bc2000-06-15 15:57:22 +0000564 for(i=0; z[i]; i++){
565 if( z[i]=='\'' ) nSingle++;
drh28bd4bc2000-06-15 15:57:22 +0000566 }
567 if( nSingle==0 ){
568 fprintf(out,"'%s'",z);
drh28bd4bc2000-06-15 15:57:22 +0000569 }else{
570 fprintf(out,"'");
571 while( *z ){
572 for(i=0; z[i] && z[i]!='\''; i++){}
573 if( i==0 ){
574 fprintf(out,"''");
575 z++;
576 }else if( z[i]=='\'' ){
577 fprintf(out,"%.*s''",i,z);
578 z += i+1;
579 }else{
drhcd7d2732002-02-26 23:24:26 +0000580 fprintf(out,"%s",z);
drh28bd4bc2000-06-15 15:57:22 +0000581 break;
582 }
583 }
drhcd7d2732002-02-26 23:24:26 +0000584 fprintf(out,"'");
drh28bd4bc2000-06-15 15:57:22 +0000585 }
586}
587
588/*
drhfeac5f82004-08-01 00:10:45 +0000589** Output the given string as a quoted according to C or TCL quoting rules.
590*/
591static void output_c_string(FILE *out, const char *z){
592 unsigned int c;
593 fputc('"', out);
594 while( (c = *(z++))!=0 ){
595 if( c=='\\' ){
596 fputc(c, out);
597 fputc(c, out);
mistachkin585dcb22012-12-04 00:23:43 +0000598 }else if( c=='"' ){
599 fputc('\\', out);
600 fputc('"', out);
drhfeac5f82004-08-01 00:10:45 +0000601 }else if( c=='\t' ){
602 fputc('\\', out);
603 fputc('t', out);
604 }else if( c=='\n' ){
605 fputc('\\', out);
606 fputc('n', out);
607 }else if( c=='\r' ){
608 fputc('\\', out);
609 fputc('r', out);
mistachkinf6418892013-08-28 01:54:12 +0000610 }else if( !isprint(c&0xff) ){
drh0a8640d2005-08-30 20:12:02 +0000611 fprintf(out, "\\%03o", c&0xff);
drhfeac5f82004-08-01 00:10:45 +0000612 }else{
613 fputc(c, out);
614 }
615 }
616 fputc('"', out);
617}
618
619/*
drhc08a4f12000-06-15 16:49:48 +0000620** Output the given string with characters that are special to
621** HTML escaped.
622*/
623static void output_html_string(FILE *out, const char *z){
624 int i;
drhc3d6ba42014-01-13 20:38:35 +0000625 if( z==0 ) z = "";
drhc08a4f12000-06-15 16:49:48 +0000626 while( *z ){
shane43d9cb22009-10-21 14:11:48 +0000627 for(i=0; z[i]
628 && z[i]!='<'
629 && z[i]!='&'
630 && z[i]!='>'
631 && z[i]!='\"'
632 && z[i]!='\'';
633 i++){}
drhc08a4f12000-06-15 16:49:48 +0000634 if( i>0 ){
635 fprintf(out,"%.*s",i,z);
636 }
637 if( z[i]=='<' ){
638 fprintf(out,"&lt;");
639 }else if( z[i]=='&' ){
640 fprintf(out,"&amp;");
shane43d9cb22009-10-21 14:11:48 +0000641 }else if( z[i]=='>' ){
642 fprintf(out,"&gt;");
643 }else if( z[i]=='\"' ){
644 fprintf(out,"&quot;");
645 }else if( z[i]=='\'' ){
646 fprintf(out,"&#39;");
drhc08a4f12000-06-15 16:49:48 +0000647 }else{
648 break;
649 }
650 z += i + 1;
651 }
652}
653
654/*
drhc49f44e2006-10-26 18:15:42 +0000655** If a field contains any character identified by a 1 in the following
656** array, then the string must be quoted for CSV.
657*/
658static const char needCsvQuote[] = {
659 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
660 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
661 1, 0, 1, 0, 0, 0, 0, 1, 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, 0,
665 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
666 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 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 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
674 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
675};
676
677/*
drh8e64d1c2004-10-07 00:32:39 +0000678** Output a single term of CSV. Actually, p->separator is used for
679** the separator, which may or may not be a comma. p->nullvalue is
drh6976c212014-07-24 12:09:47 +0000680** the null value. Strings are quoted if necessary. The separator
681** is only issued if bSep is true.
drh8e64d1c2004-10-07 00:32:39 +0000682*/
683static void output_csv(struct callback_data *p, const char *z, int bSep){
drhc49f44e2006-10-26 18:15:42 +0000684 FILE *out = p->out;
drh8e64d1c2004-10-07 00:32:39 +0000685 if( z==0 ){
drhc49f44e2006-10-26 18:15:42 +0000686 fprintf(out,"%s",p->nullvalue);
drh8e64d1c2004-10-07 00:32:39 +0000687 }else{
drhc49f44e2006-10-26 18:15:42 +0000688 int i;
mistachkin636bf9f2014-07-19 20:15:16 +0000689 int nSep = strlen30(p->colSeparator);
drhc49f44e2006-10-26 18:15:42 +0000690 for(i=0; z[i]; i++){
drhc85375d2007-12-18 15:41:44 +0000691 if( needCsvQuote[((unsigned char*)z)[i]]
mistachkin636bf9f2014-07-19 20:15:16 +0000692 || (z[i]==p->colSeparator[0] &&
693 (nSep==1 || memcmp(z, p->colSeparator, nSep)==0)) ){
drhc49f44e2006-10-26 18:15:42 +0000694 i = 0;
695 break;
696 }
697 }
698 if( i==0 ){
699 putc('"', out);
700 for(i=0; z[i]; i++){
701 if( z[i]=='"' ) putc('"', out);
702 putc(z[i], out);
703 }
704 putc('"', out);
705 }else{
706 fprintf(out, "%s", z);
707 }
drh8e64d1c2004-10-07 00:32:39 +0000708 }
709 if( bSep ){
mistachkin636bf9f2014-07-19 20:15:16 +0000710 fprintf(p->out, "%s", p->colSeparator);
drh8e64d1c2004-10-07 00:32:39 +0000711 }
712}
713
danielk19774af00c62005-01-23 23:43:21 +0000714#ifdef SIGINT
drh8e64d1c2004-10-07 00:32:39 +0000715/*
drh4c504392000-10-16 22:06:40 +0000716** This routine runs when the user presses Ctrl-C
717*/
718static void interrupt_handler(int NotUsed){
drh902b9ee2008-12-05 17:17:07 +0000719 UNUSED_PARAMETER(NotUsed);
drh43ae8f62014-05-23 12:03:47 +0000720 seenInterrupt++;
721 if( seenInterrupt>2 ) exit(1);
danielk19776f8a5032004-05-10 10:34:51 +0000722 if( db ) sqlite3_interrupt(db);
drh4c504392000-10-16 22:06:40 +0000723}
danielk19774af00c62005-01-23 23:43:21 +0000724#endif
drh4c504392000-10-16 22:06:40 +0000725
726/*
shane626a6e42009-10-22 17:30:15 +0000727** This is the callback routine that the shell
drh75897232000-05-29 14:26:00 +0000728** invokes for each row of a query result.
729*/
shane626a6e42009-10-22 17:30:15 +0000730static int shell_callback(void *pArg, int nArg, char **azArg, char **azCol, int *aiType){
drh75897232000-05-29 14:26:00 +0000731 int i;
732 struct callback_data *p = (struct callback_data*)pArg;
shaneb9fc17d2009-10-22 21:23:35 +0000733
drh75897232000-05-29 14:26:00 +0000734 switch( p->mode ){
735 case MODE_Line: {
drhe3710332000-09-29 13:30:53 +0000736 int w = 5;
drh6a535342001-10-19 16:44:56 +0000737 if( azArg==0 ) break;
drhe3710332000-09-29 13:30:53 +0000738 for(i=0; i<nArg; i++){
drh4f21c4a2008-12-10 22:15:00 +0000739 int len = strlen30(azCol[i] ? azCol[i] : "");
drhe3710332000-09-29 13:30:53 +0000740 if( len>w ) w = len;
741 }
mistachkin636bf9f2014-07-19 20:15:16 +0000742 if( p->cnt++>0 ) fprintf(p->out, "%s", p->rowSeparator);
drh75897232000-05-29 14:26:00 +0000743 for(i=0; i<nArg; i++){
mistachkin636bf9f2014-07-19 20:15:16 +0000744 fprintf(p->out,"%*s = %s%s", w, azCol[i],
745 azArg[i] ? azArg[i] : p->nullvalue, p->rowSeparator);
drh75897232000-05-29 14:26:00 +0000746 }
747 break;
748 }
danielk19770d78bae2008-01-03 07:09:48 +0000749 case MODE_Explain:
drh75897232000-05-29 14:26:00 +0000750 case MODE_Column: {
drha0c66f52000-07-29 13:20:21 +0000751 if( p->cnt++==0 ){
drh75897232000-05-29 14:26:00 +0000752 for(i=0; i<nArg; i++){
drha0c66f52000-07-29 13:20:21 +0000753 int w, n;
754 if( i<ArraySize(p->colWidth) ){
danielk19770d78bae2008-01-03 07:09:48 +0000755 w = p->colWidth[i];
drh75897232000-05-29 14:26:00 +0000756 }else{
danielk19770d78bae2008-01-03 07:09:48 +0000757 w = 0;
drh75897232000-05-29 14:26:00 +0000758 }
drh078b1fd2012-09-21 13:40:02 +0000759 if( w==0 ){
drh4f21c4a2008-12-10 22:15:00 +0000760 w = strlen30(azCol[i] ? azCol[i] : "");
drha0c66f52000-07-29 13:20:21 +0000761 if( w<10 ) w = 10;
drh4f21c4a2008-12-10 22:15:00 +0000762 n = strlen30(azArg && azArg[i] ? azArg[i] : p->nullvalue);
drha0c66f52000-07-29 13:20:21 +0000763 if( w<n ) w = n;
764 }
765 if( i<ArraySize(p->actualWidth) ){
persicom1d0b8722002-04-18 02:53:04 +0000766 p->actualWidth[i] = w;
drha0c66f52000-07-29 13:20:21 +0000767 }
768 if( p->showHeader ){
drh078b1fd2012-09-21 13:40:02 +0000769 if( w<0 ){
mistachkin636bf9f2014-07-19 20:15:16 +0000770 fprintf(p->out,"%*.*s%s",-w,-w,azCol[i],
771 i==nArg-1 ? p->rowSeparator : " ");
drh078b1fd2012-09-21 13:40:02 +0000772 }else{
mistachkin636bf9f2014-07-19 20:15:16 +0000773 fprintf(p->out,"%-*.*s%s",w,w,azCol[i],
774 i==nArg-1 ? p->rowSeparator : " ");
drh078b1fd2012-09-21 13:40:02 +0000775 }
drha0c66f52000-07-29 13:20:21 +0000776 }
777 }
778 if( p->showHeader ){
779 for(i=0; i<nArg; i++){
780 int w;
781 if( i<ArraySize(p->actualWidth) ){
782 w = p->actualWidth[i];
drh078b1fd2012-09-21 13:40:02 +0000783 if( w<0 ) w = -w;
drha0c66f52000-07-29 13:20:21 +0000784 }else{
785 w = 10;
786 }
787 fprintf(p->out,"%-*.*s%s",w,w,"-----------------------------------"
788 "----------------------------------------------------------",
mistachkin636bf9f2014-07-19 20:15:16 +0000789 i==nArg-1 ? p->rowSeparator : " ");
drha0c66f52000-07-29 13:20:21 +0000790 }
drh75897232000-05-29 14:26:00 +0000791 }
792 }
drh6a535342001-10-19 16:44:56 +0000793 if( azArg==0 ) break;
drh75897232000-05-29 14:26:00 +0000794 for(i=0; i<nArg; i++){
795 int w;
drha0c66f52000-07-29 13:20:21 +0000796 if( i<ArraySize(p->actualWidth) ){
797 w = p->actualWidth[i];
drh75897232000-05-29 14:26:00 +0000798 }else{
799 w = 10;
800 }
dana98bf362013-11-13 18:35:01 +0000801 if( p->mode==MODE_Explain && azArg[i] && strlen30(azArg[i])>w ){
drh4f21c4a2008-12-10 22:15:00 +0000802 w = strlen30(azArg[i]);
danielk19770d78bae2008-01-03 07:09:48 +0000803 }
dana98bf362013-11-13 18:35:01 +0000804 if( i==1 && p->aiIndent && p->pStmt ){
danc4650bb2013-11-18 08:41:06 +0000805 if( p->iIndent<p->nIndent ){
806 fprintf(p->out, "%*.s", p->aiIndent[p->iIndent], "");
dana98bf362013-11-13 18:35:01 +0000807 }
danc4650bb2013-11-18 08:41:06 +0000808 p->iIndent++;
dana98bf362013-11-13 18:35:01 +0000809 }
drh078b1fd2012-09-21 13:40:02 +0000810 if( w<0 ){
811 fprintf(p->out,"%*.*s%s",-w,-w,
mistachkin636bf9f2014-07-19 20:15:16 +0000812 azArg[i] ? azArg[i] : p->nullvalue,
813 i==nArg-1 ? p->rowSeparator : " ");
drh078b1fd2012-09-21 13:40:02 +0000814 }else{
815 fprintf(p->out,"%-*.*s%s",w,w,
mistachkin636bf9f2014-07-19 20:15:16 +0000816 azArg[i] ? azArg[i] : p->nullvalue,
817 i==nArg-1 ? p->rowSeparator : " ");
drh078b1fd2012-09-21 13:40:02 +0000818 }
drh75897232000-05-29 14:26:00 +0000819 }
820 break;
821 }
drhe3710332000-09-29 13:30:53 +0000822 case MODE_Semi:
drh75897232000-05-29 14:26:00 +0000823 case MODE_List: {
824 if( p->cnt++==0 && p->showHeader ){
825 for(i=0; i<nArg; i++){
mistachkin636bf9f2014-07-19 20:15:16 +0000826 fprintf(p->out,"%s%s",azCol[i],
827 i==nArg-1 ? p->rowSeparator : p->colSeparator);
drh75897232000-05-29 14:26:00 +0000828 }
829 }
drh6a535342001-10-19 16:44:56 +0000830 if( azArg==0 ) break;
drh75897232000-05-29 14:26:00 +0000831 for(i=0; i<nArg; i++){
drh4c653a02000-06-07 01:27:47 +0000832 char *z = azArg[i];
persicom7e2dfdd2002-04-18 02:46:52 +0000833 if( z==0 ) z = p->nullvalue;
drh71172c52002-01-24 00:00:21 +0000834 fprintf(p->out, "%s", z);
drhe3710332000-09-29 13:30:53 +0000835 if( i<nArg-1 ){
mistachkin636bf9f2014-07-19 20:15:16 +0000836 fprintf(p->out, "%s", p->colSeparator);
drhe3710332000-09-29 13:30:53 +0000837 }else if( p->mode==MODE_Semi ){
mistachkin636bf9f2014-07-19 20:15:16 +0000838 fprintf(p->out, ";%s", p->rowSeparator);
drhe3710332000-09-29 13:30:53 +0000839 }else{
mistachkin636bf9f2014-07-19 20:15:16 +0000840 fprintf(p->out, "%s", p->rowSeparator);
drhe3710332000-09-29 13:30:53 +0000841 }
drh75897232000-05-29 14:26:00 +0000842 }
843 break;
844 }
drh1e5d0e92000-05-31 23:33:17 +0000845 case MODE_Html: {
846 if( p->cnt++==0 && p->showHeader ){
mihailim57c591a2008-06-23 21:26:05 +0000847 fprintf(p->out,"<TR>");
drh1e5d0e92000-05-31 23:33:17 +0000848 for(i=0; i<nArg; i++){
shane43d9cb22009-10-21 14:11:48 +0000849 fprintf(p->out,"<TH>");
850 output_html_string(p->out, azCol[i]);
851 fprintf(p->out,"</TH>\n");
drh1e5d0e92000-05-31 23:33:17 +0000852 }
mihailim57c591a2008-06-23 21:26:05 +0000853 fprintf(p->out,"</TR>\n");
drh1e5d0e92000-05-31 23:33:17 +0000854 }
drh6a535342001-10-19 16:44:56 +0000855 if( azArg==0 ) break;
mihailim57c591a2008-06-23 21:26:05 +0000856 fprintf(p->out,"<TR>");
drh1e5d0e92000-05-31 23:33:17 +0000857 for(i=0; i<nArg; i++){
mihailim57c591a2008-06-23 21:26:05 +0000858 fprintf(p->out,"<TD>");
persicom7e2dfdd2002-04-18 02:46:52 +0000859 output_html_string(p->out, azArg[i] ? azArg[i] : p->nullvalue);
mihailim57c591a2008-06-23 21:26:05 +0000860 fprintf(p->out,"</TD>\n");
drh1e5d0e92000-05-31 23:33:17 +0000861 }
mihailim57c591a2008-06-23 21:26:05 +0000862 fprintf(p->out,"</TR>\n");
drh1e5d0e92000-05-31 23:33:17 +0000863 break;
864 }
drhfeac5f82004-08-01 00:10:45 +0000865 case MODE_Tcl: {
866 if( p->cnt++==0 && p->showHeader ){
867 for(i=0; i<nArg; i++){
drh2cc55692006-06-27 20:39:04 +0000868 output_c_string(p->out,azCol[i] ? azCol[i] : "");
mistachkin636bf9f2014-07-19 20:15:16 +0000869 if(i<nArg-1) fprintf(p->out, "%s", p->colSeparator);
drhfeac5f82004-08-01 00:10:45 +0000870 }
mistachkin636bf9f2014-07-19 20:15:16 +0000871 fprintf(p->out, "%s", p->rowSeparator);
drhfeac5f82004-08-01 00:10:45 +0000872 }
873 if( azArg==0 ) break;
874 for(i=0; i<nArg; i++){
875 output_c_string(p->out, azArg[i] ? azArg[i] : p->nullvalue);
mistachkin636bf9f2014-07-19 20:15:16 +0000876 if(i<nArg-1) fprintf(p->out, "%s", p->colSeparator);
drhfeac5f82004-08-01 00:10:45 +0000877 }
mistachkin636bf9f2014-07-19 20:15:16 +0000878 fprintf(p->out, "%s", p->rowSeparator);
drhfeac5f82004-08-01 00:10:45 +0000879 break;
880 }
drh8e64d1c2004-10-07 00:32:39 +0000881 case MODE_Csv: {
drh6976c212014-07-24 12:09:47 +0000882#if defined(WIN32) || defined(_WIN32)
883 fflush(p->out);
884 _setmode(_fileno(p->out), _O_BINARY);
885#endif
drh8e64d1c2004-10-07 00:32:39 +0000886 if( p->cnt++==0 && p->showHeader ){
887 for(i=0; i<nArg; i++){
drh2cc55692006-06-27 20:39:04 +0000888 output_csv(p, azCol[i] ? azCol[i] : "", i<nArg-1);
drh8e64d1c2004-10-07 00:32:39 +0000889 }
mistachkinfad42082014-07-24 22:13:12 +0000890 fprintf(p->out, "%s", p->newline);
drh8e64d1c2004-10-07 00:32:39 +0000891 }
drh6976c212014-07-24 12:09:47 +0000892 if( azArg>0 ){
893 for(i=0; i<nArg; i++){
894 output_csv(p, azArg[i], i<nArg-1);
895 }
mistachkinfad42082014-07-24 22:13:12 +0000896 fprintf(p->out, "%s", p->newline);
drh8e64d1c2004-10-07 00:32:39 +0000897 }
drh6976c212014-07-24 12:09:47 +0000898#if defined(WIN32) || defined(_WIN32)
899 fflush(p->out);
900 _setmode(_fileno(p->out), _O_TEXT);
901#endif
drh8e64d1c2004-10-07 00:32:39 +0000902 break;
903 }
drh28bd4bc2000-06-15 15:57:22 +0000904 case MODE_Insert: {
shaneb9fc17d2009-10-22 21:23:35 +0000905 p->cnt++;
drh6a535342001-10-19 16:44:56 +0000906 if( azArg==0 ) break;
drh33048c02001-10-01 14:29:22 +0000907 fprintf(p->out,"INSERT INTO %s VALUES(",p->zDestTable);
drh28bd4bc2000-06-15 15:57:22 +0000908 for(i=0; i<nArg; i++){
909 char *zSep = i>0 ? ",": "";
shanead6b8d02009-10-22 18:12:58 +0000910 if( (azArg[i]==0) || (aiType && aiType[i]==SQLITE_NULL) ){
drh28bd4bc2000-06-15 15:57:22 +0000911 fprintf(p->out,"%sNULL",zSep);
shanead6b8d02009-10-22 18:12:58 +0000912 }else if( aiType && aiType[i]==SQLITE_TEXT ){
913 if( zSep[0] ) fprintf(p->out,"%s",zSep);
914 output_quoted_string(p->out, azArg[i]);
drhc2ce0be2014-05-29 12:36:14 +0000915 }else if( aiType && (aiType[i]==SQLITE_INTEGER
916 || aiType[i]==SQLITE_FLOAT) ){
shanead6b8d02009-10-22 18:12:58 +0000917 fprintf(p->out,"%s%s",zSep, azArg[i]);
shane626a6e42009-10-22 17:30:15 +0000918 }else if( aiType && aiType[i]==SQLITE_BLOB && p->pStmt ){
919 const void *pBlob = sqlite3_column_blob(p->pStmt, i);
920 int nBlob = sqlite3_column_bytes(p->pStmt, i);
921 if( zSep[0] ) fprintf(p->out,"%s",zSep);
922 output_hex_blob(p->out, pBlob, nBlob);
drhc8d74412004-08-31 23:41:26 +0000923 }else if( isNumber(azArg[i], 0) ){
drh28bd4bc2000-06-15 15:57:22 +0000924 fprintf(p->out,"%s%s",zSep, azArg[i]);
925 }else{
926 if( zSep[0] ) fprintf(p->out,"%s",zSep);
927 output_quoted_string(p->out, azArg[i]);
928 }
929 }
930 fprintf(p->out,");\n");
drh6a535342001-10-19 16:44:56 +0000931 break;
drh28bd4bc2000-06-15 15:57:22 +0000932 }
mistachkin636bf9f2014-07-19 20:15:16 +0000933 case MODE_Ascii: {
934 if( p->cnt++==0 && p->showHeader ){
935 for(i=0; i<nArg; i++){
936 if( i>0 ) fprintf(p->out, "%s", p->colSeparator);
937 fprintf(p->out,"%s",azCol[i] ? azCol[i] : "");
938 }
939 fprintf(p->out, "%s", p->rowSeparator);
940 }
941 if( azArg==0 ) break;
942 for(i=0; i<nArg; i++){
943 if( i>0 ) fprintf(p->out, "%s", p->colSeparator);
944 fprintf(p->out,"%s",azArg[i] ? azArg[i] : p->nullvalue);
945 }
946 fprintf(p->out, "%s", p->rowSeparator);
947 break;
948 }
persicom1d0b8722002-04-18 02:53:04 +0000949 }
drh75897232000-05-29 14:26:00 +0000950 return 0;
951}
952
953/*
shane626a6e42009-10-22 17:30:15 +0000954** This is the callback routine that the SQLite library
955** invokes for each row of a query result.
956*/
957static int callback(void *pArg, int nArg, char **azArg, char **azCol){
958 /* since we don't have type info, call the shell_callback with a NULL value */
959 return shell_callback(pArg, nArg, azArg, azCol, NULL);
960}
961
962/*
drh33048c02001-10-01 14:29:22 +0000963** Set the destination table field of the callback_data structure to
964** the name of the table given. Escape any quote characters in the
965** table name.
966*/
967static void set_table_name(struct callback_data *p, const char *zName){
968 int i, n;
969 int needQuote;
970 char *z;
971
972 if( p->zDestTable ){
973 free(p->zDestTable);
974 p->zDestTable = 0;
975 }
976 if( zName==0 ) return;
drh4c755c02004-08-08 20:22:17 +0000977 needQuote = !isalpha((unsigned char)*zName) && *zName!='_';
drh33048c02001-10-01 14:29:22 +0000978 for(i=n=0; zName[i]; i++, n++){
drh4c755c02004-08-08 20:22:17 +0000979 if( !isalnum((unsigned char)zName[i]) && zName[i]!='_' ){
drh33048c02001-10-01 14:29:22 +0000980 needQuote = 1;
981 if( zName[i]=='\'' ) n++;
982 }
983 }
984 if( needQuote ) n += 2;
985 z = p->zDestTable = malloc( n+1 );
986 if( z==0 ){
shane86f5bdb2009-10-24 02:00:07 +0000987 fprintf(stderr,"Error: out of memory\n");
drh33048c02001-10-01 14:29:22 +0000988 exit(1);
989 }
990 n = 0;
991 if( needQuote ) z[n++] = '\'';
992 for(i=0; zName[i]; i++){
993 z[n++] = zName[i];
994 if( zName[i]=='\'' ) z[n++] = '\'';
995 }
996 if( needQuote ) z[n++] = '\'';
997 z[n] = 0;
998}
999
danielk19772a02e332004-06-05 08:04:36 +00001000/* zIn is either a pointer to a NULL-terminated string in memory obtained
1001** from malloc(), or a NULL pointer. The string pointed to by zAppend is
1002** added to zIn, and the result returned in memory obtained from malloc().
1003** zIn, if it was not NULL, is freed.
1004**
1005** If the third argument, quote, is not '\0', then it is used as a
1006** quote character for zAppend.
1007*/
drhc28490c2006-10-26 14:25:58 +00001008static char *appendText(char *zIn, char const *zAppend, char quote){
danielk19772a02e332004-06-05 08:04:36 +00001009 int len;
1010 int i;
drh4f21c4a2008-12-10 22:15:00 +00001011 int nAppend = strlen30(zAppend);
1012 int nIn = (zIn?strlen30(zIn):0);
danielk19772a02e332004-06-05 08:04:36 +00001013
1014 len = nAppend+nIn+1;
1015 if( quote ){
1016 len += 2;
1017 for(i=0; i<nAppend; i++){
1018 if( zAppend[i]==quote ) len++;
1019 }
1020 }
1021
1022 zIn = (char *)realloc(zIn, len);
1023 if( !zIn ){
1024 return 0;
1025 }
1026
1027 if( quote ){
1028 char *zCsr = &zIn[nIn];
1029 *zCsr++ = quote;
1030 for(i=0; i<nAppend; i++){
1031 *zCsr++ = zAppend[i];
1032 if( zAppend[i]==quote ) *zCsr++ = quote;
1033 }
1034 *zCsr++ = quote;
1035 *zCsr++ = '\0';
1036 assert( (zCsr-zIn)==len );
1037 }else{
1038 memcpy(&zIn[nIn], zAppend, nAppend);
1039 zIn[len-1] = '\0';
1040 }
1041
1042 return zIn;
1043}
1044
drhdd3d4592004-08-30 01:54:05 +00001045
1046/*
drhb21a8e42012-01-28 21:08:51 +00001047** Execute a query statement that will generate SQL output. Print
1048** the result columns, comma-separated, on a line and then add a
1049** semicolon terminator to the end of that line.
drh45e29d82006-11-20 16:21:10 +00001050**
drhb21a8e42012-01-28 21:08:51 +00001051** If the number of columns is 1 and that column contains text "--"
1052** then write the semicolon on a separate line. That way, if a
1053** "--" comment occurs at the end of the statement, the comment
1054** won't consume the semicolon terminator.
drhdd3d4592004-08-30 01:54:05 +00001055*/
drh157e29a2009-05-21 15:15:00 +00001056static int run_table_dump_query(
drh2f464a02011-10-13 00:41:49 +00001057 struct callback_data *p, /* Query context */
1058 const char *zSelect, /* SELECT statement to extract content */
1059 const char *zFirstRow /* Print before first row, if not NULL */
drh157e29a2009-05-21 15:15:00 +00001060){
drhdd3d4592004-08-30 01:54:05 +00001061 sqlite3_stmt *pSelect;
1062 int rc;
drhb21a8e42012-01-28 21:08:51 +00001063 int nResult;
1064 int i;
1065 const char *z;
drhc7181902014-02-27 15:04:13 +00001066 rc = sqlite3_prepare_v2(p->db, zSelect, -1, &pSelect, 0);
drhdd3d4592004-08-30 01:54:05 +00001067 if( rc!=SQLITE_OK || !pSelect ){
drh2f464a02011-10-13 00:41:49 +00001068 fprintf(p->out, "/**** ERROR: (%d) %s *****/\n", rc, sqlite3_errmsg(p->db));
drh4384e982013-10-01 15:30:05 +00001069 if( (rc&0xff)!=SQLITE_CORRUPT ) p->nErr++;
drhdd3d4592004-08-30 01:54:05 +00001070 return rc;
1071 }
1072 rc = sqlite3_step(pSelect);
drhb21a8e42012-01-28 21:08:51 +00001073 nResult = sqlite3_column_count(pSelect);
drhdd3d4592004-08-30 01:54:05 +00001074 while( rc==SQLITE_ROW ){
drh157e29a2009-05-21 15:15:00 +00001075 if( zFirstRow ){
drh2f464a02011-10-13 00:41:49 +00001076 fprintf(p->out, "%s", zFirstRow);
drh157e29a2009-05-21 15:15:00 +00001077 zFirstRow = 0;
1078 }
drhb21a8e42012-01-28 21:08:51 +00001079 z = (const char*)sqlite3_column_text(pSelect, 0);
1080 fprintf(p->out, "%s", z);
1081 for(i=1; i<nResult; i++){
1082 fprintf(p->out, ",%s", sqlite3_column_text(pSelect, i));
1083 }
1084 if( z==0 ) z = "";
1085 while( z[0] && (z[0]!='-' || z[1]!='-') ) z++;
1086 if( z[0] ){
1087 fprintf(p->out, "\n;\n");
1088 }else{
1089 fprintf(p->out, ";\n");
1090 }
drhdd3d4592004-08-30 01:54:05 +00001091 rc = sqlite3_step(pSelect);
1092 }
drh2f464a02011-10-13 00:41:49 +00001093 rc = sqlite3_finalize(pSelect);
1094 if( rc!=SQLITE_OK ){
1095 fprintf(p->out, "/**** ERROR: (%d) %s *****/\n", rc, sqlite3_errmsg(p->db));
drh4384e982013-10-01 15:30:05 +00001096 if( (rc&0xff)!=SQLITE_CORRUPT ) p->nErr++;
drh2f464a02011-10-13 00:41:49 +00001097 }
1098 return rc;
drhdd3d4592004-08-30 01:54:05 +00001099}
1100
shane626a6e42009-10-22 17:30:15 +00001101/*
1102** Allocate space and save off current error string.
1103*/
1104static char *save_err_msg(
1105 sqlite3 *db /* Database to query */
1106){
1107 int nErrMsg = 1+strlen30(sqlite3_errmsg(db));
1108 char *zErrMsg = sqlite3_malloc(nErrMsg);
1109 if( zErrMsg ){
1110 memcpy(zErrMsg, sqlite3_errmsg(db), nErrMsg);
1111 }
1112 return zErrMsg;
1113}
1114
1115/*
shaneh642d8b82010-07-28 16:05:34 +00001116** Display memory stats.
1117*/
1118static int display_stats(
1119 sqlite3 *db, /* Database to query */
1120 struct callback_data *pArg, /* Pointer to struct callback_data */
1121 int bReset /* True to reset the stats */
1122){
1123 int iCur;
1124 int iHiwtr;
1125
1126 if( pArg && pArg->out ){
1127
1128 iHiwtr = iCur = -1;
1129 sqlite3_status(SQLITE_STATUS_MEMORY_USED, &iCur, &iHiwtr, bReset);
drh29dfbe32010-07-28 17:01:24 +00001130 fprintf(pArg->out, "Memory Used: %d (max %d) bytes\n", iCur, iHiwtr);
shaneh642d8b82010-07-28 16:05:34 +00001131 iHiwtr = iCur = -1;
1132 sqlite3_status(SQLITE_STATUS_MALLOC_COUNT, &iCur, &iHiwtr, bReset);
drh2a58e9c2010-12-21 21:28:38 +00001133 fprintf(pArg->out, "Number of Outstanding Allocations: %d (max %d)\n", iCur, iHiwtr);
shaneh642d8b82010-07-28 16:05:34 +00001134/*
1135** Not currently used by the CLI.
1136** iHiwtr = iCur = -1;
1137** sqlite3_status(SQLITE_STATUS_PAGECACHE_USED, &iCur, &iHiwtr, bReset);
1138** fprintf(pArg->out, "Number of Pcache Pages Used: %d (max %d) pages\n", iCur, iHiwtr);
1139*/
1140 iHiwtr = iCur = -1;
1141 sqlite3_status(SQLITE_STATUS_PAGECACHE_OVERFLOW, &iCur, &iHiwtr, bReset);
1142 fprintf(pArg->out, "Number of Pcache Overflow Bytes: %d (max %d) bytes\n", iCur, iHiwtr);
1143/*
1144** Not currently used by the CLI.
1145** iHiwtr = iCur = -1;
1146** sqlite3_status(SQLITE_STATUS_SCRATCH_USED, &iCur, &iHiwtr, bReset);
1147** fprintf(pArg->out, "Number of Scratch Allocations Used: %d (max %d)\n", iCur, iHiwtr);
1148*/
1149 iHiwtr = iCur = -1;
1150 sqlite3_status(SQLITE_STATUS_SCRATCH_OVERFLOW, &iCur, &iHiwtr, bReset);
1151 fprintf(pArg->out, "Number of Scratch Overflow Bytes: %d (max %d) bytes\n", iCur, iHiwtr);
1152 iHiwtr = iCur = -1;
1153 sqlite3_status(SQLITE_STATUS_MALLOC_SIZE, &iCur, &iHiwtr, bReset);
1154 fprintf(pArg->out, "Largest Allocation: %d bytes\n", iHiwtr);
1155 iHiwtr = iCur = -1;
1156 sqlite3_status(SQLITE_STATUS_PAGECACHE_SIZE, &iCur, &iHiwtr, bReset);
1157 fprintf(pArg->out, "Largest Pcache Allocation: %d bytes\n", iHiwtr);
1158 iHiwtr = iCur = -1;
1159 sqlite3_status(SQLITE_STATUS_SCRATCH_SIZE, &iCur, &iHiwtr, bReset);
1160 fprintf(pArg->out, "Largest Scratch Allocation: %d bytes\n", iHiwtr);
1161#ifdef YYTRACKMAXSTACKDEPTH
1162 iHiwtr = iCur = -1;
1163 sqlite3_status(SQLITE_STATUS_PARSER_STACK, &iCur, &iHiwtr, bReset);
1164 fprintf(pArg->out, "Deepest Parser Stack: %d (max %d)\n", iCur, iHiwtr);
1165#endif
1166 }
1167
1168 if( pArg && pArg->out && db ){
1169 iHiwtr = iCur = -1;
1170 sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_USED, &iCur, &iHiwtr, bReset);
1171 fprintf(pArg->out, "Lookaside Slots Used: %d (max %d)\n", iCur, iHiwtr);
drh2a58e9c2010-12-21 21:28:38 +00001172 sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_HIT, &iCur, &iHiwtr, bReset);
1173 fprintf(pArg->out, "Successful lookaside attempts: %d\n", iHiwtr);
1174 sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_MISS_SIZE, &iCur, &iHiwtr, bReset);
1175 fprintf(pArg->out, "Lookaside failures due to size: %d\n", iHiwtr);
1176 sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_MISS_FULL, &iCur, &iHiwtr, bReset);
1177 fprintf(pArg->out, "Lookaside failures due to OOM: %d\n", iHiwtr);
shaneh642d8b82010-07-28 16:05:34 +00001178 iHiwtr = iCur = -1;
1179 sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_USED, &iCur, &iHiwtr, bReset);
drhc78e6e42011-09-23 18:58:23 +00001180 fprintf(pArg->out, "Pager Heap Usage: %d bytes\n", iCur); iHiwtr = iCur = -1;
1181 sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_HIT, &iCur, &iHiwtr, 1);
1182 fprintf(pArg->out, "Page cache hits: %d\n", iCur);
1183 iHiwtr = iCur = -1;
1184 sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_MISS, &iCur, &iHiwtr, 1);
1185 fprintf(pArg->out, "Page cache misses: %d\n", iCur);
shaneh642d8b82010-07-28 16:05:34 +00001186 iHiwtr = iCur = -1;
drhfbbcd5d2012-03-24 20:09:33 +00001187 sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_WRITE, &iCur, &iHiwtr, 1);
1188 fprintf(pArg->out, "Page cache writes: %d\n", iCur);
1189 iHiwtr = iCur = -1;
shaneh642d8b82010-07-28 16:05:34 +00001190 sqlite3_db_status(db, SQLITE_DBSTATUS_SCHEMA_USED, &iCur, &iHiwtr, bReset);
1191 fprintf(pArg->out, "Schema Heap Usage: %d bytes\n", iCur);
1192 iHiwtr = iCur = -1;
1193 sqlite3_db_status(db, SQLITE_DBSTATUS_STMT_USED, &iCur, &iHiwtr, bReset);
1194 fprintf(pArg->out, "Statement Heap/Lookaside Usage: %d bytes\n", iCur);
1195 }
1196
1197 if( pArg && pArg->out && db && pArg->pStmt ){
1198 iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_FULLSCAN_STEP, bReset);
1199 fprintf(pArg->out, "Fullscan Steps: %d\n", iCur);
1200 iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_SORT, bReset);
1201 fprintf(pArg->out, "Sort Operations: %d\n", iCur);
1202 iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_AUTOINDEX, bReset);
1203 fprintf(pArg->out, "Autoindex Inserts: %d\n", iCur);
drhbf159fa2013-06-25 22:01:22 +00001204 iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_VM_STEP, bReset);
1205 fprintf(pArg->out, "Virtual Machine Steps: %d\n", iCur);
shaneh642d8b82010-07-28 16:05:34 +00001206 }
1207
1208 return 0;
1209}
1210
1211/*
dana98bf362013-11-13 18:35:01 +00001212** Parameter azArray points to a zero-terminated array of strings. zStr
1213** points to a single nul-terminated string. Return non-zero if zStr
1214** is equal, according to strcmp(), to any of the strings in the array.
1215** Otherwise, return zero.
1216*/
1217static int str_in_array(const char *zStr, const char **azArray){
1218 int i;
1219 for(i=0; azArray[i]; i++){
1220 if( 0==strcmp(zStr, azArray[i]) ) return 1;
1221 }
1222 return 0;
1223}
1224
1225/*
1226** If compiled statement pSql appears to be an EXPLAIN statement, allocate
1227** and populate the callback_data.aiIndent[] array with the number of
1228** spaces each opcode should be indented before it is output.
1229**
1230** The indenting rules are:
1231**
1232** * For each "Next", "Prev", "VNext" or "VPrev" instruction, indent
1233** all opcodes that occur between the p2 jump destination and the opcode
1234** itself by 2 spaces.
1235**
drh01752bc2013-11-14 23:59:33 +00001236** * For each "Goto", if the jump destination is earlier in the program
1237** and ends on one of:
drhe73f0592014-01-21 22:25:45 +00001238** Yield SeekGt SeekLt RowSetRead Rewind
drhfe705102014-03-06 13:38:37 +00001239** or if the P1 parameter is one instead of zero,
drh01752bc2013-11-14 23:59:33 +00001240** then indent all opcodes between the earlier instruction
drhd2447442013-11-13 19:01:41 +00001241** and "Goto" by 2 spaces.
dana98bf362013-11-13 18:35:01 +00001242*/
1243static void explain_data_prepare(struct callback_data *p, sqlite3_stmt *pSql){
1244 const char *zSql; /* The text of the SQL statement */
1245 const char *z; /* Used to check if this is an EXPLAIN */
1246 int *abYield = 0; /* True if op is an OP_Yield */
1247 int nAlloc = 0; /* Allocated size of p->aiIndent[], abYield */
danc4650bb2013-11-18 08:41:06 +00001248 int iOp; /* Index of operation in p->aiIndent[] */
dana98bf362013-11-13 18:35:01 +00001249
drh8ad0de32014-03-20 18:45:27 +00001250 const char *azNext[] = { "Next", "Prev", "VPrev", "VNext", "SorterNext",
1251 "NextIfOpen", "PrevIfOpen", 0 };
drhb463fef2014-05-29 20:17:57 +00001252 const char *azYield[] = { "Yield", "SeekLT", "SeekGT", "RowSetRead", "Rewind", 0 };
dana98bf362013-11-13 18:35:01 +00001253 const char *azGoto[] = { "Goto", 0 };
1254
1255 /* Try to figure out if this is really an EXPLAIN statement. If this
1256 ** cannot be verified, return early. */
1257 zSql = sqlite3_sql(pSql);
1258 if( zSql==0 ) return;
1259 for(z=zSql; *z==' ' || *z=='\t' || *z=='\n' || *z=='\f' || *z=='\r'; z++);
1260 if( sqlite3_strnicmp(z, "explain", 7) ) return;
1261
1262 for(iOp=0; SQLITE_ROW==sqlite3_step(pSql); iOp++){
1263 int i;
danc4650bb2013-11-18 08:41:06 +00001264 int iAddr = sqlite3_column_int(pSql, 0);
dana98bf362013-11-13 18:35:01 +00001265 const char *zOp = (const char*)sqlite3_column_text(pSql, 1);
danc4650bb2013-11-18 08:41:06 +00001266
1267 /* Set p2 to the P2 field of the current opcode. Then, assuming that
1268 ** p2 is an instruction address, set variable p2op to the index of that
1269 ** instruction in the aiIndent[] array. p2 and p2op may be different if
1270 ** the current instruction is part of a sub-program generated by an
1271 ** SQL trigger or foreign key. */
dana98bf362013-11-13 18:35:01 +00001272 int p2 = sqlite3_column_int(pSql, 3);
danc4650bb2013-11-18 08:41:06 +00001273 int p2op = (p2 + (iOp-iAddr));
dana98bf362013-11-13 18:35:01 +00001274
1275 /* Grow the p->aiIndent array as required */
1276 if( iOp>=nAlloc ){
1277 nAlloc += 100;
1278 p->aiIndent = (int*)sqlite3_realloc(p->aiIndent, nAlloc*sizeof(int));
1279 abYield = (int*)sqlite3_realloc(abYield, nAlloc*sizeof(int));
1280 }
1281 abYield[iOp] = str_in_array(zOp, azYield);
1282 p->aiIndent[iOp] = 0;
1283 p->nIndent = iOp+1;
1284
1285 if( str_in_array(zOp, azNext) ){
danc4650bb2013-11-18 08:41:06 +00001286 for(i=p2op; i<iOp; i++) p->aiIndent[i] += 2;
dana98bf362013-11-13 18:35:01 +00001287 }
drhfe705102014-03-06 13:38:37 +00001288 if( str_in_array(zOp, azGoto) && p2op<p->nIndent
1289 && (abYield[p2op] || sqlite3_column_int(pSql, 2))
1290 ){
drhe73f0592014-01-21 22:25:45 +00001291 for(i=p2op+1; i<iOp; i++) p->aiIndent[i] += 2;
dana98bf362013-11-13 18:35:01 +00001292 }
1293 }
1294
danc4650bb2013-11-18 08:41:06 +00001295 p->iIndent = 0;
dana98bf362013-11-13 18:35:01 +00001296 sqlite3_free(abYield);
1297 sqlite3_reset(pSql);
1298}
1299
1300/*
1301** Free the array allocated by explain_data_prepare().
1302*/
1303static void explain_data_delete(struct callback_data *p){
1304 sqlite3_free(p->aiIndent);
1305 p->aiIndent = 0;
1306 p->nIndent = 0;
danc4650bb2013-11-18 08:41:06 +00001307 p->iIndent = 0;
dana98bf362013-11-13 18:35:01 +00001308}
1309
1310/*
shane626a6e42009-10-22 17:30:15 +00001311** Execute a statement or set of statements. Print
1312** any result rows/columns depending on the current mode
1313** set via the supplied callback.
1314**
1315** This is very similar to SQLite's built-in sqlite3_exec()
1316** function except it takes a slightly different callback
1317** and callback data argument.
1318*/
1319static int shell_exec(
1320 sqlite3 *db, /* An open database */
1321 const char *zSql, /* SQL to be evaluated */
1322 int (*xCallback)(void*,int,char**,char**,int*), /* Callback function */
1323 /* (not the same as sqlite3_exec) */
1324 struct callback_data *pArg, /* Pointer to struct callback_data */
1325 char **pzErrMsg /* Error msg written here */
1326){
dan4564ced2010-01-05 04:59:56 +00001327 sqlite3_stmt *pStmt = NULL; /* Statement to execute. */
1328 int rc = SQLITE_OK; /* Return Code */
drhb07028f2011-10-14 21:49:18 +00001329 int rc2;
dan4564ced2010-01-05 04:59:56 +00001330 const char *zLeftover; /* Tail of unprocessed SQL */
shane626a6e42009-10-22 17:30:15 +00001331
1332 if( pzErrMsg ){
1333 *pzErrMsg = NULL;
1334 }
1335
shaneb9fc17d2009-10-22 21:23:35 +00001336 while( zSql[0] && (SQLITE_OK == rc) ){
1337 rc = sqlite3_prepare_v2(db, zSql, -1, &pStmt, &zLeftover);
1338 if( SQLITE_OK != rc ){
shane626a6e42009-10-22 17:30:15 +00001339 if( pzErrMsg ){
1340 *pzErrMsg = save_err_msg(db);
1341 }
1342 }else{
shaneb9fc17d2009-10-22 21:23:35 +00001343 if( !pStmt ){
1344 /* this happens for a comment or white-space */
1345 zSql = zLeftover;
drhf0693c82011-10-11 20:41:54 +00001346 while( IsSpace(zSql[0]) ) zSql++;
shaneb9fc17d2009-10-22 21:23:35 +00001347 continue;
1348 }
shane626a6e42009-10-22 17:30:15 +00001349
shaneh642d8b82010-07-28 16:05:34 +00001350 /* save off the prepared statment handle and reset row count */
1351 if( pArg ){
1352 pArg->pStmt = pStmt;
1353 pArg->cnt = 0;
1354 }
1355
shanehb7977c52010-01-18 18:17:10 +00001356 /* echo the sql statement if echo on */
shaneh642d8b82010-07-28 16:05:34 +00001357 if( pArg && pArg->echoOn ){
drha8c62df2010-02-15 15:47:18 +00001358 const char *zStmtSql = sqlite3_sql(pStmt);
shaneh642d8b82010-07-28 16:05:34 +00001359 fprintf(pArg->out, "%s\n", zStmtSql ? zStmtSql : zSql);
drha8c62df2010-02-15 15:47:18 +00001360 }
shanehb7977c52010-01-18 18:17:10 +00001361
drhefbf3b12014-02-28 20:47:24 +00001362 /* Show the EXPLAIN QUERY PLAN if .eqp is on */
1363 if( pArg && pArg->autoEQP ){
1364 sqlite3_stmt *pExplain;
1365 char *zEQP = sqlite3_mprintf("EXPLAIN QUERY PLAN %s", sqlite3_sql(pStmt));
1366 rc = sqlite3_prepare_v2(db, zEQP, -1, &pExplain, 0);
1367 if( rc==SQLITE_OK ){
1368 while( sqlite3_step(pExplain)==SQLITE_ROW ){
1369 fprintf(pArg->out,"--EQP-- %d,", sqlite3_column_int(pExplain, 0));
1370 fprintf(pArg->out,"%d,", sqlite3_column_int(pExplain, 1));
1371 fprintf(pArg->out,"%d,", sqlite3_column_int(pExplain, 2));
1372 fprintf(pArg->out,"%s\n", sqlite3_column_text(pExplain, 3));
1373 }
1374 }
1375 sqlite3_finalize(pExplain);
1376 sqlite3_free(zEQP);
1377 }
1378
drh7e02e5e2011-12-06 19:44:51 +00001379 /* Output TESTCTRL_EXPLAIN text of requested */
1380 if( pArg && pArg->mode==MODE_Explain ){
1381 const char *zExplain = 0;
1382 sqlite3_test_control(SQLITE_TESTCTRL_EXPLAIN_STMT, pStmt, &zExplain);
1383 if( zExplain && zExplain[0] ){
1384 fprintf(pArg->out, "%s", zExplain);
1385 }
1386 }
1387
dana98bf362013-11-13 18:35:01 +00001388 /* If the shell is currently in ".explain" mode, gather the extra
1389 ** data required to add indents to the output.*/
drh0a305922013-11-21 23:37:02 +00001390 if( pArg && pArg->mode==MODE_Explain ){
dana98bf362013-11-13 18:35:01 +00001391 explain_data_prepare(pArg, pStmt);
1392 }
1393
shaneb9fc17d2009-10-22 21:23:35 +00001394 /* perform the first step. this will tell us if we
1395 ** have a result set or not and how wide it is.
1396 */
1397 rc = sqlite3_step(pStmt);
1398 /* if we have a result set... */
1399 if( SQLITE_ROW == rc ){
1400 /* if we have a callback... */
1401 if( xCallback ){
1402 /* allocate space for col name ptr, value ptr, and type */
1403 int nCol = sqlite3_column_count(pStmt);
1404 void *pData = sqlite3_malloc(3*nCol*sizeof(const char*) + 1);
1405 if( !pData ){
1406 rc = SQLITE_NOMEM;
1407 }else{
1408 char **azCols = (char **)pData; /* Names of result columns */
1409 char **azVals = &azCols[nCol]; /* Results */
1410 int *aiTypes = (int *)&azVals[nCol]; /* Result types */
drh55a1b302013-09-04 16:08:50 +00001411 int i, x;
shaneb9fc17d2009-10-22 21:23:35 +00001412 assert(sizeof(int) <= sizeof(char *));
1413 /* save off ptrs to column names */
1414 for(i=0; i<nCol; i++){
1415 azCols[i] = (char *)sqlite3_column_name(pStmt, i);
1416 }
shaneb9fc17d2009-10-22 21:23:35 +00001417 do{
1418 /* extract the data and data types */
1419 for(i=0; i<nCol; i++){
drh55a1b302013-09-04 16:08:50 +00001420 aiTypes[i] = x = sqlite3_column_type(pStmt, i);
drh3432daa2013-10-11 16:35:49 +00001421 if( x==SQLITE_BLOB && pArg && pArg->mode==MODE_Insert ){
drh55a1b302013-09-04 16:08:50 +00001422 azVals[i] = "";
1423 }else{
1424 azVals[i] = (char*)sqlite3_column_text(pStmt, i);
1425 }
shaneb9fc17d2009-10-22 21:23:35 +00001426 if( !azVals[i] && (aiTypes[i]!=SQLITE_NULL) ){
1427 rc = SQLITE_NOMEM;
1428 break; /* from for */
1429 }
1430 } /* end for */
1431
1432 /* if data and types extracted successfully... */
1433 if( SQLITE_ROW == rc ){
1434 /* call the supplied callback with the result row data */
1435 if( xCallback(pArg, nCol, azVals, azCols, aiTypes) ){
1436 rc = SQLITE_ABORT;
1437 }else{
1438 rc = sqlite3_step(pStmt);
1439 }
1440 }
1441 } while( SQLITE_ROW == rc );
1442 sqlite3_free(pData);
shaneb9fc17d2009-10-22 21:23:35 +00001443 }
1444 }else{
1445 do{
1446 rc = sqlite3_step(pStmt);
1447 } while( rc == SQLITE_ROW );
1448 }
1449 }
1450
dana98bf362013-11-13 18:35:01 +00001451 explain_data_delete(pArg);
1452
shaneh642d8b82010-07-28 16:05:34 +00001453 /* print usage stats if stats on */
1454 if( pArg && pArg->statsOn ){
1455 display_stats(db, pArg, 0);
1456 }
1457
dan4564ced2010-01-05 04:59:56 +00001458 /* Finalize the statement just executed. If this fails, save a
1459 ** copy of the error message. Otherwise, set zSql to point to the
1460 ** next statement to execute. */
drhb07028f2011-10-14 21:49:18 +00001461 rc2 = sqlite3_finalize(pStmt);
1462 if( rc!=SQLITE_NOMEM ) rc = rc2;
dan4564ced2010-01-05 04:59:56 +00001463 if( rc==SQLITE_OK ){
shaneb9fc17d2009-10-22 21:23:35 +00001464 zSql = zLeftover;
drhf0693c82011-10-11 20:41:54 +00001465 while( IsSpace(zSql[0]) ) zSql++;
dan4564ced2010-01-05 04:59:56 +00001466 }else if( pzErrMsg ){
1467 *pzErrMsg = save_err_msg(db);
shane626a6e42009-10-22 17:30:15 +00001468 }
shaneh642d8b82010-07-28 16:05:34 +00001469
1470 /* clear saved stmt handle */
1471 if( pArg ){
1472 pArg->pStmt = NULL;
1473 }
shane626a6e42009-10-22 17:30:15 +00001474 }
shaneb9fc17d2009-10-22 21:23:35 +00001475 } /* end while */
shane626a6e42009-10-22 17:30:15 +00001476
1477 return rc;
1478}
1479
drhdd3d4592004-08-30 01:54:05 +00001480
drh33048c02001-10-01 14:29:22 +00001481/*
drh4c653a02000-06-07 01:27:47 +00001482** This is a different callback routine used for dumping the database.
1483** Each row received by this callback consists of a table name,
1484** the table type ("index" or "table") and SQL to create the table.
1485** This routine should print text sufficient to recreate the table.
1486*/
1487static int dump_callback(void *pArg, int nArg, char **azArg, char **azCol){
danielk19772a02e332004-06-05 08:04:36 +00001488 int rc;
1489 const char *zTable;
1490 const char *zType;
1491 const char *zSql;
drh157e29a2009-05-21 15:15:00 +00001492 const char *zPrepStmt = 0;
drhdaffd0e2001-04-11 14:28:42 +00001493 struct callback_data *p = (struct callback_data *)pArg;
danielk19772a02e332004-06-05 08:04:36 +00001494
drh902b9ee2008-12-05 17:17:07 +00001495 UNUSED_PARAMETER(azCol);
drh4c653a02000-06-07 01:27:47 +00001496 if( nArg!=3 ) return 1;
danielk19772a02e332004-06-05 08:04:36 +00001497 zTable = azArg[0];
1498 zType = azArg[1];
1499 zSql = azArg[2];
1500
drh00b950d2005-09-11 02:03:03 +00001501 if( strcmp(zTable, "sqlite_sequence")==0 ){
drh157e29a2009-05-21 15:15:00 +00001502 zPrepStmt = "DELETE FROM sqlite_sequence;\n";
drh7ed10322013-08-07 16:04:27 +00001503 }else if( sqlite3_strglob("sqlite_stat?", zTable)==0 ){
drh00b950d2005-09-11 02:03:03 +00001504 fprintf(p->out, "ANALYZE sqlite_master;\n");
1505 }else if( strncmp(zTable, "sqlite_", 7)==0 ){
1506 return 0;
drh45e29d82006-11-20 16:21:10 +00001507 }else if( strncmp(zSql, "CREATE VIRTUAL TABLE", 20)==0 ){
1508 char *zIns;
1509 if( !p->writableSchema ){
1510 fprintf(p->out, "PRAGMA writable_schema=ON;\n");
1511 p->writableSchema = 1;
1512 }
1513 zIns = sqlite3_mprintf(
1514 "INSERT INTO sqlite_master(type,name,tbl_name,rootpage,sql)"
1515 "VALUES('table','%q','%q',0,'%q');",
1516 zTable, zTable, zSql);
1517 fprintf(p->out, "%s\n", zIns);
1518 sqlite3_free(zIns);
1519 return 0;
drh00b950d2005-09-11 02:03:03 +00001520 }else{
1521 fprintf(p->out, "%s;\n", zSql);
drhf8eb96a2005-02-03 00:42:34 +00001522 }
danielk19772a02e332004-06-05 08:04:36 +00001523
1524 if( strcmp(zType, "table")==0 ){
1525 sqlite3_stmt *pTableInfo = 0;
danielk19772a02e332004-06-05 08:04:36 +00001526 char *zSelect = 0;
1527 char *zTableInfo = 0;
1528 char *zTmp = 0;
drh157e29a2009-05-21 15:15:00 +00001529 int nRow = 0;
danielk19772a02e332004-06-05 08:04:36 +00001530
1531 zTableInfo = appendText(zTableInfo, "PRAGMA table_info(", 0);
1532 zTableInfo = appendText(zTableInfo, zTable, '"');
1533 zTableInfo = appendText(zTableInfo, ");", 0);
1534
drhc7181902014-02-27 15:04:13 +00001535 rc = sqlite3_prepare_v2(p->db, zTableInfo, -1, &pTableInfo, 0);
drh157e29a2009-05-21 15:15:00 +00001536 free(zTableInfo);
danielk19772a02e332004-06-05 08:04:36 +00001537 if( rc!=SQLITE_OK || !pTableInfo ){
1538 return 1;
1539 }
1540
1541 zSelect = appendText(zSelect, "SELECT 'INSERT INTO ' || ", 0);
drhbf92ec02012-03-22 12:50:34 +00001542 /* Always quote the table name, even if it appears to be pure ascii,
1543 ** in case it is a keyword. Ex: INSERT INTO "table" ... */
1544 zTmp = appendText(zTmp, zTable, '"');
danielk19772a02e332004-06-05 08:04:36 +00001545 if( zTmp ){
1546 zSelect = appendText(zSelect, zTmp, '\'');
drh85e72432012-04-11 11:38:53 +00001547 free(zTmp);
danielk19772a02e332004-06-05 08:04:36 +00001548 }
1549 zSelect = appendText(zSelect, " || ' VALUES(' || ", 0);
1550 rc = sqlite3_step(pTableInfo);
1551 while( rc==SQLITE_ROW ){
danielk19772e588c72005-12-09 14:25:08 +00001552 const char *zText = (const char *)sqlite3_column_text(pTableInfo, 1);
danielk19773f41e972004-06-08 00:39:01 +00001553 zSelect = appendText(zSelect, "quote(", 0);
danielk19772e588c72005-12-09 14:25:08 +00001554 zSelect = appendText(zSelect, zText, '"');
danielk19772a02e332004-06-05 08:04:36 +00001555 rc = sqlite3_step(pTableInfo);
1556 if( rc==SQLITE_ROW ){
drhb21a8e42012-01-28 21:08:51 +00001557 zSelect = appendText(zSelect, "), ", 0);
danielk19772a02e332004-06-05 08:04:36 +00001558 }else{
1559 zSelect = appendText(zSelect, ") ", 0);
1560 }
drh157e29a2009-05-21 15:15:00 +00001561 nRow++;
danielk19772a02e332004-06-05 08:04:36 +00001562 }
1563 rc = sqlite3_finalize(pTableInfo);
drh157e29a2009-05-21 15:15:00 +00001564 if( rc!=SQLITE_OK || nRow==0 ){
1565 free(zSelect);
danielk19772a02e332004-06-05 08:04:36 +00001566 return 1;
1567 }
1568 zSelect = appendText(zSelect, "|| ')' FROM ", 0);
1569 zSelect = appendText(zSelect, zTable, '"');
1570
drh2f464a02011-10-13 00:41:49 +00001571 rc = run_table_dump_query(p, zSelect, zPrepStmt);
drhdd3d4592004-08-30 01:54:05 +00001572 if( rc==SQLITE_CORRUPT ){
1573 zSelect = appendText(zSelect, " ORDER BY rowid DESC", 0);
drh2f464a02011-10-13 00:41:49 +00001574 run_table_dump_query(p, zSelect, 0);
drhdd3d4592004-08-30 01:54:05 +00001575 }
drh85e72432012-04-11 11:38:53 +00001576 free(zSelect);
drh4c653a02000-06-07 01:27:47 +00001577 }
drh4c653a02000-06-07 01:27:47 +00001578 return 0;
1579}
1580
1581/*
drh45e29d82006-11-20 16:21:10 +00001582** Run zQuery. Use dump_callback() as the callback routine so that
1583** the contents of the query are output as SQL statements.
1584**
drhdd3d4592004-08-30 01:54:05 +00001585** If we get a SQLITE_CORRUPT error, rerun the query after appending
1586** "ORDER BY rowid DESC" to the end.
1587*/
1588static int run_schema_dump_query(
1589 struct callback_data *p,
drh2f464a02011-10-13 00:41:49 +00001590 const char *zQuery
drhdd3d4592004-08-30 01:54:05 +00001591){
1592 int rc;
drh2f464a02011-10-13 00:41:49 +00001593 char *zErr = 0;
1594 rc = sqlite3_exec(p->db, zQuery, dump_callback, p, &zErr);
drhdd3d4592004-08-30 01:54:05 +00001595 if( rc==SQLITE_CORRUPT ){
1596 char *zQ2;
drh4f21c4a2008-12-10 22:15:00 +00001597 int len = strlen30(zQuery);
drh2f464a02011-10-13 00:41:49 +00001598 fprintf(p->out, "/****** CORRUPTION ERROR *******/\n");
1599 if( zErr ){
1600 fprintf(p->out, "/****** %s ******/\n", zErr);
1601 sqlite3_free(zErr);
1602 zErr = 0;
1603 }
drhdd3d4592004-08-30 01:54:05 +00001604 zQ2 = malloc( len+100 );
1605 if( zQ2==0 ) return rc;
drh8c5058b2012-04-16 17:22:30 +00001606 sqlite3_snprintf(len+100, zQ2, "%s ORDER BY rowid DESC", zQuery);
drh2f464a02011-10-13 00:41:49 +00001607 rc = sqlite3_exec(p->db, zQ2, dump_callback, p, &zErr);
1608 if( rc ){
1609 fprintf(p->out, "/****** ERROR: %s ******/\n", zErr);
1610 }else{
1611 rc = SQLITE_CORRUPT;
1612 }
1613 sqlite3_free(zErr);
drhdd3d4592004-08-30 01:54:05 +00001614 free(zQ2);
1615 }
1616 return rc;
1617}
1618
1619/*
drh75897232000-05-29 14:26:00 +00001620** Text of a help message
1621*/
persicom1d0b8722002-04-18 02:53:04 +00001622static char zHelp[] =
drh9ff849f2009-02-04 20:55:57 +00001623 ".backup ?DB? FILE Backup DB (default \"main\") to FILE\n"
drhc2ce0be2014-05-29 12:36:14 +00001624 ".bail on|off Stop after hitting an error. Default OFF\n"
drh4bbcf102014-02-06 02:46:08 +00001625 ".clone NEWDB Clone data into NEWDB from the existing database\n"
mistachkin486fd432014-07-24 22:20:23 +00001626 ".colseparator STRING This is an alias for the one argument version of\n"
1627 " .separator\n"
jplyon6a65bb32003-05-04 07:25:57 +00001628 ".databases List names and files of attached databases\n"
drhb860bc92004-08-04 15:16:55 +00001629 ".dump ?TABLE? ... Dump the database in an SQL text format\n"
shane86f5bdb2009-10-24 02:00:07 +00001630 " If TABLE specified, only dump tables matching\n"
1631 " LIKE pattern TABLE.\n"
drhc2ce0be2014-05-29 12:36:14 +00001632 ".echo on|off Turn command echo on or off\n"
drh6d36ffe2014-06-16 15:01:37 +00001633 ".eqp on|off Enable or disable automatic EXPLAIN QUERY PLAN\n"
drh75897232000-05-29 14:26:00 +00001634 ".exit Exit this program\n"
drhc2ce0be2014-05-29 12:36:14 +00001635 ".explain ?on|off? Turn output mode suitable for EXPLAIN on or off.\n"
shanehe2aa9d72009-11-06 17:20:17 +00001636 " With no args, it turns EXPLAIN on.\n"
drhc1971542014-06-23 23:28:13 +00001637 ".fullschema Show schema and the content of sqlite_stat tables\n"
drhc2ce0be2014-05-29 12:36:14 +00001638 ".headers on|off Turn display of headers on or off\n"
drh75897232000-05-29 14:26:00 +00001639 ".help Show this message\n"
drhb860bc92004-08-04 15:16:55 +00001640 ".import FILE TABLE Import data from FILE into TABLE\n"
shane86f5bdb2009-10-24 02:00:07 +00001641 ".indices ?TABLE? Show names of all indices\n"
1642 " If TABLE specified, only show indices for tables\n"
1643 " matching LIKE pattern TABLE.\n"
drhae5e4452007-05-03 17:18:36 +00001644#ifdef SQLITE_ENABLE_IOTRACE
1645 ".iotrace FILE Enable I/O diagnostic logging to FILE\n"
1646#endif
drh70df4fe2006-06-13 15:12:21 +00001647#ifndef SQLITE_OMIT_LOAD_EXTENSION
drh1e397f82006-06-08 15:28:43 +00001648 ".load FILE ?ENTRY? Load an extension library\n"
drh70df4fe2006-06-13 15:12:21 +00001649#endif
drh127f9d72010-02-23 01:47:00 +00001650 ".log FILE|off Turn logging on or off. FILE can be stderr/stdout\n"
danielk19776b77a362005-01-13 11:10:25 +00001651 ".mode MODE ?TABLE? Set output mode where MODE is one of:\n"
mistachkin636bf9f2014-07-19 20:15:16 +00001652 " ascii Columns/rows delimited with 0x1F and 0x1E\n"
drh3b584fa2004-09-24 12:50:03 +00001653 " csv Comma-separated values\n"
drhb860bc92004-08-04 15:16:55 +00001654 " column Left-aligned columns. (See .width)\n"
1655 " html HTML <table> code\n"
1656 " insert SQL insert statements for TABLE\n"
1657 " line One value per line\n"
1658 " list Values delimited by .separator string\n"
1659 " tabs Tab-separated values\n"
1660 " tcl TCL list elements\n"
drh078b1fd2012-09-21 13:40:02 +00001661 ".nullvalue STRING Use STRING in place of NULL values\n"
drhc2ce0be2014-05-29 12:36:14 +00001662 ".once FILENAME Output for the next SQL command only to FILENAME\n"
drh05782482013-10-24 15:20:20 +00001663 ".open ?FILENAME? Close existing database and reopen FILENAME\n"
drhc2ce0be2014-05-29 12:36:14 +00001664 ".output ?FILENAME? Send output to FILENAME or stdout\n"
drh078b1fd2012-09-21 13:40:02 +00001665 ".print STRING... Print literal STRING\n"
persicom7e2dfdd2002-04-18 02:46:52 +00001666 ".prompt MAIN CONTINUE Replace the standard prompts\n"
persicom7e2dfdd2002-04-18 02:46:52 +00001667 ".quit Exit this program\n"
drhdaffd0e2001-04-11 14:28:42 +00001668 ".read FILENAME Execute SQL in FILENAME\n"
drh9ff849f2009-02-04 20:55:57 +00001669 ".restore ?DB? FILE Restore content of DB (default \"main\") from FILE\n"
mistachkin636bf9f2014-07-19 20:15:16 +00001670 ".rowseparator STRING Change row separator for output mode and .import\n"
drh5c7976f2014-02-10 19:59:27 +00001671 ".save FILE Write in-memory database into FILE\n"
drh75897232000-05-29 14:26:00 +00001672 ".schema ?TABLE? Show the CREATE statements\n"
shane86f5bdb2009-10-24 02:00:07 +00001673 " If TABLE specified, only show tables matching\n"
1674 " LIKE pattern TABLE.\n"
mistachkinfad42082014-07-24 22:13:12 +00001675 ".separator STRING ?NL? Change column separator for output mode and .import\n"
drh6976c212014-07-24 12:09:47 +00001676 " NL is the end-of-line mark for CSV\n"
drh62cdde52014-05-28 20:22:28 +00001677 ".shell CMD ARGS... Run CMD ARGS... in a system shell\n"
drhdd45df82002-04-18 12:39:03 +00001678 ".show Show the current values for various settings\n"
drhc2ce0be2014-05-29 12:36:14 +00001679 ".stats on|off Turn stats on or off\n"
drh62cdde52014-05-28 20:22:28 +00001680 ".system CMD ARGS... Run CMD ARGS... in a system shell\n"
shane86f5bdb2009-10-24 02:00:07 +00001681 ".tables ?TABLE? List names of tables\n"
1682 " If TABLE specified, only list tables matching\n"
1683 " LIKE pattern TABLE.\n"
drh2dfbbca2000-07-28 14:32:48 +00001684 ".timeout MS Try opening locked tables for MS milliseconds\n"
drhc2ce0be2014-05-29 12:36:14 +00001685 ".timer on|off Turn SQL timer on or off\n"
drh42f64e52012-04-04 16:56:23 +00001686 ".trace FILE|off Output each SQL statement as it is run\n"
drhde60fc22011-12-14 17:53:36 +00001687 ".vfsname ?AUX? Print the name of the VFS stack\n"
shanehe2aa9d72009-11-06 17:20:17 +00001688 ".width NUM1 NUM2 ... Set column widths for \"column\" mode\n"
drh62cdde52014-05-28 20:22:28 +00001689 " Negative values right-justify\n"
drh75897232000-05-29 14:26:00 +00001690;
1691
drhdaffd0e2001-04-11 14:28:42 +00001692/* Forward reference */
drhc28490c2006-10-26 14:25:58 +00001693static int process_input(struct callback_data *p, FILE *in);
drhba5b0932014-07-24 12:39:59 +00001694/*
1695** Implementation of the "readfile(X)" SQL function. The entire content
1696** of the file named X is read and returned as a BLOB. NULL is returned
1697** if the file does not exist or is unreadable.
1698*/
1699static void readfileFunc(
1700 sqlite3_context *context,
1701 int argc,
1702 sqlite3_value **argv
1703){
1704 const char *zName;
1705 FILE *in;
1706 long nIn;
1707 void *pBuf;
1708
1709 zName = (const char*)sqlite3_value_text(argv[0]);
1710 if( zName==0 ) return;
1711 in = fopen(zName, "rb");
1712 if( in==0 ) return;
1713 fseek(in, 0, SEEK_END);
1714 nIn = ftell(in);
1715 rewind(in);
1716 pBuf = sqlite3_malloc( nIn );
1717 if( pBuf && 1==fread(pBuf, nIn, 1, in) ){
1718 sqlite3_result_blob(context, pBuf, nIn, sqlite3_free);
1719 }else{
1720 sqlite3_free(pBuf);
1721 }
1722 fclose(in);
1723}
1724
1725/*
1726** Implementation of the "writefile(X,Y)" SQL function. The argument Y
1727** is written into file X. The number of bytes written is returned. Or
1728** NULL is returned if something goes wrong, such as being unable to open
1729** file X for writing.
1730*/
1731static void writefileFunc(
1732 sqlite3_context *context,
1733 int argc,
1734 sqlite3_value **argv
1735){
1736 FILE *out;
1737 const char *z;
1738 int n;
1739 sqlite3_int64 rc;
1740 const char *zFile;
1741
1742 zFile = (const char*)sqlite3_value_text(argv[0]);
1743 if( zFile==0 ) return;
1744 out = fopen(zFile, "wb");
1745 if( out==0 ) return;
1746 z = (const char*)sqlite3_value_blob(argv[1]);
1747 if( z==0 ){
1748 n = 0;
1749 rc = 0;
1750 }else{
1751 n = sqlite3_value_bytes(argv[1]);
1752 rc = fwrite(z, 1, n, out);
1753 }
1754 fclose(out);
1755 sqlite3_result_int64(context, rc);
1756}
drhdaffd0e2001-04-11 14:28:42 +00001757
drh75897232000-05-29 14:26:00 +00001758/*
drh44c2eb12003-04-30 11:38:26 +00001759** Make sure the database is open. If it is not, then open it. If
1760** the database fails to open, print an error message and exit.
1761*/
drh05782482013-10-24 15:20:20 +00001762static void open_db(struct callback_data *p, int keepAlive){
drh44c2eb12003-04-30 11:38:26 +00001763 if( p->db==0 ){
drhbbb0be82012-06-27 16:12:27 +00001764 sqlite3_initialize();
danielk19774f057f92004-06-08 00:02:33 +00001765 sqlite3_open(p->zDbFilename, &p->db);
danielk197780290862004-05-22 09:21:21 +00001766 db = p->db;
drh4cea5ba2008-05-05 16:27:24 +00001767 if( db && sqlite3_errcode(db)==SQLITE_OK ){
1768 sqlite3_create_function(db, "shellstatic", 0, SQLITE_UTF8, 0,
1769 shellstaticFunc, 0, 0);
1770 }
1771 if( db==0 || SQLITE_OK!=sqlite3_errcode(db) ){
shane86f5bdb2009-10-24 02:00:07 +00001772 fprintf(stderr,"Error: unable to open database \"%s\": %s\n",
danielk197780290862004-05-22 09:21:21 +00001773 p->zDbFilename, sqlite3_errmsg(db));
drh05782482013-10-24 15:20:20 +00001774 if( keepAlive ) return;
drh22fbcb82004-02-01 01:22:50 +00001775 exit(1);
drh44c2eb12003-04-30 11:38:26 +00001776 }
drhc2e87a32006-06-27 15:16:14 +00001777#ifndef SQLITE_OMIT_LOAD_EXTENSION
1778 sqlite3_enable_load_extension(p->db, 1);
1779#endif
drhba5b0932014-07-24 12:39:59 +00001780 sqlite3_create_function(db, "readfile", 1, SQLITE_UTF8, 0,
1781 readfileFunc, 0, 0);
1782 sqlite3_create_function(db, "writefile", 2, SQLITE_UTF8, 0,
1783 writefileFunc, 0, 0);
drh44c2eb12003-04-30 11:38:26 +00001784 }
1785}
1786
1787/*
drhfeac5f82004-08-01 00:10:45 +00001788** Do C-language style dequoting.
1789**
1790** \t -> tab
1791** \n -> newline
1792** \r -> carriage return
drh4c56b992013-06-27 13:26:55 +00001793** \" -> "
drhfeac5f82004-08-01 00:10:45 +00001794** \NNN -> ascii character NNN in octal
1795** \\ -> backslash
1796*/
1797static void resolve_backslashes(char *z){
shane7d3846a2008-12-11 02:58:26 +00001798 int i, j;
1799 char c;
drhc2ce0be2014-05-29 12:36:14 +00001800 while( *z && *z!='\\' ) z++;
drhfeac5f82004-08-01 00:10:45 +00001801 for(i=j=0; (c = z[i])!=0; i++, j++){
1802 if( c=='\\' ){
1803 c = z[++i];
1804 if( c=='n' ){
1805 c = '\n';
1806 }else if( c=='t' ){
1807 c = '\t';
1808 }else if( c=='r' ){
1809 c = '\r';
drh4c56b992013-06-27 13:26:55 +00001810 }else if( c=='\\' ){
1811 c = '\\';
drhfeac5f82004-08-01 00:10:45 +00001812 }else if( c>='0' && c<='7' ){
drhaa816082005-12-29 12:53:09 +00001813 c -= '0';
drhfeac5f82004-08-01 00:10:45 +00001814 if( z[i+1]>='0' && z[i+1]<='7' ){
1815 i++;
1816 c = (c<<3) + z[i] - '0';
1817 if( z[i+1]>='0' && z[i+1]<='7' ){
1818 i++;
1819 c = (c<<3) + z[i] - '0';
1820 }
1821 }
1822 }
1823 }
1824 z[j] = c;
1825 }
drhc2ce0be2014-05-29 12:36:14 +00001826 if( j<i ) z[j] = 0;
drhfeac5f82004-08-01 00:10:45 +00001827}
1828
1829/*
drh348d19c2013-06-03 12:47:43 +00001830** Return the value of a hexadecimal digit. Return -1 if the input
1831** is not a hex digit.
drhc28490c2006-10-26 14:25:58 +00001832*/
drh348d19c2013-06-03 12:47:43 +00001833static int hexDigitValue(char c){
1834 if( c>='0' && c<='9' ) return c - '0';
1835 if( c>='a' && c<='f' ) return c - 'a' + 10;
1836 if( c>='A' && c<='F' ) return c - 'A' + 10;
1837 return -1;
drhc28490c2006-10-26 14:25:58 +00001838}
1839
1840/*
drh7d9f3942013-04-03 01:26:54 +00001841** Interpret zArg as an integer value, possibly with suffixes.
1842*/
1843static sqlite3_int64 integerValue(const char *zArg){
1844 sqlite3_int64 v = 0;
1845 static const struct { char *zSuffix; int iMult; } aMult[] = {
1846 { "KiB", 1024 },
1847 { "MiB", 1024*1024 },
1848 { "GiB", 1024*1024*1024 },
1849 { "KB", 1000 },
1850 { "MB", 1000000 },
1851 { "GB", 1000000000 },
1852 { "K", 1000 },
1853 { "M", 1000000 },
1854 { "G", 1000000000 },
1855 };
1856 int i;
1857 int isNeg = 0;
1858 if( zArg[0]=='-' ){
1859 isNeg = 1;
1860 zArg++;
1861 }else if( zArg[0]=='+' ){
1862 zArg++;
1863 }
drh348d19c2013-06-03 12:47:43 +00001864 if( zArg[0]=='0' && zArg[1]=='x' ){
1865 int x;
1866 zArg += 2;
1867 while( (x = hexDigitValue(zArg[0]))>=0 ){
1868 v = (v<<4) + x;
1869 zArg++;
1870 }
1871 }else{
1872 while( IsDigit(zArg[0]) ){
1873 v = v*10 + zArg[0] - '0';
1874 zArg++;
1875 }
drh7d9f3942013-04-03 01:26:54 +00001876 }
drhc2bed0a2013-05-24 11:57:50 +00001877 for(i=0; i<ArraySize(aMult); i++){
drh7d9f3942013-04-03 01:26:54 +00001878 if( sqlite3_stricmp(aMult[i].zSuffix, zArg)==0 ){
1879 v *= aMult[i].iMult;
1880 break;
1881 }
1882 }
1883 return isNeg? -v : v;
1884}
1885
1886/*
drh348d19c2013-06-03 12:47:43 +00001887** Interpret zArg as either an integer or a boolean value. Return 1 or 0
1888** for TRUE and FALSE. Return the integer value if appropriate.
1889*/
1890static int booleanValue(char *zArg){
1891 int i;
1892 if( zArg[0]=='0' && zArg[1]=='x' ){
1893 for(i=2; hexDigitValue(zArg[i])>=0; i++){}
1894 }else{
1895 for(i=0; zArg[i]>='0' && zArg[i]<='9'; i++){}
1896 }
1897 if( i>0 && zArg[i]==0 ) return (int)(integerValue(zArg) & 0xffffffff);
1898 if( sqlite3_stricmp(zArg, "on")==0 || sqlite3_stricmp(zArg,"yes")==0 ){
1899 return 1;
1900 }
1901 if( sqlite3_stricmp(zArg, "off")==0 || sqlite3_stricmp(zArg,"no")==0 ){
1902 return 0;
1903 }
1904 fprintf(stderr, "ERROR: Not a boolean value: \"%s\". Assuming \"no\".\n",
1905 zArg);
1906 return 0;
1907}
1908
1909/*
drh42f64e52012-04-04 16:56:23 +00001910** Close an output file, assuming it is not stderr or stdout
1911*/
1912static void output_file_close(FILE *f){
1913 if( f && f!=stdout && f!=stderr ) fclose(f);
1914}
1915
1916/*
1917** Try to open an output file. The names "stdout" and "stderr" are
1918** recognized and do the right thing. NULL is returned if the output
1919** filename is "off".
1920*/
1921static FILE *output_file_open(const char *zFile){
1922 FILE *f;
1923 if( strcmp(zFile,"stdout")==0 ){
1924 f = stdout;
1925 }else if( strcmp(zFile, "stderr")==0 ){
1926 f = stderr;
1927 }else if( strcmp(zFile, "off")==0 ){
1928 f = 0;
1929 }else{
1930 f = fopen(zFile, "wb");
1931 if( f==0 ){
1932 fprintf(stderr, "Error: cannot open \"%s\"\n", zFile);
1933 }
1934 }
1935 return f;
1936}
1937
1938/*
1939** A routine for handling output from sqlite3_trace().
1940*/
1941static void sql_trace_callback(void *pArg, const char *z){
1942 FILE *f = (FILE*)pArg;
1943 if( f ) fprintf(f, "%s\n", z);
1944}
1945
1946/*
drhd8621b92012-04-17 09:09:33 +00001947** A no-op routine that runs with the ".breakpoint" doc-command. This is
1948** a useful spot to set a debugger breakpoint.
1949*/
1950static void test_breakpoint(void){
1951 static int nCall = 0;
1952 nCall++;
1953}
1954
1955/*
mistachkin636bf9f2014-07-19 20:15:16 +00001956** An object used to read a CSV and other files for import.
drhdb95f682013-06-26 22:46:00 +00001957*/
mistachkin636bf9f2014-07-19 20:15:16 +00001958typedef struct ImportCtx ImportCtx;
1959struct ImportCtx {
drhdb95f682013-06-26 22:46:00 +00001960 const char *zFile; /* Name of the input file */
1961 FILE *in; /* Read the CSV text from this input stream */
1962 char *z; /* Accumulated text for a field */
1963 int n; /* Number of bytes in z */
1964 int nAlloc; /* Space allocated for z[] */
1965 int nLine; /* Current line number */
1966 int cTerm; /* Character that terminated the most recent field */
mistachkin636bf9f2014-07-19 20:15:16 +00001967 int cColSep; /* The column separator character. (Usually ",") */
1968 int cRowSep; /* The row separator character. (Usually "\n") */
drhdb95f682013-06-26 22:46:00 +00001969};
1970
1971/* Append a single byte to z[] */
mistachkin636bf9f2014-07-19 20:15:16 +00001972static void import_append_char(ImportCtx *p, int c){
drhdb95f682013-06-26 22:46:00 +00001973 if( p->n+1>=p->nAlloc ){
1974 p->nAlloc += p->nAlloc + 100;
1975 p->z = sqlite3_realloc(p->z, p->nAlloc);
1976 if( p->z==0 ){
1977 fprintf(stderr, "out of memory\n");
1978 exit(1);
1979 }
1980 }
1981 p->z[p->n++] = (char)c;
1982}
1983
1984/* Read a single field of CSV text. Compatible with rfc4180 and extended
1985** with the option of having a separator other than ",".
1986**
1987** + Input comes from p->in.
1988** + Store results in p->z of length p->n. Space to hold p->z comes
1989** from sqlite3_malloc().
mistachkin636bf9f2014-07-19 20:15:16 +00001990** + Use p->cSep as the column separator. The default is ",".
1991** + Use p->rSep as the row separator. The default is "\n".
drhdb95f682013-06-26 22:46:00 +00001992** + Keep track of the line number in p->nLine.
1993** + Store the character that terminates the field in p->cTerm. Store
1994** EOF on end-of-file.
1995** + Report syntax errors on stderr
1996*/
mistachkin636bf9f2014-07-19 20:15:16 +00001997static char *csv_read_one_field(ImportCtx *p){
1998 int c;
1999 int cSep = p->cColSep;
2000 int rSep = p->cRowSep;
drhdb95f682013-06-26 22:46:00 +00002001 p->n = 0;
2002 c = fgetc(p->in);
2003 if( c==EOF || seenInterrupt ){
2004 p->cTerm = EOF;
2005 return 0;
2006 }
2007 if( c=='"' ){
mistachkin636bf9f2014-07-19 20:15:16 +00002008 int pc, ppc;
drhdb95f682013-06-26 22:46:00 +00002009 int startLine = p->nLine;
2010 int cQuote = c;
drha81ad172013-12-11 14:00:04 +00002011 pc = ppc = 0;
drhdb95f682013-06-26 22:46:00 +00002012 while( 1 ){
2013 c = fgetc(p->in);
mistachkin636bf9f2014-07-19 20:15:16 +00002014 if( c==rSep ) p->nLine++;
drhdb95f682013-06-26 22:46:00 +00002015 if( c==cQuote ){
2016 if( pc==cQuote ){
2017 pc = 0;
2018 continue;
2019 }
2020 }
2021 if( (c==cSep && pc==cQuote)
mistachkin636bf9f2014-07-19 20:15:16 +00002022 || (c==rSep && pc==cQuote)
2023 || (c==rSep && pc=='\r' && ppc==cQuote)
drhdb95f682013-06-26 22:46:00 +00002024 || (c==EOF && pc==cQuote)
2025 ){
2026 do{ p->n--; }while( p->z[p->n]!=cQuote );
drhdb95f682013-06-26 22:46:00 +00002027 p->cTerm = c;
2028 break;
2029 }
2030 if( pc==cQuote && c!='\r' ){
2031 fprintf(stderr, "%s:%d: unescaped %c character\n",
2032 p->zFile, p->nLine, cQuote);
2033 }
2034 if( c==EOF ){
2035 fprintf(stderr, "%s:%d: unterminated %c-quoted field\n",
2036 p->zFile, startLine, cQuote);
mistachkin636bf9f2014-07-19 20:15:16 +00002037 p->cTerm = c;
drhdb95f682013-06-26 22:46:00 +00002038 break;
2039 }
mistachkin636bf9f2014-07-19 20:15:16 +00002040 import_append_char(p, c);
drha81ad172013-12-11 14:00:04 +00002041 ppc = pc;
drhdb95f682013-06-26 22:46:00 +00002042 pc = c;
drhd0a64dc2013-06-30 20:24:26 +00002043 }
drhdb95f682013-06-26 22:46:00 +00002044 }else{
mistachkin636bf9f2014-07-19 20:15:16 +00002045 while( c!=EOF && c!=cSep && c!=rSep ){
2046 import_append_char(p, c);
drhd0a64dc2013-06-30 20:24:26 +00002047 c = fgetc(p->in);
drhdb95f682013-06-26 22:46:00 +00002048 }
mistachkin636bf9f2014-07-19 20:15:16 +00002049 if( c==rSep ){
drhdb95f682013-06-26 22:46:00 +00002050 p->nLine++;
drh3852b682014-02-26 13:53:34 +00002051 if( p->n>0 && p->z[p->n-1]=='\r' ) p->n--;
drhdb95f682013-06-26 22:46:00 +00002052 }
drhdb95f682013-06-26 22:46:00 +00002053 p->cTerm = c;
2054 }
drh8dd675e2013-07-12 21:09:24 +00002055 if( p->z ) p->z[p->n] = 0;
drhdb95f682013-06-26 22:46:00 +00002056 return p->z;
2057}
2058
mistachkin636bf9f2014-07-19 20:15:16 +00002059/* Read a single field of ASCII delimited text.
2060**
2061** + Input comes from p->in.
2062** + Store results in p->z of length p->n. Space to hold p->z comes
2063** from sqlite3_malloc().
2064** + Use p->cSep as the column separator. The default is "\x1F".
2065** + Use p->rSep as the row separator. The default is "\x1E".
2066** + Keep track of the row number in p->nLine.
2067** + Store the character that terminates the field in p->cTerm. Store
2068** EOF on end-of-file.
2069** + Report syntax errors on stderr
2070*/
2071static char *ascii_read_one_field(ImportCtx *p){
2072 int c;
2073 int cSep = p->cColSep;
2074 int rSep = p->cRowSep;
2075 p->n = 0;
2076 c = fgetc(p->in);
2077 if( c==EOF || seenInterrupt ){
2078 p->cTerm = EOF;
2079 return 0;
2080 }
2081 while( c!=EOF && c!=cSep && c!=rSep ){
2082 import_append_char(p, c);
2083 c = fgetc(p->in);
2084 }
2085 if( c==rSep ){
2086 p->nLine++;
2087 }
2088 p->cTerm = c;
2089 if( p->z ) p->z[p->n] = 0;
2090 return p->z;
2091}
2092
drhdb95f682013-06-26 22:46:00 +00002093/*
drh4bbcf102014-02-06 02:46:08 +00002094** Try to transfer data for table zTable. If an error is seen while
2095** moving forward, try to go backwards. The backwards movement won't
2096** work for WITHOUT ROWID tables.
drh3350ce92014-02-06 00:49:12 +00002097*/
mistachkine31ae902014-02-06 01:15:29 +00002098static void tryToCloneData(
drh3350ce92014-02-06 00:49:12 +00002099 struct callback_data *p,
2100 sqlite3 *newDb,
2101 const char *zTable
2102){
2103 sqlite3_stmt *pQuery = 0;
2104 sqlite3_stmt *pInsert = 0;
2105 char *zQuery = 0;
2106 char *zInsert = 0;
2107 int rc;
2108 int i, j, n;
2109 int nTable = (int)strlen(zTable);
2110 int k = 0;
drh4bbcf102014-02-06 02:46:08 +00002111 int cnt = 0;
2112 const int spinRate = 10000;
drh3350ce92014-02-06 00:49:12 +00002113
2114 zQuery = sqlite3_mprintf("SELECT * FROM \"%w\"", zTable);
2115 rc = sqlite3_prepare_v2(p->db, zQuery, -1, &pQuery, 0);
2116 if( rc ){
drh4bbcf102014-02-06 02:46:08 +00002117 fprintf(stderr, "Error %d: %s on [%s]\n",
drh3350ce92014-02-06 00:49:12 +00002118 sqlite3_extended_errcode(p->db), sqlite3_errmsg(p->db),
2119 zQuery);
2120 goto end_data_xfer;
2121 }
2122 n = sqlite3_column_count(pQuery);
2123 zInsert = sqlite3_malloc(200 + nTable + n*3);
2124 if( zInsert==0 ){
2125 fprintf(stderr, "out of memory\n");
2126 goto end_data_xfer;
2127 }
2128 sqlite3_snprintf(200+nTable,zInsert,
2129 "INSERT OR IGNORE INTO \"%s\" VALUES(?", zTable);
2130 i = (int)strlen(zInsert);
2131 for(j=1; j<n; j++){
2132 memcpy(zInsert+i, ",?", 2);
2133 i += 2;
2134 }
2135 memcpy(zInsert+i, ");", 3);
2136 rc = sqlite3_prepare_v2(newDb, zInsert, -1, &pInsert, 0);
2137 if( rc ){
drh4bbcf102014-02-06 02:46:08 +00002138 fprintf(stderr, "Error %d: %s on [%s]\n",
drh3350ce92014-02-06 00:49:12 +00002139 sqlite3_extended_errcode(newDb), sqlite3_errmsg(newDb),
2140 zQuery);
2141 goto end_data_xfer;
2142 }
2143 for(k=0; k<2; k++){
2144 while( (rc = sqlite3_step(pQuery))==SQLITE_ROW ){
2145 for(i=0; i<n; i++){
2146 switch( sqlite3_column_type(pQuery, i) ){
2147 case SQLITE_NULL: {
2148 sqlite3_bind_null(pInsert, i+1);
2149 break;
2150 }
2151 case SQLITE_INTEGER: {
2152 sqlite3_bind_int64(pInsert, i+1, sqlite3_column_int64(pQuery,i));
2153 break;
2154 }
2155 case SQLITE_FLOAT: {
2156 sqlite3_bind_double(pInsert, i+1, sqlite3_column_double(pQuery,i));
2157 break;
2158 }
2159 case SQLITE_TEXT: {
2160 sqlite3_bind_text(pInsert, i+1,
2161 (const char*)sqlite3_column_text(pQuery,i),
2162 -1, SQLITE_STATIC);
2163 break;
2164 }
2165 case SQLITE_BLOB: {
2166 sqlite3_bind_blob(pInsert, i+1, sqlite3_column_blob(pQuery,i),
2167 sqlite3_column_bytes(pQuery,i),
2168 SQLITE_STATIC);
2169 break;
2170 }
2171 }
2172 } /* End for */
drh4bbcf102014-02-06 02:46:08 +00002173 rc = sqlite3_step(pInsert);
2174 if( rc!=SQLITE_OK && rc!=SQLITE_ROW && rc!=SQLITE_DONE ){
2175 fprintf(stderr, "Error %d: %s\n", sqlite3_extended_errcode(newDb),
2176 sqlite3_errmsg(newDb));
2177 }
drh3350ce92014-02-06 00:49:12 +00002178 sqlite3_reset(pInsert);
drh4bbcf102014-02-06 02:46:08 +00002179 cnt++;
2180 if( (cnt%spinRate)==0 ){
2181 printf("%c\b", "|/-\\"[(cnt/spinRate)%4]);
2182 fflush(stdout);
2183 }
drh3350ce92014-02-06 00:49:12 +00002184 } /* End while */
2185 if( rc==SQLITE_DONE ) break;
2186 sqlite3_finalize(pQuery);
2187 sqlite3_free(zQuery);
2188 zQuery = sqlite3_mprintf("SELECT * FROM \"%w\" ORDER BY rowid DESC;",
2189 zTable);
2190 rc = sqlite3_prepare_v2(p->db, zQuery, -1, &pQuery, 0);
2191 if( rc ){
drh4bbcf102014-02-06 02:46:08 +00002192 fprintf(stderr, "Warning: cannot step \"%s\" backwards", zTable);
2193 break;
drh3350ce92014-02-06 00:49:12 +00002194 }
2195 } /* End for(k=0...) */
2196
2197end_data_xfer:
2198 sqlite3_finalize(pQuery);
2199 sqlite3_finalize(pInsert);
2200 sqlite3_free(zQuery);
2201 sqlite3_free(zInsert);
2202}
2203
2204
2205/*
2206** Try to transfer all rows of the schema that match zWhere. For
2207** each row, invoke xForEach() on the object defined by that row.
drh4bbcf102014-02-06 02:46:08 +00002208** If an error is encountered while moving forward through the
2209** sqlite_master table, try again moving backwards.
drh3350ce92014-02-06 00:49:12 +00002210*/
mistachkine31ae902014-02-06 01:15:29 +00002211static void tryToCloneSchema(
drh3350ce92014-02-06 00:49:12 +00002212 struct callback_data *p,
2213 sqlite3 *newDb,
2214 const char *zWhere,
2215 void (*xForEach)(struct callback_data*,sqlite3*,const char*)
2216){
2217 sqlite3_stmt *pQuery = 0;
2218 char *zQuery = 0;
2219 int rc;
2220 const unsigned char *zName;
2221 const unsigned char *zSql;
drh4bbcf102014-02-06 02:46:08 +00002222 char *zErrMsg = 0;
drh3350ce92014-02-06 00:49:12 +00002223
2224 zQuery = sqlite3_mprintf("SELECT name, sql FROM sqlite_master"
2225 " WHERE %s", zWhere);
2226 rc = sqlite3_prepare_v2(p->db, zQuery, -1, &pQuery, 0);
2227 if( rc ){
2228 fprintf(stderr, "Error: (%d) %s on [%s]\n",
2229 sqlite3_extended_errcode(p->db), sqlite3_errmsg(p->db),
2230 zQuery);
2231 goto end_schema_xfer;
2232 }
2233 while( (rc = sqlite3_step(pQuery))==SQLITE_ROW ){
2234 zName = sqlite3_column_text(pQuery, 0);
2235 zSql = sqlite3_column_text(pQuery, 1);
2236 printf("%s... ", zName); fflush(stdout);
drh4bbcf102014-02-06 02:46:08 +00002237 sqlite3_exec(newDb, (const char*)zSql, 0, 0, &zErrMsg);
2238 if( zErrMsg ){
2239 fprintf(stderr, "Error: %s\nSQL: [%s]\n", zErrMsg, zSql);
2240 sqlite3_free(zErrMsg);
2241 zErrMsg = 0;
2242 }
drh3350ce92014-02-06 00:49:12 +00002243 if( xForEach ){
2244 xForEach(p, newDb, (const char*)zName);
2245 }
2246 printf("done\n");
2247 }
2248 if( rc!=SQLITE_DONE ){
2249 sqlite3_finalize(pQuery);
2250 sqlite3_free(zQuery);
2251 zQuery = sqlite3_mprintf("SELECT name, sql FROM sqlite_master"
2252 " WHERE %s ORDER BY rowid DESC", zWhere);
2253 rc = sqlite3_prepare_v2(p->db, zQuery, -1, &pQuery, 0);
2254 if( rc ){
2255 fprintf(stderr, "Error: (%d) %s on [%s]\n",
2256 sqlite3_extended_errcode(p->db), sqlite3_errmsg(p->db),
2257 zQuery);
2258 goto end_schema_xfer;
2259 }
2260 while( (rc = sqlite3_step(pQuery))==SQLITE_ROW ){
2261 zName = sqlite3_column_text(pQuery, 0);
2262 zSql = sqlite3_column_text(pQuery, 1);
2263 printf("%s... ", zName); fflush(stdout);
drh4bbcf102014-02-06 02:46:08 +00002264 sqlite3_exec(newDb, (const char*)zSql, 0, 0, &zErrMsg);
2265 if( zErrMsg ){
2266 fprintf(stderr, "Error: %s\nSQL: [%s]\n", zErrMsg, zSql);
2267 sqlite3_free(zErrMsg);
2268 zErrMsg = 0;
2269 }
drh3350ce92014-02-06 00:49:12 +00002270 if( xForEach ){
2271 xForEach(p, newDb, (const char*)zName);
2272 }
2273 printf("done\n");
2274 }
2275 }
2276end_schema_xfer:
2277 sqlite3_finalize(pQuery);
2278 sqlite3_free(zQuery);
2279}
2280
2281/*
2282** Open a new database file named "zNewDb". Try to recover as much information
2283** as possible out of the main database (which might be corrupt) and write it
2284** into zNewDb.
2285*/
mistachkine31ae902014-02-06 01:15:29 +00002286static void tryToClone(struct callback_data *p, const char *zNewDb){
drh3350ce92014-02-06 00:49:12 +00002287 int rc;
2288 sqlite3 *newDb = 0;
2289 if( access(zNewDb,0)==0 ){
2290 fprintf(stderr, "File \"%s\" already exists.\n", zNewDb);
2291 return;
2292 }
2293 rc = sqlite3_open(zNewDb, &newDb);
2294 if( rc ){
2295 fprintf(stderr, "Cannot create output database: %s\n",
2296 sqlite3_errmsg(newDb));
2297 }else{
drh54d0d2d2014-04-03 00:32:13 +00002298 sqlite3_exec(p->db, "PRAGMA writable_schema=ON;", 0, 0, 0);
drh3350ce92014-02-06 00:49:12 +00002299 sqlite3_exec(newDb, "BEGIN EXCLUSIVE;", 0, 0, 0);
mistachkine31ae902014-02-06 01:15:29 +00002300 tryToCloneSchema(p, newDb, "type='table'", tryToCloneData);
2301 tryToCloneSchema(p, newDb, "type!='table'", 0);
drh3350ce92014-02-06 00:49:12 +00002302 sqlite3_exec(newDb, "COMMIT;", 0, 0, 0);
drh54d0d2d2014-04-03 00:32:13 +00002303 sqlite3_exec(p->db, "PRAGMA writable_schema=OFF;", 0, 0, 0);
drh3350ce92014-02-06 00:49:12 +00002304 }
2305 sqlite3_close(newDb);
2306}
2307
2308/*
drhc2ce0be2014-05-29 12:36:14 +00002309** Change the output file back to stdout
2310*/
2311static void output_reset(struct callback_data *p){
2312 if( p->outfile[0]=='|' ){
2313 pclose(p->out);
2314 }else{
2315 output_file_close(p->out);
2316 }
2317 p->outfile[0] = 0;
2318 p->out = stdout;
2319}
2320
2321/*
drh75897232000-05-29 14:26:00 +00002322** If an input line begins with "." then invoke this routine to
2323** process that line.
drh67505e72002-04-19 12:34:06 +00002324**
drh47ad6842006-11-08 12:25:42 +00002325** Return 1 on error, 2 to exit, and 0 otherwise.
drh75897232000-05-29 14:26:00 +00002326*/
drh44c2eb12003-04-30 11:38:26 +00002327static int do_meta_command(char *zLine, struct callback_data *p){
drh75897232000-05-29 14:26:00 +00002328 int i = 1;
2329 int nArg = 0;
2330 int n, c;
drh67505e72002-04-19 12:34:06 +00002331 int rc = 0;
drh75897232000-05-29 14:26:00 +00002332 char *azArg[50];
2333
2334 /* Parse the input line into tokens.
2335 */
2336 while( zLine[i] && nArg<ArraySize(azArg) ){
drhf0693c82011-10-11 20:41:54 +00002337 while( IsSpace(zLine[i]) ){ i++; }
drh06333682004-03-09 13:37:45 +00002338 if( zLine[i]==0 ) break;
drh75897232000-05-29 14:26:00 +00002339 if( zLine[i]=='\'' || zLine[i]=='"' ){
2340 int delim = zLine[i++];
2341 azArg[nArg++] = &zLine[i];
drh4c56b992013-06-27 13:26:55 +00002342 while( zLine[i] && zLine[i]!=delim ){
2343 if( zLine[i]=='\\' && delim=='"' && zLine[i+1]!=0 ) i++;
2344 i++;
2345 }
drh75897232000-05-29 14:26:00 +00002346 if( zLine[i]==delim ){
2347 zLine[i++] = 0;
2348 }
drhfeac5f82004-08-01 00:10:45 +00002349 if( delim=='"' ) resolve_backslashes(azArg[nArg-1]);
drh75897232000-05-29 14:26:00 +00002350 }else{
2351 azArg[nArg++] = &zLine[i];
drhf0693c82011-10-11 20:41:54 +00002352 while( zLine[i] && !IsSpace(zLine[i]) ){ i++; }
drh75897232000-05-29 14:26:00 +00002353 if( zLine[i] ) zLine[i++] = 0;
drhfeac5f82004-08-01 00:10:45 +00002354 resolve_backslashes(azArg[nArg-1]);
drh75897232000-05-29 14:26:00 +00002355 }
2356 }
2357
2358 /* Process the input line.
2359 */
shane9bd1b442009-10-23 01:27:39 +00002360 if( nArg==0 ) return 0; /* no tokens, no error */
drh4f21c4a2008-12-10 22:15:00 +00002361 n = strlen30(azArg[0]);
drh75897232000-05-29 14:26:00 +00002362 c = azArg[0][0];
drh5c7976f2014-02-10 19:59:27 +00002363 if( (c=='b' && n>=3 && strncmp(azArg[0], "backup", n)==0)
2364 || (c=='s' && n>=3 && strncmp(azArg[0], "save", n)==0)
2365 ){
drhbc46f022013-01-23 18:53:23 +00002366 const char *zDestFile = 0;
2367 const char *zDb = 0;
drh9ff849f2009-02-04 20:55:57 +00002368 sqlite3 *pDest;
2369 sqlite3_backup *pBackup;
drhbc46f022013-01-23 18:53:23 +00002370 int j;
2371 for(j=1; j<nArg; j++){
2372 const char *z = azArg[j];
2373 if( z[0]=='-' ){
2374 while( z[0]=='-' ) z++;
drhaf664332013-07-18 20:28:29 +00002375 /* No options to process at this time */
drhbc46f022013-01-23 18:53:23 +00002376 {
2377 fprintf(stderr, "unknown option: %s\n", azArg[j]);
2378 return 1;
2379 }
2380 }else if( zDestFile==0 ){
2381 zDestFile = azArg[j];
2382 }else if( zDb==0 ){
2383 zDb = zDestFile;
2384 zDestFile = azArg[j];
2385 }else{
2386 fprintf(stderr, "too many arguments to .backup\n");
2387 return 1;
2388 }
drh9ff849f2009-02-04 20:55:57 +00002389 }
drhbc46f022013-01-23 18:53:23 +00002390 if( zDestFile==0 ){
2391 fprintf(stderr, "missing FILENAME argument on .backup\n");
2392 return 1;
2393 }
2394 if( zDb==0 ) zDb = "main";
drh9ff849f2009-02-04 20:55:57 +00002395 rc = sqlite3_open(zDestFile, &pDest);
2396 if( rc!=SQLITE_OK ){
shane9bd1b442009-10-23 01:27:39 +00002397 fprintf(stderr, "Error: cannot open \"%s\"\n", zDestFile);
drh9ff849f2009-02-04 20:55:57 +00002398 sqlite3_close(pDest);
2399 return 1;
2400 }
drh05782482013-10-24 15:20:20 +00002401 open_db(p, 0);
drh9ff849f2009-02-04 20:55:57 +00002402 pBackup = sqlite3_backup_init(pDest, "main", p->db, zDb);
2403 if( pBackup==0 ){
2404 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(pDest));
2405 sqlite3_close(pDest);
2406 return 1;
2407 }
2408 while( (rc = sqlite3_backup_step(pBackup,100))==SQLITE_OK ){}
2409 sqlite3_backup_finish(pBackup);
2410 if( rc==SQLITE_DONE ){
shane9bd1b442009-10-23 01:27:39 +00002411 rc = 0;
drh9ff849f2009-02-04 20:55:57 +00002412 }else{
2413 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(pDest));
shane9bd1b442009-10-23 01:27:39 +00002414 rc = 1;
drh9ff849f2009-02-04 20:55:57 +00002415 }
2416 sqlite3_close(pDest);
2417 }else
2418
drhc2ce0be2014-05-29 12:36:14 +00002419 if( c=='b' && n>=3 && strncmp(azArg[0], "bail", n)==0 ){
2420 if( nArg==2 ){
2421 bail_on_error = booleanValue(azArg[1]);
2422 }else{
2423 fprintf(stderr, "Usage: .bail on|off\n");
2424 rc = 1;
2425 }
drhc49f44e2006-10-26 18:15:42 +00002426 }else
2427
drhd8621b92012-04-17 09:09:33 +00002428 /* The undocumented ".breakpoint" command causes a call to the no-op
2429 ** routine named test_breakpoint().
2430 */
2431 if( c=='b' && n>=3 && strncmp(azArg[0], "breakpoint", n)==0 ){
2432 test_breakpoint();
2433 }else
2434
drhc2ce0be2014-05-29 12:36:14 +00002435 if( c=='c' && strncmp(azArg[0], "clone", n)==0 ){
2436 if( nArg==2 ){
2437 tryToClone(p, azArg[1]);
2438 }else{
2439 fprintf(stderr, "Usage: .clone FILENAME\n");
2440 rc = 1;
2441 }
mistachkine31ae902014-02-06 01:15:29 +00002442 }else
2443
drhc2ce0be2014-05-29 12:36:14 +00002444 if( c=='d' && n>1 && strncmp(azArg[0], "databases", n)==0 ){
jplyon672a1ed2003-05-11 20:07:05 +00002445 struct callback_data data;
2446 char *zErrMsg = 0;
drh05782482013-10-24 15:20:20 +00002447 open_db(p, 0);
jplyon672a1ed2003-05-11 20:07:05 +00002448 memcpy(&data, p, sizeof(data));
drhd8885442004-03-17 23:42:12 +00002449 data.showHeader = 1;
jplyon672a1ed2003-05-11 20:07:05 +00002450 data.mode = MODE_Column;
drhd8885442004-03-17 23:42:12 +00002451 data.colWidth[0] = 3;
2452 data.colWidth[1] = 15;
2453 data.colWidth[2] = 58;
drh0b2110c2004-10-26 00:08:10 +00002454 data.cnt = 0;
danielk19776f8a5032004-05-10 10:34:51 +00002455 sqlite3_exec(p->db, "PRAGMA database_list; ", callback, &data, &zErrMsg);
jplyon672a1ed2003-05-11 20:07:05 +00002456 if( zErrMsg ){
2457 fprintf(stderr,"Error: %s\n", zErrMsg);
drh3f4fedb2004-05-31 19:34:33 +00002458 sqlite3_free(zErrMsg);
shane9bd1b442009-10-23 01:27:39 +00002459 rc = 1;
jplyon6a65bb32003-05-04 07:25:57 +00002460 }
2461 }else
2462
drhc2ce0be2014-05-29 12:36:14 +00002463 if( c=='d' && strncmp(azArg[0], "dump", n)==0 ){
drh05782482013-10-24 15:20:20 +00002464 open_db(p, 0);
drhf1dfc4f2009-09-23 15:51:35 +00002465 /* When playing back a "dump", the content might appear in an order
2466 ** which causes immediate foreign key constraints to be violated.
2467 ** So disable foreign-key constraint enforcement to prevent problems. */
drhc2ce0be2014-05-29 12:36:14 +00002468 if( nArg!=1 && nArg!=2 ){
2469 fprintf(stderr, "Usage: .dump ?LIKE-PATTERN?\n");
2470 rc = 1;
2471 goto meta_command_exit;
2472 }
drhf1dfc4f2009-09-23 15:51:35 +00002473 fprintf(p->out, "PRAGMA foreign_keys=OFF;\n");
drh33048c02001-10-01 14:29:22 +00002474 fprintf(p->out, "BEGIN TRANSACTION;\n");
drh45e29d82006-11-20 16:21:10 +00002475 p->writableSchema = 0;
drh56197952011-10-13 16:30:13 +00002476 sqlite3_exec(p->db, "SAVEPOINT dump; PRAGMA writable_schema=ON", 0, 0, 0);
drh2f464a02011-10-13 00:41:49 +00002477 p->nErr = 0;
drh4c653a02000-06-07 01:27:47 +00002478 if( nArg==1 ){
drhdd3d4592004-08-30 01:54:05 +00002479 run_schema_dump_query(p,
drha18c5682000-10-08 22:20:57 +00002480 "SELECT name, type, sql FROM sqlite_master "
drh2f464a02011-10-13 00:41:49 +00002481 "WHERE sql NOT NULL AND type=='table' AND name!='sqlite_sequence'"
drh4f324762009-05-21 14:51:03 +00002482 );
2483 run_schema_dump_query(p,
2484 "SELECT name, type, sql FROM sqlite_master "
drh2f464a02011-10-13 00:41:49 +00002485 "WHERE name=='sqlite_sequence'"
drh0b9a5942006-09-13 20:22:02 +00002486 );
drh2f464a02011-10-13 00:41:49 +00002487 run_table_dump_query(p,
drh0b9a5942006-09-13 20:22:02 +00002488 "SELECT sql FROM sqlite_master "
drh157e29a2009-05-21 15:15:00 +00002489 "WHERE sql NOT NULL AND type IN ('index','trigger','view')", 0
drha18c5682000-10-08 22:20:57 +00002490 );
drh4c653a02000-06-07 01:27:47 +00002491 }else{
2492 int i;
drhdd3d4592004-08-30 01:54:05 +00002493 for(i=1; i<nArg; i++){
danielk1977bc6ada42004-06-30 08:20:16 +00002494 zShellStatic = azArg[i];
drhdd3d4592004-08-30 01:54:05 +00002495 run_schema_dump_query(p,
drha18c5682000-10-08 22:20:57 +00002496 "SELECT name, type, sql FROM sqlite_master "
drhdd3d4592004-08-30 01:54:05 +00002497 "WHERE tbl_name LIKE shellstatic() AND type=='table'"
drh2f464a02011-10-13 00:41:49 +00002498 " AND sql NOT NULL");
2499 run_table_dump_query(p,
drh0b9a5942006-09-13 20:22:02 +00002500 "SELECT sql FROM sqlite_master "
drh45e29d82006-11-20 16:21:10 +00002501 "WHERE sql NOT NULL"
2502 " AND type IN ('index','trigger','view')"
drh157e29a2009-05-21 15:15:00 +00002503 " AND tbl_name LIKE shellstatic()", 0
drh0b9a5942006-09-13 20:22:02 +00002504 );
danielk1977bc6ada42004-06-30 08:20:16 +00002505 zShellStatic = 0;
drh4c653a02000-06-07 01:27:47 +00002506 }
2507 }
drh45e29d82006-11-20 16:21:10 +00002508 if( p->writableSchema ){
drh56197952011-10-13 16:30:13 +00002509 fprintf(p->out, "PRAGMA writable_schema=OFF;\n");
drh45e29d82006-11-20 16:21:10 +00002510 p->writableSchema = 0;
2511 }
drh56197952011-10-13 16:30:13 +00002512 sqlite3_exec(p->db, "PRAGMA writable_schema=OFF;", 0, 0, 0);
2513 sqlite3_exec(p->db, "RELEASE dump;", 0, 0, 0);
drh2f464a02011-10-13 00:41:49 +00002514 fprintf(p->out, p->nErr ? "ROLLBACK; -- due to errors\n" : "COMMIT;\n");
drh4c653a02000-06-07 01:27:47 +00002515 }else
drh75897232000-05-29 14:26:00 +00002516
drhc2ce0be2014-05-29 12:36:14 +00002517 if( c=='e' && strncmp(azArg[0], "echo", n)==0 ){
2518 if( nArg==2 ){
2519 p->echoOn = booleanValue(azArg[1]);
2520 }else{
2521 fprintf(stderr, "Usage: .echo on|off\n");
2522 rc = 1;
2523 }
drhdaffd0e2001-04-11 14:28:42 +00002524 }else
2525
drhc2ce0be2014-05-29 12:36:14 +00002526 if( c=='e' && strncmp(azArg[0], "eqp", n)==0 ){
2527 if( nArg==2 ){
2528 p->autoEQP = booleanValue(azArg[1]);
2529 }else{
2530 fprintf(stderr, "Usage: .eqp on|off\n");
2531 rc = 1;
2532 }
drhefbf3b12014-02-28 20:47:24 +00002533 }else
2534
drhd3ac7d92013-01-25 18:33:43 +00002535 if( c=='e' && strncmp(azArg[0], "exit", n)==0 ){
drh348d19c2013-06-03 12:47:43 +00002536 if( nArg>1 && (rc = (int)integerValue(azArg[1]))!=0 ) exit(rc);
drh47ad6842006-11-08 12:25:42 +00002537 rc = 2;
drh75897232000-05-29 14:26:00 +00002538 }else
2539
drhc2ce0be2014-05-29 12:36:14 +00002540 if( c=='e' && strncmp(azArg[0], "explain", n)==0 ){
drhc28490c2006-10-26 14:25:58 +00002541 int val = nArg>=2 ? booleanValue(azArg[1]) : 1;
persicom7e2dfdd2002-04-18 02:46:52 +00002542 if(val == 1) {
2543 if(!p->explainPrev.valid) {
2544 p->explainPrev.valid = 1;
2545 p->explainPrev.mode = p->mode;
2546 p->explainPrev.showHeader = p->showHeader;
2547 memcpy(p->explainPrev.colWidth,p->colWidth,sizeof(p->colWidth));
2548 }
2549 /* We could put this code under the !p->explainValid
2550 ** condition so that it does not execute if we are already in
2551 ** explain mode. However, always executing it allows us an easy
2552 ** was to reset to explain mode in case the user previously
2553 ** did an .explain followed by a .width, .mode or .header
2554 ** command.
2555 */
danielk19770d78bae2008-01-03 07:09:48 +00002556 p->mode = MODE_Explain;
persicom7e2dfdd2002-04-18 02:46:52 +00002557 p->showHeader = 1;
drhac68ced2013-11-27 13:24:18 +00002558 memset(p->colWidth,0,sizeof(p->colWidth));
danielk19770d78bae2008-01-03 07:09:48 +00002559 p->colWidth[0] = 4; /* addr */
drh60a713c2008-01-21 16:22:45 +00002560 p->colWidth[1] = 13; /* opcode */
2561 p->colWidth[2] = 4; /* P1 */
2562 p->colWidth[3] = 4; /* P2 */
2563 p->colWidth[4] = 4; /* P3 */
2564 p->colWidth[5] = 13; /* P4 */
danielk19770d78bae2008-01-03 07:09:48 +00002565 p->colWidth[6] = 2; /* P5 */
drh60a713c2008-01-21 16:22:45 +00002566 p->colWidth[7] = 13; /* Comment */
persicom7e2dfdd2002-04-18 02:46:52 +00002567 }else if (p->explainPrev.valid) {
2568 p->explainPrev.valid = 0;
2569 p->mode = p->explainPrev.mode;
2570 p->showHeader = p->explainPrev.showHeader;
2571 memcpy(p->colWidth,p->explainPrev.colWidth,sizeof(p->colWidth));
2572 }
drh75897232000-05-29 14:26:00 +00002573 }else
2574
drhc1971542014-06-23 23:28:13 +00002575 if( c=='f' && strncmp(azArg[0], "fullschema", n)==0 ){
2576 struct callback_data data;
2577 char *zErrMsg = 0;
drh56f674c2014-07-18 14:43:29 +00002578 int doStats = 0;
drhc1971542014-06-23 23:28:13 +00002579 if( nArg!=1 ){
2580 fprintf(stderr, "Usage: .fullschema\n");
2581 rc = 1;
2582 goto meta_command_exit;
2583 }
2584 open_db(p, 0);
2585 memcpy(&data, p, sizeof(data));
2586 data.showHeader = 0;
2587 data.mode = MODE_Semi;
2588 rc = sqlite3_exec(p->db,
2589 "SELECT sql FROM"
2590 " (SELECT sql sql, type type, tbl_name tbl_name, name name, rowid x"
2591 " FROM sqlite_master UNION ALL"
2592 " SELECT sql, type, tbl_name, name, rowid FROM sqlite_temp_master) "
2593 "WHERE type!='meta' AND sql NOTNULL AND name NOT LIKE 'sqlite_%'"
2594 "ORDER BY rowid",
2595 callback, &data, &zErrMsg
2596 );
drh56f674c2014-07-18 14:43:29 +00002597 if( rc==SQLITE_OK ){
2598 sqlite3_stmt *pStmt;
2599 rc = sqlite3_prepare_v2(p->db,
2600 "SELECT rowid FROM sqlite_master"
2601 " WHERE name GLOB 'sqlite_stat[134]'",
2602 -1, &pStmt, 0);
2603 doStats = sqlite3_step(pStmt)==SQLITE_ROW;
2604 sqlite3_finalize(pStmt);
2605 }
2606 if( doStats==0 ){
2607 fprintf(p->out, "/* No STAT tables available */\n");
2608 }else{
2609 fprintf(p->out, "ANALYZE sqlite_master;\n");
2610 sqlite3_exec(p->db, "SELECT 'ANALYZE sqlite_master'",
2611 callback, &data, &zErrMsg);
2612 data.mode = MODE_Insert;
2613 data.zDestTable = "sqlite_stat1";
2614 shell_exec(p->db, "SELECT * FROM sqlite_stat1",
2615 shell_callback, &data,&zErrMsg);
2616 data.zDestTable = "sqlite_stat3";
2617 shell_exec(p->db, "SELECT * FROM sqlite_stat3",
2618 shell_callback, &data,&zErrMsg);
2619 data.zDestTable = "sqlite_stat4";
2620 shell_exec(p->db, "SELECT * FROM sqlite_stat4",
2621 shell_callback, &data, &zErrMsg);
2622 fprintf(p->out, "ANALYZE sqlite_master;\n");
2623 }
drhc1971542014-06-23 23:28:13 +00002624 }else
2625
drhc2ce0be2014-05-29 12:36:14 +00002626 if( c=='h' && strncmp(azArg[0], "headers", n)==0 ){
2627 if( nArg==2 ){
2628 p->showHeader = booleanValue(azArg[1]);
2629 }else{
2630 fprintf(stderr, "Usage: .headers on|off\n");
2631 rc = 1;
shaneb320ccd2009-10-21 03:42:58 +00002632 }
drh75897232000-05-29 14:26:00 +00002633 }else
2634
drhc2ce0be2014-05-29 12:36:14 +00002635 if( c=='h' && strncmp(azArg[0], "help", n)==0 ){
2636 fprintf(p->out, "%s", zHelp);
2637 }else
2638
2639 if( c=='i' && strncmp(azArg[0], "import", n)==0 ){
drh01f37542014-05-31 15:43:33 +00002640 char *zTable; /* Insert data into this table */
2641 char *zFile; /* Name of file to extra content from */
shane916f9612009-10-23 00:37:15 +00002642 sqlite3_stmt *pStmt = NULL; /* A statement */
drhfeac5f82004-08-01 00:10:45 +00002643 int nCol; /* Number of columns in the table */
2644 int nByte; /* Number of bytes in an SQL string */
2645 int i, j; /* Loop counters */
drh2d463112013-08-06 14:36:36 +00002646 int needCommit; /* True to COMMIT or ROLLBACK at end */
mistachkin636bf9f2014-07-19 20:15:16 +00002647 int nSep; /* Number of bytes in p->colSeparator[] */
drhfeac5f82004-08-01 00:10:45 +00002648 char *zSql; /* An SQL statement */
mistachkin636bf9f2014-07-19 20:15:16 +00002649 ImportCtx sCtx; /* Reader context */
mistachkin486fd432014-07-24 22:20:23 +00002650 char *(*xRead)(ImportCtx*); /* Procedure to read one value */
drh5bde8162013-06-27 14:07:53 +00002651 int (*xCloser)(FILE*); /* Procedure to close th3 connection */
drhfeac5f82004-08-01 00:10:45 +00002652
drhc2ce0be2014-05-29 12:36:14 +00002653 if( nArg!=3 ){
2654 fprintf(stderr, "Usage: .import FILE TABLE\n");
2655 goto meta_command_exit;
2656 }
drh01f37542014-05-31 15:43:33 +00002657 zFile = azArg[1];
2658 zTable = azArg[2];
drhdb95f682013-06-26 22:46:00 +00002659 seenInterrupt = 0;
mistachkin636bf9f2014-07-19 20:15:16 +00002660 memset(&sCtx, 0, sizeof(sCtx));
drh05782482013-10-24 15:20:20 +00002661 open_db(p, 0);
mistachkin636bf9f2014-07-19 20:15:16 +00002662 nSep = strlen30(p->colSeparator);
drhfeac5f82004-08-01 00:10:45 +00002663 if( nSep==0 ){
mistachkin636bf9f2014-07-19 20:15:16 +00002664 fprintf(stderr, "Error: non-null column separator required for import\n");
shane916f9612009-10-23 00:37:15 +00002665 return 1;
drhfeac5f82004-08-01 00:10:45 +00002666 }
drhdb95f682013-06-26 22:46:00 +00002667 if( nSep>1 ){
mistachkin636bf9f2014-07-19 20:15:16 +00002668 fprintf(stderr, "Error: multi-character column separators not allowed"
drhdb95f682013-06-26 22:46:00 +00002669 " for import\n");
2670 return 1;
2671 }
mistachkin636bf9f2014-07-19 20:15:16 +00002672 nSep = strlen30(p->rowSeparator);
2673 if( nSep==0 ){
2674 fprintf(stderr, "Error: non-null row separator required for import\n");
2675 return 1;
2676 }
2677 if( nSep>1 ){
2678 fprintf(stderr, "Error: multi-character row separators not allowed"
2679 " for import\n");
2680 return 1;
2681 }
2682 sCtx.zFile = zFile;
2683 sCtx.nLine = 1;
2684 if( sCtx.zFile[0]=='|' ){
2685 sCtx.in = popen(sCtx.zFile+1, "r");
2686 sCtx.zFile = "<pipe>";
drh5bde8162013-06-27 14:07:53 +00002687 xCloser = pclose;
2688 }else{
mistachkin636bf9f2014-07-19 20:15:16 +00002689 sCtx.in = fopen(sCtx.zFile, "rb");
drh5bde8162013-06-27 14:07:53 +00002690 xCloser = fclose;
2691 }
mistachkin636bf9f2014-07-19 20:15:16 +00002692 if( p->mode==MODE_Ascii ){
2693 xRead = ascii_read_one_field;
2694 }else{
2695 xRead = csv_read_one_field;
2696 }
2697 if( sCtx.in==0 ){
drh5bde8162013-06-27 14:07:53 +00002698 fprintf(stderr, "Error: cannot open \"%s\"\n", zFile);
drhdb95f682013-06-26 22:46:00 +00002699 return 1;
2700 }
mistachkin636bf9f2014-07-19 20:15:16 +00002701 sCtx.cColSep = p->colSeparator[0];
2702 sCtx.cRowSep = p->rowSeparator[0];
drh7b075e32011-09-28 01:10:00 +00002703 zSql = sqlite3_mprintf("SELECT * FROM %s", zTable);
shane916f9612009-10-23 00:37:15 +00002704 if( zSql==0 ){
2705 fprintf(stderr, "Error: out of memory\n");
mistachkin636bf9f2014-07-19 20:15:16 +00002706 xCloser(sCtx.in);
shane916f9612009-10-23 00:37:15 +00002707 return 1;
2708 }
drh4f21c4a2008-12-10 22:15:00 +00002709 nByte = strlen30(zSql);
drhc7181902014-02-27 15:04:13 +00002710 rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
mistachkin636bf9f2014-07-19 20:15:16 +00002711 import_append_char(&sCtx, 0); /* To ensure sCtx.z is allocated */
drhdb95f682013-06-26 22:46:00 +00002712 if( rc && sqlite3_strglob("no such table: *", sqlite3_errmsg(db))==0 ){
2713 char *zCreate = sqlite3_mprintf("CREATE TABLE %s", zTable);
2714 char cSep = '(';
mistachkin636bf9f2014-07-19 20:15:16 +00002715 while( xRead(&sCtx) ){
2716 zCreate = sqlite3_mprintf("%z%c\n \"%s\" TEXT", zCreate, cSep, sCtx.z);
drhdb95f682013-06-26 22:46:00 +00002717 cSep = ',';
mistachkin636bf9f2014-07-19 20:15:16 +00002718 if( sCtx.cTerm!=sCtx.cColSep ) break;
drhdb95f682013-06-26 22:46:00 +00002719 }
drh5bde8162013-06-27 14:07:53 +00002720 if( cSep=='(' ){
2721 sqlite3_free(zCreate);
mistachkin636bf9f2014-07-19 20:15:16 +00002722 sqlite3_free(sCtx.z);
2723 xCloser(sCtx.in);
2724 fprintf(stderr,"%s: empty file\n", sCtx.zFile);
drh5bde8162013-06-27 14:07:53 +00002725 return 1;
2726 }
drhdb95f682013-06-26 22:46:00 +00002727 zCreate = sqlite3_mprintf("%z\n)", zCreate);
2728 rc = sqlite3_exec(p->db, zCreate, 0, 0, 0);
2729 sqlite3_free(zCreate);
2730 if( rc ){
2731 fprintf(stderr, "CREATE TABLE %s(...) failed: %s\n", zTable,
2732 sqlite3_errmsg(db));
mistachkin636bf9f2014-07-19 20:15:16 +00002733 sqlite3_free(sCtx.z);
2734 xCloser(sCtx.in);
drhdb95f682013-06-26 22:46:00 +00002735 return 1;
2736 }
drhc7181902014-02-27 15:04:13 +00002737 rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
drhdb95f682013-06-26 22:46:00 +00002738 }
drhfeac5f82004-08-01 00:10:45 +00002739 sqlite3_free(zSql);
2740 if( rc ){
shane916f9612009-10-23 00:37:15 +00002741 if (pStmt) sqlite3_finalize(pStmt);
drhfeac5f82004-08-01 00:10:45 +00002742 fprintf(stderr,"Error: %s\n", sqlite3_errmsg(db));
mistachkin636bf9f2014-07-19 20:15:16 +00002743 xCloser(sCtx.in);
shane916f9612009-10-23 00:37:15 +00002744 return 1;
drhfeac5f82004-08-01 00:10:45 +00002745 }
shane916f9612009-10-23 00:37:15 +00002746 nCol = sqlite3_column_count(pStmt);
drhfeac5f82004-08-01 00:10:45 +00002747 sqlite3_finalize(pStmt);
shane916f9612009-10-23 00:37:15 +00002748 pStmt = 0;
shane9bd1b442009-10-23 01:27:39 +00002749 if( nCol==0 ) return 0; /* no columns, no error */
drhdb95f682013-06-26 22:46:00 +00002750 zSql = sqlite3_malloc( nByte*2 + 20 + nCol*2 );
shane916f9612009-10-23 00:37:15 +00002751 if( zSql==0 ){
2752 fprintf(stderr, "Error: out of memory\n");
mistachkin636bf9f2014-07-19 20:15:16 +00002753 xCloser(sCtx.in);
shane916f9612009-10-23 00:37:15 +00002754 return 1;
2755 }
drhdb95f682013-06-26 22:46:00 +00002756 sqlite3_snprintf(nByte+20, zSql, "INSERT INTO \"%w\" VALUES(?", zTable);
drh4f21c4a2008-12-10 22:15:00 +00002757 j = strlen30(zSql);
drhfeac5f82004-08-01 00:10:45 +00002758 for(i=1; i<nCol; i++){
2759 zSql[j++] = ',';
2760 zSql[j++] = '?';
2761 }
2762 zSql[j++] = ')';
2763 zSql[j] = 0;
drhc7181902014-02-27 15:04:13 +00002764 rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
drhdb95f682013-06-26 22:46:00 +00002765 sqlite3_free(zSql);
drhfeac5f82004-08-01 00:10:45 +00002766 if( rc ){
2767 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(db));
shane916f9612009-10-23 00:37:15 +00002768 if (pStmt) sqlite3_finalize(pStmt);
mistachkin636bf9f2014-07-19 20:15:16 +00002769 xCloser(sCtx.in);
drh47ad6842006-11-08 12:25:42 +00002770 return 1;
drhfeac5f82004-08-01 00:10:45 +00002771 }
drh2d463112013-08-06 14:36:36 +00002772 needCommit = sqlite3_get_autocommit(db);
2773 if( needCommit ) sqlite3_exec(db, "BEGIN", 0, 0, 0);
drhdb95f682013-06-26 22:46:00 +00002774 do{
mistachkin636bf9f2014-07-19 20:15:16 +00002775 int startLine = sCtx.nLine;
drhfeac5f82004-08-01 00:10:45 +00002776 for(i=0; i<nCol; i++){
mistachkin636bf9f2014-07-19 20:15:16 +00002777 char *z = xRead(&sCtx);
2778 /*
2779 ** Did we reach end-of-file before finding any columns?
2780 ** If so, stop instead of NULL filling the remaining columns.
2781 */
drhdb95f682013-06-26 22:46:00 +00002782 if( z==0 && i==0 ) break;
mistachkin636bf9f2014-07-19 20:15:16 +00002783 /*
2784 ** Did we reach end-of-file OR end-of-line before finding any
2785 ** columns in ASCII mode? If so, stop instead of NULL filling
2786 ** the remaining columns.
2787 */
2788 if( p->mode==MODE_Ascii && (z==0 || z[0]==0) && i==0 ) break;
drhdb95f682013-06-26 22:46:00 +00002789 sqlite3_bind_text(pStmt, i+1, z, -1, SQLITE_TRANSIENT);
mistachkin636bf9f2014-07-19 20:15:16 +00002790 if( i<nCol-1 && sCtx.cTerm!=sCtx.cColSep ){
drhdb95f682013-06-26 22:46:00 +00002791 fprintf(stderr, "%s:%d: expected %d columns but found %d - "
2792 "filling the rest with NULL\n",
mistachkin636bf9f2014-07-19 20:15:16 +00002793 sCtx.zFile, startLine, nCol, i+1);
drhdb95f682013-06-26 22:46:00 +00002794 i++;
mistachkin6fe03382014-06-16 22:45:28 +00002795 while( i<=nCol ){ sqlite3_bind_null(pStmt, i); i++; }
drh18f52e02012-01-16 16:56:31 +00002796 }
drhfeac5f82004-08-01 00:10:45 +00002797 }
mistachkin636bf9f2014-07-19 20:15:16 +00002798 if( sCtx.cTerm==sCtx.cColSep ){
drhdb95f682013-06-26 22:46:00 +00002799 do{
mistachkin636bf9f2014-07-19 20:15:16 +00002800 xRead(&sCtx);
drhdb95f682013-06-26 22:46:00 +00002801 i++;
mistachkin636bf9f2014-07-19 20:15:16 +00002802 }while( sCtx.cTerm==sCtx.cColSep );
drhdb95f682013-06-26 22:46:00 +00002803 fprintf(stderr, "%s:%d: expected %d columns but found %d - "
2804 "extras ignored\n",
mistachkin636bf9f2014-07-19 20:15:16 +00002805 sCtx.zFile, startLine, nCol, i);
drhfeac5f82004-08-01 00:10:45 +00002806 }
drhdb95f682013-06-26 22:46:00 +00002807 if( i>=nCol ){
2808 sqlite3_step(pStmt);
2809 rc = sqlite3_reset(pStmt);
2810 if( rc!=SQLITE_OK ){
mistachkin636bf9f2014-07-19 20:15:16 +00002811 fprintf(stderr, "%s:%d: INSERT failed: %s\n", sCtx.zFile, startLine,
drhdb95f682013-06-26 22:46:00 +00002812 sqlite3_errmsg(db));
2813 }
2814 }
mistachkin636bf9f2014-07-19 20:15:16 +00002815 }while( sCtx.cTerm!=EOF );
drhdb95f682013-06-26 22:46:00 +00002816
mistachkin636bf9f2014-07-19 20:15:16 +00002817 xCloser(sCtx.in);
2818 sqlite3_free(sCtx.z);
drhfeac5f82004-08-01 00:10:45 +00002819 sqlite3_finalize(pStmt);
drh2d463112013-08-06 14:36:36 +00002820 if( needCommit ) sqlite3_exec(db, "COMMIT", 0, 0, 0);
drhfeac5f82004-08-01 00:10:45 +00002821 }else
2822
drhc2ce0be2014-05-29 12:36:14 +00002823 if( c=='i' && strncmp(azArg[0], "indices", n)==0 ){
drh75897232000-05-29 14:26:00 +00002824 struct callback_data data;
2825 char *zErrMsg = 0;
drh05782482013-10-24 15:20:20 +00002826 open_db(p, 0);
drh75897232000-05-29 14:26:00 +00002827 memcpy(&data, p, sizeof(data));
2828 data.showHeader = 0;
2829 data.mode = MODE_List;
shane86f5bdb2009-10-24 02:00:07 +00002830 if( nArg==1 ){
2831 rc = sqlite3_exec(p->db,
2832 "SELECT name FROM sqlite_master "
2833 "WHERE type='index' AND name NOT LIKE 'sqlite_%' "
2834 "UNION ALL "
2835 "SELECT name FROM sqlite_temp_master "
2836 "WHERE type='index' "
2837 "ORDER BY 1",
2838 callback, &data, &zErrMsg
2839 );
drhc2ce0be2014-05-29 12:36:14 +00002840 }else if( nArg==2 ){
shane86f5bdb2009-10-24 02:00:07 +00002841 zShellStatic = azArg[1];
2842 rc = sqlite3_exec(p->db,
2843 "SELECT name FROM sqlite_master "
2844 "WHERE type='index' AND tbl_name LIKE shellstatic() "
2845 "UNION ALL "
2846 "SELECT name FROM sqlite_temp_master "
2847 "WHERE type='index' AND tbl_name LIKE shellstatic() "
2848 "ORDER BY 1",
2849 callback, &data, &zErrMsg
2850 );
2851 zShellStatic = 0;
drhc2ce0be2014-05-29 12:36:14 +00002852 }else{
2853 fprintf(stderr, "Usage: .indices ?LIKE-PATTERN?\n");
2854 rc = 1;
2855 goto meta_command_exit;
shane86f5bdb2009-10-24 02:00:07 +00002856 }
drh75897232000-05-29 14:26:00 +00002857 if( zErrMsg ){
2858 fprintf(stderr,"Error: %s\n", zErrMsg);
drh3f4fedb2004-05-31 19:34:33 +00002859 sqlite3_free(zErrMsg);
shane9bd1b442009-10-23 01:27:39 +00002860 rc = 1;
shane86f5bdb2009-10-24 02:00:07 +00002861 }else if( rc != SQLITE_OK ){
2862 fprintf(stderr,"Error: querying sqlite_master and sqlite_temp_master\n");
2863 rc = 1;
drh75897232000-05-29 14:26:00 +00002864 }
2865 }else
2866
drhae5e4452007-05-03 17:18:36 +00002867#ifdef SQLITE_ENABLE_IOTRACE
drhb0603412007-02-28 04:47:26 +00002868 if( c=='i' && strncmp(azArg[0], "iotrace", n)==0 ){
mlcreech3a00f902008-03-04 17:45:01 +00002869 extern void (*sqlite3IoTrace)(const char*, ...);
drhb0603412007-02-28 04:47:26 +00002870 if( iotrace && iotrace!=stdout ) fclose(iotrace);
2871 iotrace = 0;
2872 if( nArg<2 ){
mlcreech3a00f902008-03-04 17:45:01 +00002873 sqlite3IoTrace = 0;
drhb0603412007-02-28 04:47:26 +00002874 }else if( strcmp(azArg[1], "-")==0 ){
mlcreech3a00f902008-03-04 17:45:01 +00002875 sqlite3IoTrace = iotracePrintf;
drhb0603412007-02-28 04:47:26 +00002876 iotrace = stdout;
2877 }else{
2878 iotrace = fopen(azArg[1], "w");
2879 if( iotrace==0 ){
shane9bd1b442009-10-23 01:27:39 +00002880 fprintf(stderr, "Error: cannot open \"%s\"\n", azArg[1]);
mlcreech3a00f902008-03-04 17:45:01 +00002881 sqlite3IoTrace = 0;
shane9bd1b442009-10-23 01:27:39 +00002882 rc = 1;
drhb0603412007-02-28 04:47:26 +00002883 }else{
mlcreech3a00f902008-03-04 17:45:01 +00002884 sqlite3IoTrace = iotracePrintf;
drhb0603412007-02-28 04:47:26 +00002885 }
2886 }
2887 }else
drhae5e4452007-05-03 17:18:36 +00002888#endif
drhb0603412007-02-28 04:47:26 +00002889
drh70df4fe2006-06-13 15:12:21 +00002890#ifndef SQLITE_OMIT_LOAD_EXTENSION
drhc2ce0be2014-05-29 12:36:14 +00002891 if( c=='l' && strncmp(azArg[0], "load", n)==0 ){
drh1e397f82006-06-08 15:28:43 +00002892 const char *zFile, *zProc;
2893 char *zErrMsg = 0;
drhc2ce0be2014-05-29 12:36:14 +00002894 if( nArg<2 ){
2895 fprintf(stderr, "Usage: .load FILE ?ENTRYPOINT?\n");
2896 rc = 1;
2897 goto meta_command_exit;
2898 }
drh1e397f82006-06-08 15:28:43 +00002899 zFile = azArg[1];
2900 zProc = nArg>=3 ? azArg[2] : 0;
drh05782482013-10-24 15:20:20 +00002901 open_db(p, 0);
drh1e397f82006-06-08 15:28:43 +00002902 rc = sqlite3_load_extension(p->db, zFile, zProc, &zErrMsg);
2903 if( rc!=SQLITE_OK ){
shane9bd1b442009-10-23 01:27:39 +00002904 fprintf(stderr, "Error: %s\n", zErrMsg);
drh1e397f82006-06-08 15:28:43 +00002905 sqlite3_free(zErrMsg);
drh47ad6842006-11-08 12:25:42 +00002906 rc = 1;
drh1e397f82006-06-08 15:28:43 +00002907 }
2908 }else
drh70df4fe2006-06-13 15:12:21 +00002909#endif
drh1e397f82006-06-08 15:28:43 +00002910
drhc2ce0be2014-05-29 12:36:14 +00002911 if( c=='l' && strncmp(azArg[0], "log", n)==0 ){
2912 if( nArg!=2 ){
2913 fprintf(stderr, "Usage: .log FILENAME\n");
2914 rc = 1;
2915 }else{
2916 const char *zFile = azArg[1];
2917 output_file_close(p->pLog);
2918 p->pLog = output_file_open(zFile);
2919 }
drh127f9d72010-02-23 01:47:00 +00002920 }else
2921
drhc2ce0be2014-05-29 12:36:14 +00002922 if( c=='m' && strncmp(azArg[0], "mode", n)==0 ){
2923 const char *zMode = nArg>=2 ? azArg[1] : "";
2924 int n2 = (int)strlen(zMode);
2925 int c2 = zMode[0];
2926 if( c2=='l' && n2>2 && strncmp(azArg[1],"lines",n2)==0 ){
drh75897232000-05-29 14:26:00 +00002927 p->mode = MODE_Line;
drhc2ce0be2014-05-29 12:36:14 +00002928 }else if( c2=='c' && strncmp(azArg[1],"columns",n2)==0 ){
drh75897232000-05-29 14:26:00 +00002929 p->mode = MODE_Column;
drhc2ce0be2014-05-29 12:36:14 +00002930 }else if( c2=='l' && n2>2 && strncmp(azArg[1],"list",n2)==0 ){
drh75897232000-05-29 14:26:00 +00002931 p->mode = MODE_List;
drhc2ce0be2014-05-29 12:36:14 +00002932 }else if( c2=='h' && strncmp(azArg[1],"html",n2)==0 ){
drh1e5d0e92000-05-31 23:33:17 +00002933 p->mode = MODE_Html;
drhc2ce0be2014-05-29 12:36:14 +00002934 }else if( c2=='t' && strncmp(azArg[1],"tcl",n2)==0 ){
drhfeac5f82004-08-01 00:10:45 +00002935 p->mode = MODE_Tcl;
mistachkinfad42082014-07-24 22:13:12 +00002936 sqlite3_snprintf(sizeof(p->colSeparator), p->colSeparator, SEP_Space);
2937 sqlite3_snprintf(sizeof(p->rowSeparator), p->rowSeparator, SEP_Row);
drhc2ce0be2014-05-29 12:36:14 +00002938 }else if( c2=='c' && strncmp(azArg[1],"csv",n2)==0 ){
drh8e64d1c2004-10-07 00:32:39 +00002939 p->mode = MODE_Csv;
mistachkinfad42082014-07-24 22:13:12 +00002940 sqlite3_snprintf(sizeof(p->newline), p->newline, SEP_CrLf);
2941 sqlite3_snprintf(sizeof(p->colSeparator), p->colSeparator, SEP_Comma);
2942 sqlite3_snprintf(sizeof(p->rowSeparator), p->rowSeparator, SEP_Row);
drhc2ce0be2014-05-29 12:36:14 +00002943 }else if( c2=='t' && strncmp(azArg[1],"tabs",n2)==0 ){
drhfeac5f82004-08-01 00:10:45 +00002944 p->mode = MODE_List;
mistachkinfad42082014-07-24 22:13:12 +00002945 sqlite3_snprintf(sizeof(p->colSeparator), p->colSeparator, SEP_Tab);
2946 sqlite3_snprintf(sizeof(p->rowSeparator), p->rowSeparator, SEP_Row);
drhc2ce0be2014-05-29 12:36:14 +00002947 }else if( c2=='i' && strncmp(azArg[1],"insert",n2)==0 ){
drh28bd4bc2000-06-15 15:57:22 +00002948 p->mode = MODE_Insert;
drhc2ce0be2014-05-29 12:36:14 +00002949 set_table_name(p, nArg>=3 ? azArg[2] : "table");
mistachkin636bf9f2014-07-19 20:15:16 +00002950 }else if( c2=='a' && strncmp(azArg[1],"ascii",n2)==0 ){
2951 p->mode = MODE_Ascii;
mistachkinfad42082014-07-24 22:13:12 +00002952 sqlite3_snprintf(sizeof(p->colSeparator), p->colSeparator, SEP_Unit);
2953 sqlite3_snprintf(sizeof(p->rowSeparator), p->rowSeparator, SEP_Record);
drhdaffd0e2001-04-11 14:28:42 +00002954 }else {
shane9bd1b442009-10-23 01:27:39 +00002955 fprintf(stderr,"Error: mode should be one of: "
mistachkin636bf9f2014-07-19 20:15:16 +00002956 "ascii column csv html insert line list tabs tcl\n");
shane9bd1b442009-10-23 01:27:39 +00002957 rc = 1;
drh75897232000-05-29 14:26:00 +00002958 }
2959 }else
2960
drhc2ce0be2014-05-29 12:36:14 +00002961 if( c=='n' && strncmp(azArg[0], "nullvalue", n)==0 ){
2962 if( nArg==2 ){
2963 sqlite3_snprintf(sizeof(p->nullvalue), p->nullvalue,
2964 "%.*s", (int)ArraySize(p->nullvalue)-1, azArg[1]);
2965 }else{
2966 fprintf(stderr, "Usage: .nullvalue STRING\n");
shanehe2aa9d72009-11-06 17:20:17 +00002967 rc = 1;
2968 }
2969 }else
2970
drh05782482013-10-24 15:20:20 +00002971 if( c=='o' && strncmp(azArg[0], "open", n)==0 && n>=2 ){
2972 sqlite3 *savedDb = p->db;
2973 const char *zSavedFilename = p->zDbFilename;
2974 char *zNewFilename = 0;
2975 p->db = 0;
2976 if( nArg>=2 ){
2977 p->zDbFilename = zNewFilename = sqlite3_mprintf("%s", azArg[1]);
2978 }
2979 open_db(p, 1);
2980 if( p->db!=0 ){
2981 sqlite3_close(savedDb);
2982 sqlite3_free(p->zFreeOnClose);
2983 p->zFreeOnClose = zNewFilename;
2984 }else{
2985 sqlite3_free(zNewFilename);
2986 p->db = savedDb;
2987 p->zDbFilename = zSavedFilename;
2988 }
2989 }else
2990
drhc2ce0be2014-05-29 12:36:14 +00002991 if( c=='o'
2992 && (strncmp(azArg[0], "output", n)==0 || strncmp(azArg[0], "once", n)==0)
2993 ){
2994 const char *zFile = nArg>=2 ? azArg[1] : "stdout";
2995 if( nArg>2 ){
2996 fprintf(stderr, "Usage: .%s FILE\n", azArg[0]);
2997 rc = 1;
2998 goto meta_command_exit;
drh75897232000-05-29 14:26:00 +00002999 }
drhc2ce0be2014-05-29 12:36:14 +00003000 if( n>1 && strncmp(azArg[0], "once", n)==0 ){
3001 if( nArg<2 ){
3002 fprintf(stderr, "Usage: .once FILE\n");
3003 rc = 1;
3004 goto meta_command_exit;
3005 }
3006 p->outCount = 2;
3007 }else{
3008 p->outCount = 0;
3009 }
3010 output_reset(p);
3011 if( zFile[0]=='|' ){
3012 p->out = popen(zFile + 1, "w");
drhe1da8fa2012-03-30 00:05:57 +00003013 if( p->out==0 ){
drhc2ce0be2014-05-29 12:36:14 +00003014 fprintf(stderr,"Error: cannot open pipe \"%s\"\n", zFile + 1);
drhe1da8fa2012-03-30 00:05:57 +00003015 p->out = stdout;
3016 rc = 1;
3017 }else{
drhc2ce0be2014-05-29 12:36:14 +00003018 sqlite3_snprintf(sizeof(p->outfile), p->outfile, "%s", zFile);
drhe1da8fa2012-03-30 00:05:57 +00003019 }
drh75897232000-05-29 14:26:00 +00003020 }else{
drhc2ce0be2014-05-29 12:36:14 +00003021 p->out = output_file_open(zFile);
drh75897232000-05-29 14:26:00 +00003022 if( p->out==0 ){
drhc2ce0be2014-05-29 12:36:14 +00003023 if( strcmp(zFile,"off")!=0 ){
3024 fprintf(stderr,"Error: cannot write to \"%s\"\n", zFile);
drh42f64e52012-04-04 16:56:23 +00003025 }
drh75897232000-05-29 14:26:00 +00003026 p->out = stdout;
shane9bd1b442009-10-23 01:27:39 +00003027 rc = 1;
persicom7e2dfdd2002-04-18 02:46:52 +00003028 } else {
drhc2ce0be2014-05-29 12:36:14 +00003029 sqlite3_snprintf(sizeof(p->outfile), p->outfile, "%s", zFile);
drh75897232000-05-29 14:26:00 +00003030 }
3031 }
3032 }else
3033
drh078b1fd2012-09-21 13:40:02 +00003034 if( c=='p' && n>=3 && strncmp(azArg[0], "print", n)==0 ){
3035 int i;
3036 for(i=1; i<nArg; i++){
3037 if( i>1 ) fprintf(p->out, " ");
3038 fprintf(p->out, "%s", azArg[i]);
3039 }
3040 fprintf(p->out, "\n");
3041 }else
3042
drhc2ce0be2014-05-29 12:36:14 +00003043 if( c=='p' && strncmp(azArg[0], "prompt", n)==0 ){
persicom7e2dfdd2002-04-18 02:46:52 +00003044 if( nArg >= 2) {
3045 strncpy(mainPrompt,azArg[1],(int)ArraySize(mainPrompt)-1);
3046 }
3047 if( nArg >= 3) {
3048 strncpy(continuePrompt,azArg[2],(int)ArraySize(continuePrompt)-1);
3049 }
3050 }else
3051
drhc2ce0be2014-05-29 12:36:14 +00003052 if( c=='q' && strncmp(azArg[0], "quit", n)==0 ){
drh47ad6842006-11-08 12:25:42 +00003053 rc = 2;
persicom7e2dfdd2002-04-18 02:46:52 +00003054 }else
3055
drhc2ce0be2014-05-29 12:36:14 +00003056 if( c=='r' && n>=3 && strncmp(azArg[0], "read", n)==0 ){
3057 FILE *alt;
3058 if( nArg!=2 ){
3059 fprintf(stderr, "Usage: .read FILE\n");
3060 rc = 1;
3061 goto meta_command_exit;
3062 }
3063 alt = fopen(azArg[1], "rb");
drhdaffd0e2001-04-11 14:28:42 +00003064 if( alt==0 ){
shane9bd1b442009-10-23 01:27:39 +00003065 fprintf(stderr,"Error: cannot open \"%s\"\n", azArg[1]);
3066 rc = 1;
drhdaffd0e2001-04-11 14:28:42 +00003067 }else{
shane9bd1b442009-10-23 01:27:39 +00003068 rc = process_input(p, alt);
drhdaffd0e2001-04-11 14:28:42 +00003069 fclose(alt);
3070 }
3071 }else
3072
drhc2ce0be2014-05-29 12:36:14 +00003073 if( c=='r' && n>=3 && strncmp(azArg[0], "restore", n)==0 ){
drh9ff849f2009-02-04 20:55:57 +00003074 const char *zSrcFile;
3075 const char *zDb;
3076 sqlite3 *pSrc;
3077 sqlite3_backup *pBackup;
drhdc2c4912009-02-04 22:46:47 +00003078 int nTimeout = 0;
3079
drh9ff849f2009-02-04 20:55:57 +00003080 if( nArg==2 ){
3081 zSrcFile = azArg[1];
3082 zDb = "main";
drhc2ce0be2014-05-29 12:36:14 +00003083 }else if( nArg==3 ){
drh9ff849f2009-02-04 20:55:57 +00003084 zSrcFile = azArg[2];
3085 zDb = azArg[1];
drhc2ce0be2014-05-29 12:36:14 +00003086 }else{
3087 fprintf(stderr, "Usage: .restore ?DB? FILE\n");
3088 rc = 1;
3089 goto meta_command_exit;
drh9ff849f2009-02-04 20:55:57 +00003090 }
3091 rc = sqlite3_open(zSrcFile, &pSrc);
3092 if( rc!=SQLITE_OK ){
shane9bd1b442009-10-23 01:27:39 +00003093 fprintf(stderr, "Error: cannot open \"%s\"\n", zSrcFile);
drh9ff849f2009-02-04 20:55:57 +00003094 sqlite3_close(pSrc);
3095 return 1;
3096 }
drh05782482013-10-24 15:20:20 +00003097 open_db(p, 0);
drh9ff849f2009-02-04 20:55:57 +00003098 pBackup = sqlite3_backup_init(p->db, zDb, pSrc, "main");
3099 if( pBackup==0 ){
3100 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(p->db));
3101 sqlite3_close(pSrc);
3102 return 1;
3103 }
drhdc2c4912009-02-04 22:46:47 +00003104 while( (rc = sqlite3_backup_step(pBackup,100))==SQLITE_OK
3105 || rc==SQLITE_BUSY ){
3106 if( rc==SQLITE_BUSY ){
3107 if( nTimeout++ >= 3 ) break;
3108 sqlite3_sleep(100);
drh9ff849f2009-02-04 20:55:57 +00003109 }
3110 }
3111 sqlite3_backup_finish(pBackup);
3112 if( rc==SQLITE_DONE ){
shane9bd1b442009-10-23 01:27:39 +00003113 rc = 0;
drhdc2c4912009-02-04 22:46:47 +00003114 }else if( rc==SQLITE_BUSY || rc==SQLITE_LOCKED ){
shane9bd1b442009-10-23 01:27:39 +00003115 fprintf(stderr, "Error: source database is busy\n");
3116 rc = 1;
drh9ff849f2009-02-04 20:55:57 +00003117 }else{
3118 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(p->db));
shane9bd1b442009-10-23 01:27:39 +00003119 rc = 1;
drh9ff849f2009-02-04 20:55:57 +00003120 }
3121 sqlite3_close(pSrc);
3122 }else
3123
drhc2ce0be2014-05-29 12:36:14 +00003124 if( c=='s' && strncmp(azArg[0], "schema", n)==0 ){
drh75897232000-05-29 14:26:00 +00003125 struct callback_data data;
3126 char *zErrMsg = 0;
drh05782482013-10-24 15:20:20 +00003127 open_db(p, 0);
drh75897232000-05-29 14:26:00 +00003128 memcpy(&data, p, sizeof(data));
3129 data.showHeader = 0;
drhe3710332000-09-29 13:30:53 +00003130 data.mode = MODE_Semi;
drhc2ce0be2014-05-29 12:36:14 +00003131 if( nArg==2 ){
drhc8d74412004-08-31 23:41:26 +00003132 int i;
drhf0693c82011-10-11 20:41:54 +00003133 for(i=0; azArg[1][i]; i++) azArg[1][i] = ToLower(azArg[1][i]);
drhc8d74412004-08-31 23:41:26 +00003134 if( strcmp(azArg[1],"sqlite_master")==0 ){
drha18c5682000-10-08 22:20:57 +00003135 char *new_argv[2], *new_colv[2];
3136 new_argv[0] = "CREATE TABLE sqlite_master (\n"
3137 " type text,\n"
3138 " name text,\n"
3139 " tbl_name text,\n"
drhadbca9c2001-09-27 15:11:53 +00003140 " rootpage integer,\n"
drha18c5682000-10-08 22:20:57 +00003141 " sql text\n"
3142 ")";
3143 new_argv[1] = 0;
3144 new_colv[0] = "sql";
3145 new_colv[1] = 0;
3146 callback(&data, 1, new_argv, new_colv);
shane9bd1b442009-10-23 01:27:39 +00003147 rc = SQLITE_OK;
drhc8d74412004-08-31 23:41:26 +00003148 }else if( strcmp(azArg[1],"sqlite_temp_master")==0 ){
drhe0bc4042002-06-25 01:09:11 +00003149 char *new_argv[2], *new_colv[2];
3150 new_argv[0] = "CREATE TEMP TABLE sqlite_temp_master (\n"
3151 " type text,\n"
3152 " name text,\n"
3153 " tbl_name text,\n"
3154 " rootpage integer,\n"
3155 " sql text\n"
3156 ")";
3157 new_argv[1] = 0;
3158 new_colv[0] = "sql";
3159 new_colv[1] = 0;
3160 callback(&data, 1, new_argv, new_colv);
shane9bd1b442009-10-23 01:27:39 +00003161 rc = SQLITE_OK;
drha18c5682000-10-08 22:20:57 +00003162 }else{
danielk1977bc6ada42004-06-30 08:20:16 +00003163 zShellStatic = azArg[1];
shane9bd1b442009-10-23 01:27:39 +00003164 rc = sqlite3_exec(p->db,
drhe0bc4042002-06-25 01:09:11 +00003165 "SELECT sql FROM "
drhac43e982012-05-21 03:15:06 +00003166 " (SELECT sql sql, type type, tbl_name tbl_name, name name, rowid x"
drh8f800a72009-01-14 23:17:55 +00003167 " FROM sqlite_master UNION ALL"
drhac43e982012-05-21 03:15:06 +00003168 " SELECT sql, type, tbl_name, name, rowid FROM sqlite_temp_master) "
drh6ac7a582011-11-04 00:35:56 +00003169 "WHERE lower(tbl_name) LIKE shellstatic()"
3170 " AND type!='meta' AND sql NOTNULL "
drh1ba00292013-05-06 21:01:06 +00003171 "ORDER BY rowid",
danielk1977bc6ada42004-06-30 08:20:16 +00003172 callback, &data, &zErrMsg);
3173 zShellStatic = 0;
drha18c5682000-10-08 22:20:57 +00003174 }
drhc2ce0be2014-05-29 12:36:14 +00003175 }else if( nArg==1 ){
shane9bd1b442009-10-23 01:27:39 +00003176 rc = sqlite3_exec(p->db,
drhe0bc4042002-06-25 01:09:11 +00003177 "SELECT sql FROM "
drhac43e982012-05-21 03:15:06 +00003178 " (SELECT sql sql, type type, tbl_name tbl_name, name name, rowid x"
drh8f800a72009-01-14 23:17:55 +00003179 " FROM sqlite_master UNION ALL"
drhac43e982012-05-21 03:15:06 +00003180 " SELECT sql, type, tbl_name, name, rowid FROM sqlite_temp_master) "
drh0c356672005-09-10 22:40:53 +00003181 "WHERE type!='meta' AND sql NOTNULL AND name NOT LIKE 'sqlite_%'"
drh1ba00292013-05-06 21:01:06 +00003182 "ORDER BY rowid",
drha18c5682000-10-08 22:20:57 +00003183 callback, &data, &zErrMsg
3184 );
drhc2ce0be2014-05-29 12:36:14 +00003185 }else{
3186 fprintf(stderr, "Usage: .schema ?LIKE-PATTERN?\n");
3187 rc = 1;
3188 goto meta_command_exit;
drh75897232000-05-29 14:26:00 +00003189 }
drh75897232000-05-29 14:26:00 +00003190 if( zErrMsg ){
3191 fprintf(stderr,"Error: %s\n", zErrMsg);
drh3f4fedb2004-05-31 19:34:33 +00003192 sqlite3_free(zErrMsg);
shane9bd1b442009-10-23 01:27:39 +00003193 rc = 1;
3194 }else if( rc != SQLITE_OK ){
3195 fprintf(stderr,"Error: querying schema information\n");
3196 rc = 1;
3197 }else{
3198 rc = 0;
drh75897232000-05-29 14:26:00 +00003199 }
3200 }else
3201
drh340f5822013-06-27 13:01:21 +00003202#ifdef SQLITE_DEBUG
drh348d19c2013-06-03 12:47:43 +00003203 /* Undocumented commands for internal testing. Subject to change
3204 ** without notice. */
3205 if( c=='s' && n>=10 && strncmp(azArg[0], "selftest-", 9)==0 ){
3206 if( strncmp(azArg[0]+9, "boolean", n-9)==0 ){
3207 int i, v;
3208 for(i=1; i<nArg; i++){
3209 v = booleanValue(azArg[i]);
3210 fprintf(p->out, "%s: %d 0x%x\n", azArg[i], v, v);
3211 }
3212 }
3213 if( strncmp(azArg[0]+9, "integer", n-9)==0 ){
3214 int i; sqlite3_int64 v;
3215 for(i=1; i<nArg; i++){
drh340f5822013-06-27 13:01:21 +00003216 char zBuf[200];
drh348d19c2013-06-03 12:47:43 +00003217 v = integerValue(azArg[i]);
drhc2ce0be2014-05-29 12:36:14 +00003218 sqlite3_snprintf(sizeof(zBuf),zBuf,"%s: %lld 0x%llx\n", azArg[i],v,v);
drh340f5822013-06-27 13:01:21 +00003219 fprintf(p->out, "%s", zBuf);
drh348d19c2013-06-03 12:47:43 +00003220 }
3221 }
3222 }else
drh340f5822013-06-27 13:01:21 +00003223#endif
drh348d19c2013-06-03 12:47:43 +00003224
mistachkin636bf9f2014-07-19 20:15:16 +00003225 if( c=='r' && strncmp(azArg[0], "rowseparator", n)==0 ){
3226 if( nArg==2 ){
3227 sqlite3_snprintf(sizeof(p->rowSeparator), p->rowSeparator,
3228 "%.*s", (int)sizeof(p->rowSeparator)-1, azArg[1]);
3229 }else{
3230 fprintf(stderr, "Usage: .rowseparator STRING\n");
3231 rc = 1;
3232 }
3233 }else
3234
3235 if( c=='c' && strncmp(azArg[0], "colseparator", n)==0 ){
3236 if( nArg==2 ){
3237 sqlite3_snprintf(sizeof(p->colSeparator), p->colSeparator,
3238 "%.*s", (int)sizeof(p->colSeparator)-1, azArg[1]);
3239 }else{
3240 fprintf(stderr, "Usage: .colseparator STRING\n");
3241 rc = 1;
3242 }
3243 }else
3244
drhc2ce0be2014-05-29 12:36:14 +00003245 if( c=='s' && strncmp(azArg[0], "separator", n)==0 ){
drh6976c212014-07-24 12:09:47 +00003246 if( nArg<2 || nArg>3 ){
3247 fprintf(stderr, "Usage: .separator SEPARATOR ?NEWLINE?\n");
drhc2ce0be2014-05-29 12:36:14 +00003248 rc = 1;
3249 }
drh6976c212014-07-24 12:09:47 +00003250 if( nArg>=2 ){
mistachkin636bf9f2014-07-19 20:15:16 +00003251 sqlite3_snprintf(sizeof(p->colSeparator), p->colSeparator,
3252 "%.*s", (int)sizeof(p->colSeparator)-1, azArg[1]);
drh6976c212014-07-24 12:09:47 +00003253 }
3254 if( nArg>=3 ){
mistachkinfad42082014-07-24 22:13:12 +00003255 sqlite3_snprintf(sizeof(p->newline), p->newline,
3256 "%.*s", (int)sizeof(p->newline)-1, azArg[2]);
drh5bb3eb92007-05-04 13:15:55 +00003257 }
drh75897232000-05-29 14:26:00 +00003258 }else
3259
drh62cdde52014-05-28 20:22:28 +00003260 if( c=='s'
3261 && (strncmp(azArg[0], "shell", n)==0 || strncmp(azArg[0],"system",n)==0)
drh62cdde52014-05-28 20:22:28 +00003262 ){
3263 char *zCmd;
3264 int i;
drhc2ce0be2014-05-29 12:36:14 +00003265 if( nArg<2 ){
3266 fprintf(stderr, "Usage: .system COMMAND\n");
3267 rc = 1;
3268 goto meta_command_exit;
3269 }
drhdcb3e3d2014-05-29 03:17:29 +00003270 zCmd = sqlite3_mprintf(strchr(azArg[1],' ')==0?"%s":"\"%s\"", azArg[1]);
drh62cdde52014-05-28 20:22:28 +00003271 for(i=2; i<nArg; i++){
drhdcb3e3d2014-05-29 03:17:29 +00003272 zCmd = sqlite3_mprintf(strchr(azArg[i],' ')==0?"%z %s":"%z \"%s\"",
3273 zCmd, azArg[i]);
drh62cdde52014-05-28 20:22:28 +00003274 }
drh3c4461f2014-05-29 20:39:59 +00003275 (void)system(zCmd);
drh62cdde52014-05-28 20:22:28 +00003276 sqlite3_free(zCmd);
3277 }else
3278
drhc2ce0be2014-05-29 12:36:14 +00003279 if( c=='s' && strncmp(azArg[0], "show", n)==0 ){
persicom7e2dfdd2002-04-18 02:46:52 +00003280 int i;
drhc2ce0be2014-05-29 12:36:14 +00003281 if( nArg!=1 ){
3282 fprintf(stderr, "Usage: .show\n");
3283 rc = 1;
3284 goto meta_command_exit;
3285 }
mistachkin636bf9f2014-07-19 20:15:16 +00003286 fprintf(p->out,"%12.12s: %s\n","echo", p->echoOn ? "on" : "off");
3287 fprintf(p->out,"%12.12s: %s\n","eqp", p->autoEQP ? "on" : "off");
3288 fprintf(p->out,"%12.12s: %s\n","explain", p->explainPrev.valid ? "on" :"off");
3289 fprintf(p->out,"%12.12s: %s\n","headers", p->showHeader ? "on" : "off");
3290 fprintf(p->out,"%12.12s: %s\n","mode", modeDescr[p->mode]);
3291 fprintf(p->out,"%12.12s: ", "nullvalue");
drhfeac5f82004-08-01 00:10:45 +00003292 output_c_string(p->out, p->nullvalue);
3293 fprintf(p->out, "\n");
mistachkin636bf9f2014-07-19 20:15:16 +00003294 fprintf(p->out,"%12.12s: %s\n","output",
drh4f21c4a2008-12-10 22:15:00 +00003295 strlen30(p->outfile) ? p->outfile : "stdout");
mistachkin636bf9f2014-07-19 20:15:16 +00003296 fprintf(p->out,"%12.12s: ", "colseparator");
3297 output_c_string(p->out, p->colSeparator);
drhfeac5f82004-08-01 00:10:45 +00003298 fprintf(p->out, "\n");
mistachkin636bf9f2014-07-19 20:15:16 +00003299 fprintf(p->out,"%12.12s: ", "rowseparator");
3300 output_c_string(p->out, p->rowSeparator);
3301 fprintf(p->out, "\n");
mistachkinfad42082014-07-24 22:13:12 +00003302 fprintf(p->out,"%12.12s: ", "newline");
drh6976c212014-07-24 12:09:47 +00003303 output_c_string(p->out, p->newline);
persicom7e2dfdd2002-04-18 02:46:52 +00003304 fprintf(p->out, "\n");
mistachkin636bf9f2014-07-19 20:15:16 +00003305 fprintf(p->out,"%12.12s: %s\n","stats", p->statsOn ? "on" : "off");
3306 fprintf(p->out,"%12.12s: ","width");
persicom7e2dfdd2002-04-18 02:46:52 +00003307 for (i=0;i<(int)ArraySize(p->colWidth) && p->colWidth[i] != 0;i++) {
drhfeac5f82004-08-01 00:10:45 +00003308 fprintf(p->out,"%d ",p->colWidth[i]);
persicom7e2dfdd2002-04-18 02:46:52 +00003309 }
drhfeac5f82004-08-01 00:10:45 +00003310 fprintf(p->out,"\n");
persicom7e2dfdd2002-04-18 02:46:52 +00003311 }else
3312
drhc2ce0be2014-05-29 12:36:14 +00003313 if( c=='s' && strncmp(azArg[0], "stats", n)==0 ){
3314 if( nArg==2 ){
3315 p->statsOn = booleanValue(azArg[1]);
3316 }else{
3317 fprintf(stderr, "Usage: .stats on|off\n");
3318 rc = 1;
3319 }
shaneh642d8b82010-07-28 16:05:34 +00003320 }else
3321
drhc2ce0be2014-05-29 12:36:14 +00003322 if( c=='t' && n>1 && strncmp(azArg[0], "tables", n)==0 ){
drh98781232012-04-23 12:38:05 +00003323 sqlite3_stmt *pStmt;
drhe3710332000-09-29 13:30:53 +00003324 char **azResult;
drh98781232012-04-23 12:38:05 +00003325 int nRow, nAlloc;
3326 char *zSql = 0;
3327 int ii;
drh05782482013-10-24 15:20:20 +00003328 open_db(p, 0);
drh98781232012-04-23 12:38:05 +00003329 rc = sqlite3_prepare_v2(p->db, "PRAGMA database_list", -1, &pStmt, 0);
3330 if( rc ) return rc;
3331 zSql = sqlite3_mprintf(
3332 "SELECT name FROM sqlite_master"
3333 " WHERE type IN ('table','view')"
3334 " AND name NOT LIKE 'sqlite_%%'"
3335 " AND name LIKE ?1");
3336 while( sqlite3_step(pStmt)==SQLITE_ROW ){
3337 const char *zDbName = (const char*)sqlite3_column_text(pStmt, 1);
3338 if( zDbName==0 || strcmp(zDbName,"main")==0 ) continue;
3339 if( strcmp(zDbName,"temp")==0 ){
3340 zSql = sqlite3_mprintf(
3341 "%z UNION ALL "
3342 "SELECT 'temp.' || name FROM sqlite_temp_master"
3343 " WHERE type IN ('table','view')"
3344 " AND name NOT LIKE 'sqlite_%%'"
3345 " AND name LIKE ?1", zSql);
3346 }else{
3347 zSql = sqlite3_mprintf(
3348 "%z UNION ALL "
3349 "SELECT '%q.' || name FROM \"%w\".sqlite_master"
3350 " WHERE type IN ('table','view')"
3351 " AND name NOT LIKE 'sqlite_%%'"
3352 " AND name LIKE ?1", zSql, zDbName, zDbName);
3353 }
drha50da102000-08-08 20:19:09 +00003354 }
drh98781232012-04-23 12:38:05 +00003355 sqlite3_finalize(pStmt);
3356 zSql = sqlite3_mprintf("%z ORDER BY 1", zSql);
3357 rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
3358 sqlite3_free(zSql);
3359 if( rc ) return rc;
3360 nRow = nAlloc = 0;
3361 azResult = 0;
3362 if( nArg>1 ){
3363 sqlite3_bind_text(pStmt, 1, azArg[1], -1, SQLITE_TRANSIENT);
shane9bd1b442009-10-23 01:27:39 +00003364 }else{
drh98781232012-04-23 12:38:05 +00003365 sqlite3_bind_text(pStmt, 1, "%", -1, SQLITE_STATIC);
3366 }
3367 while( sqlite3_step(pStmt)==SQLITE_ROW ){
3368 if( nRow>=nAlloc ){
3369 char **azNew;
3370 int n = nAlloc*2 + 10;
3371 azNew = sqlite3_realloc(azResult, sizeof(azResult[0])*n);
3372 if( azNew==0 ){
3373 fprintf(stderr, "Error: out of memory\n");
3374 break;
3375 }
3376 nAlloc = n;
3377 azResult = azNew;
3378 }
3379 azResult[nRow] = sqlite3_mprintf("%s", sqlite3_column_text(pStmt, 0));
3380 if( azResult[nRow] ) nRow++;
3381 }
3382 sqlite3_finalize(pStmt);
3383 if( nRow>0 ){
drhe3710332000-09-29 13:30:53 +00003384 int len, maxlen = 0;
3385 int i, j;
3386 int nPrintCol, nPrintRow;
drh98781232012-04-23 12:38:05 +00003387 for(i=0; i<nRow; i++){
drh4f21c4a2008-12-10 22:15:00 +00003388 len = strlen30(azResult[i]);
drhe3710332000-09-29 13:30:53 +00003389 if( len>maxlen ) maxlen = len;
3390 }
3391 nPrintCol = 80/(maxlen+2);
3392 if( nPrintCol<1 ) nPrintCol = 1;
3393 nPrintRow = (nRow + nPrintCol - 1)/nPrintCol;
3394 for(i=0; i<nPrintRow; i++){
drh98781232012-04-23 12:38:05 +00003395 for(j=i; j<nRow; j+=nPrintRow){
3396 char *zSp = j<nPrintRow ? "" : " ";
drh151b7d52013-05-06 20:28:54 +00003397 fprintf(p->out, "%s%-*s", zSp, maxlen, azResult[j] ? azResult[j] : "");
drhe3710332000-09-29 13:30:53 +00003398 }
drh151b7d52013-05-06 20:28:54 +00003399 fprintf(p->out, "\n");
drhe3710332000-09-29 13:30:53 +00003400 }
3401 }
drh98781232012-04-23 12:38:05 +00003402 for(ii=0; ii<nRow; ii++) sqlite3_free(azResult[ii]);
3403 sqlite3_free(azResult);
drh75897232000-05-29 14:26:00 +00003404 }else
3405
shaneh96887e12011-02-10 21:08:58 +00003406 if( c=='t' && n>=8 && strncmp(azArg[0], "testctrl", n)==0 && nArg>=2 ){
drhd416fe72011-03-17 16:45:50 +00003407 static const struct {
3408 const char *zCtrlName; /* Name of a test-control option */
3409 int ctrlCode; /* Integer code for that option */
3410 } aCtrl[] = {
3411 { "prng_save", SQLITE_TESTCTRL_PRNG_SAVE },
3412 { "prng_restore", SQLITE_TESTCTRL_PRNG_RESTORE },
3413 { "prng_reset", SQLITE_TESTCTRL_PRNG_RESET },
3414 { "bitvec_test", SQLITE_TESTCTRL_BITVEC_TEST },
3415 { "fault_install", SQLITE_TESTCTRL_FAULT_INSTALL },
3416 { "benign_malloc_hooks", SQLITE_TESTCTRL_BENIGN_MALLOC_HOOKS },
3417 { "pending_byte", SQLITE_TESTCTRL_PENDING_BYTE },
3418 { "assert", SQLITE_TESTCTRL_ASSERT },
3419 { "always", SQLITE_TESTCTRL_ALWAYS },
3420 { "reserve", SQLITE_TESTCTRL_RESERVE },
3421 { "optimizations", SQLITE_TESTCTRL_OPTIMIZATIONS },
3422 { "iskeyword", SQLITE_TESTCTRL_ISKEYWORD },
drhd416fe72011-03-17 16:45:50 +00003423 { "scratchmalloc", SQLITE_TESTCTRL_SCRATCHMALLOC },
drh2cf4acb2014-04-18 00:06:02 +00003424 { "byteorder", SQLITE_TESTCTRL_BYTEORDER },
drhd416fe72011-03-17 16:45:50 +00003425 };
shaneh96887e12011-02-10 21:08:58 +00003426 int testctrl = -1;
3427 int rc = 0;
drhd416fe72011-03-17 16:45:50 +00003428 int i, n;
drh05782482013-10-24 15:20:20 +00003429 open_db(p, 0);
shaneh96887e12011-02-10 21:08:58 +00003430
drhd416fe72011-03-17 16:45:50 +00003431 /* convert testctrl text option to value. allow any unique prefix
3432 ** of the option name, or a numerical value. */
shanehcef83682011-04-07 03:41:01 +00003433 n = strlen30(azArg[1]);
drhfcd71b62011-04-05 22:08:24 +00003434 for(i=0; i<(int)(sizeof(aCtrl)/sizeof(aCtrl[0])); i++){
drhd416fe72011-03-17 16:45:50 +00003435 if( strncmp(azArg[1], aCtrl[i].zCtrlName, n)==0 ){
3436 if( testctrl<0 ){
3437 testctrl = aCtrl[i].ctrlCode;
3438 }else{
drhb07028f2011-10-14 21:49:18 +00003439 fprintf(stderr, "ambiguous option name: \"%s\"\n", azArg[1]);
drhd416fe72011-03-17 16:45:50 +00003440 testctrl = -1;
3441 break;
3442 }
3443 }
3444 }
drh348d19c2013-06-03 12:47:43 +00003445 if( testctrl<0 ) testctrl = (int)integerValue(azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003446 if( (testctrl<SQLITE_TESTCTRL_FIRST) || (testctrl>SQLITE_TESTCTRL_LAST) ){
3447 fprintf(stderr,"Error: invalid testctrl option: %s\n", azArg[1]);
3448 }else{
3449 switch(testctrl){
3450
3451 /* sqlite3_test_control(int, db, int) */
3452 case SQLITE_TESTCTRL_OPTIMIZATIONS:
3453 case SQLITE_TESTCTRL_RESERVE:
3454 if( nArg==3 ){
3455 int opt = (int)strtol(azArg[2], 0, 0);
3456 rc = sqlite3_test_control(testctrl, p->db, opt);
drh151b7d52013-05-06 20:28:54 +00003457 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003458 } else {
drhd416fe72011-03-17 16:45:50 +00003459 fprintf(stderr,"Error: testctrl %s takes a single int option\n",
3460 azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003461 }
3462 break;
3463
3464 /* sqlite3_test_control(int) */
drh2cf4acb2014-04-18 00:06:02 +00003465 case SQLITE_TESTCTRL_PRNG_SAVE:
3466 case SQLITE_TESTCTRL_PRNG_RESTORE:
shaneh96887e12011-02-10 21:08:58 +00003467 case SQLITE_TESTCTRL_PRNG_RESET:
drh2cf4acb2014-04-18 00:06:02 +00003468 case SQLITE_TESTCTRL_BYTEORDER:
shaneh96887e12011-02-10 21:08:58 +00003469 if( nArg==2 ){
3470 rc = sqlite3_test_control(testctrl);
drh151b7d52013-05-06 20:28:54 +00003471 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003472 } else {
3473 fprintf(stderr,"Error: testctrl %s takes no options\n", azArg[1]);
3474 }
3475 break;
3476
3477 /* sqlite3_test_control(int, uint) */
3478 case SQLITE_TESTCTRL_PENDING_BYTE:
3479 if( nArg==3 ){
drhaf664332013-07-18 20:28:29 +00003480 unsigned int opt = (unsigned int)integerValue(azArg[2]);
shaneh96887e12011-02-10 21:08:58 +00003481 rc = sqlite3_test_control(testctrl, opt);
drh151b7d52013-05-06 20:28:54 +00003482 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003483 } else {
drhd416fe72011-03-17 16:45:50 +00003484 fprintf(stderr,"Error: testctrl %s takes a single unsigned"
3485 " int option\n", azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003486 }
3487 break;
3488
3489 /* sqlite3_test_control(int, int) */
3490 case SQLITE_TESTCTRL_ASSERT:
3491 case SQLITE_TESTCTRL_ALWAYS:
3492 if( nArg==3 ){
drh348d19c2013-06-03 12:47:43 +00003493 int opt = booleanValue(azArg[2]);
shaneh96887e12011-02-10 21:08:58 +00003494 rc = sqlite3_test_control(testctrl, opt);
drh151b7d52013-05-06 20:28:54 +00003495 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003496 } else {
drhd416fe72011-03-17 16:45:50 +00003497 fprintf(stderr,"Error: testctrl %s takes a single int option\n",
3498 azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003499 }
3500 break;
3501
3502 /* sqlite3_test_control(int, char *) */
3503#ifdef SQLITE_N_KEYWORD
3504 case SQLITE_TESTCTRL_ISKEYWORD:
3505 if( nArg==3 ){
3506 const char *opt = azArg[2];
3507 rc = sqlite3_test_control(testctrl, opt);
drh151b7d52013-05-06 20:28:54 +00003508 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003509 } else {
drhd416fe72011-03-17 16:45:50 +00003510 fprintf(stderr,"Error: testctrl %s takes a single char * option\n",
3511 azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003512 }
3513 break;
3514#endif
3515
3516 case SQLITE_TESTCTRL_BITVEC_TEST:
3517 case SQLITE_TESTCTRL_FAULT_INSTALL:
3518 case SQLITE_TESTCTRL_BENIGN_MALLOC_HOOKS:
3519 case SQLITE_TESTCTRL_SCRATCHMALLOC:
3520 default:
drhd416fe72011-03-17 16:45:50 +00003521 fprintf(stderr,"Error: CLI support for testctrl %s not implemented\n",
3522 azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003523 break;
3524 }
3525 }
3526 }else
3527
drhc2ce0be2014-05-29 12:36:14 +00003528 if( c=='t' && n>4 && strncmp(azArg[0], "timeout", n)==0 ){
drh05782482013-10-24 15:20:20 +00003529 open_db(p, 0);
drhc2ce0be2014-05-29 12:36:14 +00003530 sqlite3_busy_timeout(p->db, nArg>=2 ? (int)integerValue(azArg[1]) : 0);
shanehe2aa9d72009-11-06 17:20:17 +00003531 }else
3532
drhc2ce0be2014-05-29 12:36:14 +00003533 if( c=='t' && n>=5 && strncmp(azArg[0], "timer", n)==0 ){
3534 if( nArg==2 ){
3535 enableTimer = booleanValue(azArg[1]);
3536 if( enableTimer && !HAS_TIMER ){
3537 fprintf(stderr, "Error: timer not available on this system.\n");
3538 enableTimer = 0;
3539 }
3540 }else{
3541 fprintf(stderr, "Usage: .timer on|off\n");
3542 rc = 1;
3543 }
shanehe2aa9d72009-11-06 17:20:17 +00003544 }else
3545
drhc2ce0be2014-05-29 12:36:14 +00003546 if( c=='t' && strncmp(azArg[0], "trace", n)==0 ){
drh05782482013-10-24 15:20:20 +00003547 open_db(p, 0);
drh42f64e52012-04-04 16:56:23 +00003548 output_file_close(p->traceOut);
drhc2ce0be2014-05-29 12:36:14 +00003549 if( nArg!=2 ){
3550 fprintf(stderr, "Usage: .trace FILE|off\n");
3551 rc = 1;
3552 goto meta_command_exit;
3553 }
drh42f64e52012-04-04 16:56:23 +00003554 p->traceOut = output_file_open(azArg[1]);
drhbbb0be82012-06-27 16:12:27 +00003555#if !defined(SQLITE_OMIT_TRACE) && !defined(SQLITE_OMIT_FLOATING_POINT)
drh42f64e52012-04-04 16:56:23 +00003556 if( p->traceOut==0 ){
3557 sqlite3_trace(p->db, 0, 0);
3558 }else{
3559 sqlite3_trace(p->db, sql_trace_callback, p->traceOut);
3560 }
3561#endif
3562 }else
3563
drh9fd301b2011-06-03 13:28:22 +00003564 if( c=='v' && strncmp(azArg[0], "version", n)==0 ){
drh151b7d52013-05-06 20:28:54 +00003565 fprintf(p->out, "SQLite %s %s\n" /*extra-version-info*/,
drh9fd301b2011-06-03 13:28:22 +00003566 sqlite3_libversion(), sqlite3_sourceid());
3567 }else
3568
drhde60fc22011-12-14 17:53:36 +00003569 if( c=='v' && strncmp(azArg[0], "vfsname", n)==0 ){
3570 const char *zDbName = nArg==2 ? azArg[1] : "main";
3571 char *zVfsName = 0;
3572 if( p->db ){
3573 sqlite3_file_control(p->db, zDbName, SQLITE_FCNTL_VFSNAME, &zVfsName);
3574 if( zVfsName ){
drh151b7d52013-05-06 20:28:54 +00003575 fprintf(p->out, "%s\n", zVfsName);
drhde60fc22011-12-14 17:53:36 +00003576 sqlite3_free(zVfsName);
3577 }
3578 }
3579 }else
3580
drhcef4fc82012-09-21 22:50:45 +00003581#if defined(SQLITE_DEBUG) && defined(SQLITE_ENABLE_WHERETRACE)
3582 if( c=='w' && strncmp(azArg[0], "wheretrace", n)==0 ){
3583 extern int sqlite3WhereTrace;
drhc2ce0be2014-05-29 12:36:14 +00003584 sqlite3WhereTrace = nArg>=2 ? booleanValue(azArg[1]) : 0xff;
drhcef4fc82012-09-21 22:50:45 +00003585 }else
3586#endif
3587
drhc2ce0be2014-05-29 12:36:14 +00003588 if( c=='w' && strncmp(azArg[0], "width", n)==0 ){
drh75897232000-05-29 14:26:00 +00003589 int j;
drh43617e92006-03-06 20:55:46 +00003590 assert( nArg<=ArraySize(azArg) );
drh75897232000-05-29 14:26:00 +00003591 for(j=1; j<nArg && j<ArraySize(p->colWidth); j++){
drh348d19c2013-06-03 12:47:43 +00003592 p->colWidth[j-1] = (int)integerValue(azArg[j]);
drh75897232000-05-29 14:26:00 +00003593 }
3594 }else
3595
3596 {
shane9bd1b442009-10-23 01:27:39 +00003597 fprintf(stderr, "Error: unknown command or invalid arguments: "
drh67505e72002-04-19 12:34:06 +00003598 " \"%s\". Enter \".help\" for help\n", azArg[0]);
shane9bd1b442009-10-23 01:27:39 +00003599 rc = 1;
drh75897232000-05-29 14:26:00 +00003600 }
drh67505e72002-04-19 12:34:06 +00003601
drhc2ce0be2014-05-29 12:36:14 +00003602meta_command_exit:
3603 if( p->outCount ){
3604 p->outCount--;
3605 if( p->outCount==0 ) output_reset(p);
3606 }
drh67505e72002-04-19 12:34:06 +00003607 return rc;
drh75897232000-05-29 14:26:00 +00003608}
3609
drh67505e72002-04-19 12:34:06 +00003610/*
drh91a66392007-09-07 01:12:32 +00003611** Return TRUE if a semicolon occurs anywhere in the first N characters
3612** of string z[].
drh324ccef2003-02-05 14:06:20 +00003613*/
drh9f099fd2013-08-06 14:01:46 +00003614static int line_contains_semicolon(const char *z, int N){
drh91a66392007-09-07 01:12:32 +00003615 int i;
3616 for(i=0; i<N; i++){ if( z[i]==';' ) return 1; }
3617 return 0;
drh324ccef2003-02-05 14:06:20 +00003618}
3619
3620/*
drh70c7a4b2003-04-26 03:03:06 +00003621** Test to see if a line consists entirely of whitespace.
3622*/
3623static int _all_whitespace(const char *z){
3624 for(; *z; z++){
drhf0693c82011-10-11 20:41:54 +00003625 if( IsSpace(z[0]) ) continue;
drh70c7a4b2003-04-26 03:03:06 +00003626 if( *z=='/' && z[1]=='*' ){
3627 z += 2;
3628 while( *z && (*z!='*' || z[1]!='/') ){ z++; }
3629 if( *z==0 ) return 0;
3630 z++;
3631 continue;
3632 }
3633 if( *z=='-' && z[1]=='-' ){
3634 z += 2;
3635 while( *z && *z!='\n' ){ z++; }
3636 if( *z==0 ) return 1;
3637 continue;
3638 }
3639 return 0;
3640 }
3641 return 1;
3642}
3643
3644/*
drha9b17162003-04-29 18:01:28 +00003645** Return TRUE if the line typed in is an SQL command terminator other
3646** than a semi-colon. The SQL Server style "go" command is understood
3647** as is the Oracle "/".
3648*/
drh9f099fd2013-08-06 14:01:46 +00003649static int line_is_command_terminator(const char *zLine){
drhf0693c82011-10-11 20:41:54 +00003650 while( IsSpace(zLine[0]) ){ zLine++; };
drh233a5312008-12-18 22:25:13 +00003651 if( zLine[0]=='/' && _all_whitespace(&zLine[1]) ){
3652 return 1; /* Oracle */
3653 }
drhf0693c82011-10-11 20:41:54 +00003654 if( ToLower(zLine[0])=='g' && ToLower(zLine[1])=='o'
drhc8d74412004-08-31 23:41:26 +00003655 && _all_whitespace(&zLine[2]) ){
drha9b17162003-04-29 18:01:28 +00003656 return 1; /* SQL Server */
3657 }
3658 return 0;
3659}
3660
3661/*
drh233a5312008-12-18 22:25:13 +00003662** Return true if zSql is a complete SQL statement. Return false if it
3663** ends in the middle of a string literal or C-style comment.
3664*/
drh9f099fd2013-08-06 14:01:46 +00003665static int line_is_complete(char *zSql, int nSql){
drh233a5312008-12-18 22:25:13 +00003666 int rc;
3667 if( zSql==0 ) return 1;
3668 zSql[nSql] = ';';
3669 zSql[nSql+1] = 0;
3670 rc = sqlite3_complete(zSql);
3671 zSql[nSql] = 0;
3672 return rc;
3673}
3674
3675/*
drh67505e72002-04-19 12:34:06 +00003676** Read input from *in and process it. If *in==0 then input
3677** is interactive - the user is typing it it. Otherwise, input
3678** is coming from a file or device. A prompt is issued and history
3679** is saved only if input is interactive. An interrupt signal will
3680** cause this routine to exit immediately, unless input is interactive.
drhc28490c2006-10-26 14:25:58 +00003681**
3682** Return the number of errors.
drh67505e72002-04-19 12:34:06 +00003683*/
drhc28490c2006-10-26 14:25:58 +00003684static int process_input(struct callback_data *p, FILE *in){
drh9f099fd2013-08-06 14:01:46 +00003685 char *zLine = 0; /* A single input line */
3686 char *zSql = 0; /* Accumulated SQL text */
3687 int nLine; /* Length of current line */
3688 int nSql = 0; /* Bytes of zSql[] used */
3689 int nAlloc = 0; /* Allocated zSql[] space */
3690 int nSqlPrior = 0; /* Bytes of zSql[] used by prior line */
3691 char *zErrMsg; /* Error message returned */
3692 int rc; /* Error code */
3693 int errCnt = 0; /* Number of errors seen */
3694 int lineno = 0; /* Current line number */
3695 int startline = 0; /* Line number for start of current input */
drhc49f44e2006-10-26 18:15:42 +00003696
3697 while( errCnt==0 || !bail_on_error || (in==0 && stdin_is_interactive) ){
3698 fflush(p->out);
drh9f099fd2013-08-06 14:01:46 +00003699 zLine = one_input_line(in, zLine, nSql>0);
drhc49f44e2006-10-26 18:15:42 +00003700 if( zLine==0 ){
drh9b8d3572012-04-21 11:33:39 +00003701 /* End of input */
3702 if( stdin_is_interactive ) printf("\n");
3703 break;
drhc49f44e2006-10-26 18:15:42 +00003704 }
drh67505e72002-04-19 12:34:06 +00003705 if( seenInterrupt ){
3706 if( in!=0 ) break;
3707 seenInterrupt = 0;
3708 }
drhc28490c2006-10-26 14:25:58 +00003709 lineno++;
drh849a9d92013-12-21 15:46:06 +00003710 if( nSql==0 && _all_whitespace(zLine) ){
3711 if( p->echoOn ) printf("%s\n", zLine);
3712 continue;
3713 }
drh2af0b2d2002-02-21 02:25:02 +00003714 if( zLine && zLine[0]=='.' && nSql==0 ){
shaneb9fc17d2009-10-22 21:23:35 +00003715 if( p->echoOn ) printf("%s\n", zLine);
drhc49f44e2006-10-26 18:15:42 +00003716 rc = do_meta_command(zLine, p);
shane916f9612009-10-23 00:37:15 +00003717 if( rc==2 ){ /* exit requested */
drh47ad6842006-11-08 12:25:42 +00003718 break;
3719 }else if( rc ){
drhc49f44e2006-10-26 18:15:42 +00003720 errCnt++;
3721 }
drhdaffd0e2001-04-11 14:28:42 +00003722 continue;
3723 }
drh9f099fd2013-08-06 14:01:46 +00003724 if( line_is_command_terminator(zLine) && line_is_complete(zSql, nSql) ){
drh5bb3eb92007-05-04 13:15:55 +00003725 memcpy(zLine,";",2);
drha9b17162003-04-29 18:01:28 +00003726 }
drh9f099fd2013-08-06 14:01:46 +00003727 nLine = strlen30(zLine);
3728 if( nSql+nLine+2>=nAlloc ){
3729 nAlloc = nSql+nLine+100;
3730 zSql = realloc(zSql, nAlloc);
drhdaffd0e2001-04-11 14:28:42 +00003731 if( zSql==0 ){
drh9f099fd2013-08-06 14:01:46 +00003732 fprintf(stderr, "Error: out of memory\n");
drhdaffd0e2001-04-11 14:28:42 +00003733 exit(1);
3734 }
drhdaffd0e2001-04-11 14:28:42 +00003735 }
drh9f099fd2013-08-06 14:01:46 +00003736 nSqlPrior = nSql;
3737 if( nSql==0 ){
3738 int i;
3739 for(i=0; zLine[i] && IsSpace(zLine[i]); i++){}
drh77dfd5b2013-08-19 11:15:48 +00003740 assert( nAlloc>0 && zSql!=0 );
drh9f099fd2013-08-06 14:01:46 +00003741 memcpy(zSql, zLine+i, nLine+1-i);
3742 startline = lineno;
3743 nSql = nLine-i;
3744 }else{
3745 zSql[nSql++] = '\n';
3746 memcpy(zSql+nSql, zLine, nLine+1);
3747 nSql += nLine;
3748 }
3749 if( nSql && line_contains_semicolon(&zSql[nSqlPrior], nSql-nSqlPrior)
drh91a66392007-09-07 01:12:32 +00003750 && sqlite3_complete(zSql) ){
drhdaffd0e2001-04-11 14:28:42 +00003751 p->cnt = 0;
drh05782482013-10-24 15:20:20 +00003752 open_db(p, 0);
drh3b1a9882007-11-02 12:53:03 +00003753 BEGIN_TIMER;
shane626a6e42009-10-22 17:30:15 +00003754 rc = shell_exec(p->db, zSql, shell_callback, p, &zErrMsg);
drh3b1a9882007-11-02 12:53:03 +00003755 END_TIMER;
drh7f953e22002-07-13 17:33:45 +00003756 if( rc || zErrMsg ){
drhc28490c2006-10-26 14:25:58 +00003757 char zPrefix[100];
3758 if( in!=0 || !stdin_is_interactive ){
drh5bb3eb92007-05-04 13:15:55 +00003759 sqlite3_snprintf(sizeof(zPrefix), zPrefix,
shane9bd1b442009-10-23 01:27:39 +00003760 "Error: near line %d:", startline);
drhc28490c2006-10-26 14:25:58 +00003761 }else{
shane9bd1b442009-10-23 01:27:39 +00003762 sqlite3_snprintf(sizeof(zPrefix), zPrefix, "Error:");
drhc28490c2006-10-26 14:25:58 +00003763 }
drh7f953e22002-07-13 17:33:45 +00003764 if( zErrMsg!=0 ){
shaned2bed1c2009-10-21 03:56:54 +00003765 fprintf(stderr, "%s %s\n", zPrefix, zErrMsg);
drh3f4fedb2004-05-31 19:34:33 +00003766 sqlite3_free(zErrMsg);
drh7f953e22002-07-13 17:33:45 +00003767 zErrMsg = 0;
3768 }else{
shaned2bed1c2009-10-21 03:56:54 +00003769 fprintf(stderr, "%s %s\n", zPrefix, sqlite3_errmsg(p->db));
drh7f953e22002-07-13 17:33:45 +00003770 }
drhc49f44e2006-10-26 18:15:42 +00003771 errCnt++;
drhdaffd0e2001-04-11 14:28:42 +00003772 }
drhdaffd0e2001-04-11 14:28:42 +00003773 nSql = 0;
drhc2ce0be2014-05-29 12:36:14 +00003774 if( p->outCount ){
3775 output_reset(p);
3776 p->outCount = 0;
3777 }
drh9f099fd2013-08-06 14:01:46 +00003778 }else if( nSql && _all_whitespace(zSql) ){
drh849a9d92013-12-21 15:46:06 +00003779 if( p->echoOn ) printf("%s\n", zSql);
drh7a411f42013-04-17 17:33:17 +00003780 nSql = 0;
drhdaffd0e2001-04-11 14:28:42 +00003781 }
3782 }
drh9f099fd2013-08-06 14:01:46 +00003783 if( nSql ){
drhd416fe72011-03-17 16:45:50 +00003784 if( !_all_whitespace(zSql) ){
3785 fprintf(stderr, "Error: incomplete SQL: %s\n", zSql);
3786 }
drhdaffd0e2001-04-11 14:28:42 +00003787 free(zSql);
3788 }
danielk19772ac27622007-07-03 05:31:16 +00003789 free(zLine);
drh4d15a0d2012-12-01 20:21:22 +00003790 return errCnt>0;
drhdaffd0e2001-04-11 14:28:42 +00003791}
3792
drh67505e72002-04-19 12:34:06 +00003793/*
3794** Return a pathname which is the user's home directory. A
drh85e72432012-04-11 11:38:53 +00003795** 0 return indicates an error of some kind.
drh67505e72002-04-19 12:34:06 +00003796*/
3797static char *find_home_dir(void){
drh85e72432012-04-11 11:38:53 +00003798 static char *home_dir = NULL;
3799 if( home_dir ) return home_dir;
persicom7e2dfdd2002-04-18 02:46:52 +00003800
drh83905c92012-06-21 13:00:37 +00003801#if !defined(_WIN32) && !defined(WIN32) && !defined(_WIN32_WCE) && !defined(__RTP__) && !defined(_WRS_KERNEL)
mistachkinc8bde372012-06-18 08:00:56 +00003802 {
3803 struct passwd *pwent;
3804 uid_t uid = getuid();
3805 if( (pwent=getpwuid(uid)) != NULL) {
3806 home_dir = pwent->pw_dir;
3807 }
drh67505e72002-04-19 12:34:06 +00003808 }
3809#endif
3810
chw65d3c132007-11-12 21:09:10 +00003811#if defined(_WIN32_WCE)
3812 /* Windows CE (arm-wince-mingw32ce-gcc) does not provide getenv()
3813 */
drh85e72432012-04-11 11:38:53 +00003814 home_dir = "/";
chw65d3c132007-11-12 21:09:10 +00003815#else
3816
drh83905c92012-06-21 13:00:37 +00003817#if defined(_WIN32) || defined(WIN32)
drh164a1b62006-08-19 11:15:20 +00003818 if (!home_dir) {
3819 home_dir = getenv("USERPROFILE");
3820 }
3821#endif
3822
drh67505e72002-04-19 12:34:06 +00003823 if (!home_dir) {
3824 home_dir = getenv("HOME");
drh67505e72002-04-19 12:34:06 +00003825 }
3826
drh83905c92012-06-21 13:00:37 +00003827#if defined(_WIN32) || defined(WIN32)
drhe98d4fa2002-04-21 19:06:22 +00003828 if (!home_dir) {
drh164a1b62006-08-19 11:15:20 +00003829 char *zDrive, *zPath;
3830 int n;
3831 zDrive = getenv("HOMEDRIVE");
3832 zPath = getenv("HOMEPATH");
3833 if( zDrive && zPath ){
drh4f21c4a2008-12-10 22:15:00 +00003834 n = strlen30(zDrive) + strlen30(zPath) + 1;
drh164a1b62006-08-19 11:15:20 +00003835 home_dir = malloc( n );
3836 if( home_dir==0 ) return 0;
3837 sqlite3_snprintf(n, home_dir, "%s%s", zDrive, zPath);
3838 return home_dir;
3839 }
3840 home_dir = "c:\\";
drhe98d4fa2002-04-21 19:06:22 +00003841 }
3842#endif
3843
chw65d3c132007-11-12 21:09:10 +00003844#endif /* !_WIN32_WCE */
3845
drh67505e72002-04-19 12:34:06 +00003846 if( home_dir ){
drh4f21c4a2008-12-10 22:15:00 +00003847 int n = strlen30(home_dir) + 1;
drh5bb3eb92007-05-04 13:15:55 +00003848 char *z = malloc( n );
3849 if( z ) memcpy(z, home_dir, n);
drh67505e72002-04-19 12:34:06 +00003850 home_dir = z;
3851 }
drhe98d4fa2002-04-21 19:06:22 +00003852
drh67505e72002-04-19 12:34:06 +00003853 return home_dir;
3854}
3855
3856/*
3857** Read input from the file given by sqliterc_override. Or if that
3858** parameter is NULL, take input from ~/.sqliterc
shane9bd1b442009-10-23 01:27:39 +00003859**
3860** Returns the number of errors.
drh67505e72002-04-19 12:34:06 +00003861*/
shane9bd1b442009-10-23 01:27:39 +00003862static int process_sqliterc(
drh22fbcb82004-02-01 01:22:50 +00003863 struct callback_data *p, /* Configuration data */
3864 const char *sqliterc_override /* Name of config file. NULL to use default */
3865){
persicom7e2dfdd2002-04-18 02:46:52 +00003866 char *home_dir = NULL;
drh22fbcb82004-02-01 01:22:50 +00003867 const char *sqliterc = sqliterc_override;
drh43617e92006-03-06 20:55:46 +00003868 char *zBuf = 0;
persicom7e2dfdd2002-04-18 02:46:52 +00003869 FILE *in = NULL;
shane9bd1b442009-10-23 01:27:39 +00003870 int rc = 0;
persicom7e2dfdd2002-04-18 02:46:52 +00003871
3872 if (sqliterc == NULL) {
drh67505e72002-04-19 12:34:06 +00003873 home_dir = find_home_dir();
drhe98d4fa2002-04-21 19:06:22 +00003874 if( home_dir==0 ){
chw97185482008-11-17 08:05:31 +00003875#if !defined(__RTP__) && !defined(_WRS_KERNEL)
shane86f5bdb2009-10-24 02:00:07 +00003876 fprintf(stderr,"%s: Error: cannot locate your home directory\n", Argv0);
chw97185482008-11-17 08:05:31 +00003877#endif
shane9bd1b442009-10-23 01:27:39 +00003878 return 1;
drhe98d4fa2002-04-21 19:06:22 +00003879 }
drh2f3de322012-06-27 16:41:31 +00003880 sqlite3_initialize();
drh85e72432012-04-11 11:38:53 +00003881 zBuf = sqlite3_mprintf("%s/.sqliterc",home_dir);
3882 sqliterc = zBuf;
persicom7e2dfdd2002-04-18 02:46:52 +00003883 }
drha1f9b5e2004-02-14 16:31:02 +00003884 in = fopen(sqliterc,"rb");
drh22fbcb82004-02-01 01:22:50 +00003885 if( in ){
drhc28490c2006-10-26 14:25:58 +00003886 if( stdin_is_interactive ){
shane86f5bdb2009-10-24 02:00:07 +00003887 fprintf(stderr,"-- Loading resources from %s\n",sqliterc);
drh22fbcb82004-02-01 01:22:50 +00003888 }
shane9bd1b442009-10-23 01:27:39 +00003889 rc = process_input(p,in);
drhdd45df82002-04-18 12:39:03 +00003890 fclose(in);
persicom7e2dfdd2002-04-18 02:46:52 +00003891 }
drh85e72432012-04-11 11:38:53 +00003892 sqlite3_free(zBuf);
shane9bd1b442009-10-23 01:27:39 +00003893 return rc;
persicom7e2dfdd2002-04-18 02:46:52 +00003894}
3895
drh67505e72002-04-19 12:34:06 +00003896/*
drhe1e38c42003-05-04 18:30:59 +00003897** Show available command line options
3898*/
3899static const char zOptions[] =
mistachkin636bf9f2014-07-19 20:15:16 +00003900 " -ascii set output mode to 'ascii'\n"
drhc49f44e2006-10-26 18:15:42 +00003901 " -bail stop after hitting an error\n"
drhc49f44e2006-10-26 18:15:42 +00003902 " -batch force batch I/O\n"
mistachkin486fd432014-07-24 22:20:23 +00003903 " -colseparator SEP same as -separator with one argument\n"
drhe1e38c42003-05-04 18:30:59 +00003904 " -column set output mode to 'column'\n"
mistachkin6d81d752012-10-25 15:43:28 +00003905 " -cmd COMMAND run \"COMMAND\" before reading stdin\n"
drhc49f44e2006-10-26 18:15:42 +00003906 " -csv set output mode to 'csv'\n"
drhcc3b4f82012-02-07 14:13:50 +00003907 " -echo print commands before execution\n"
mistachkin6d81d752012-10-25 15:43:28 +00003908 " -init FILENAME read/process named file\n"
drhcc3b4f82012-02-07 14:13:50 +00003909 " -[no]header turn headers on or off\n"
drh98d312f2012-10-25 15:23:14 +00003910#if defined(SQLITE_ENABLE_MEMSYS3) || defined(SQLITE_ENABLE_MEMSYS5)
3911 " -heap SIZE Size of heap for memsys3 or memsys5\n"
3912#endif
drhcc3b4f82012-02-07 14:13:50 +00003913 " -help show this message\n"
drhe1e38c42003-05-04 18:30:59 +00003914 " -html set output mode to HTML\n"
drhcc3b4f82012-02-07 14:13:50 +00003915 " -interactive force interactive I/O\n"
drhe1e38c42003-05-04 18:30:59 +00003916 " -line set output mode to 'line'\n"
3917 " -list set output mode to 'list'\n"
drh7d9f3942013-04-03 01:26:54 +00003918 " -mmap N default mmap size set to N\n"
drhcc3b4f82012-02-07 14:13:50 +00003919#ifdef SQLITE_ENABLE_MULTIPLEX
3920 " -multiplex enable the multiplexor VFS\n"
3921#endif
drh6976c212014-07-24 12:09:47 +00003922 " -newline SEP set newline character(s) for CSV\n"
drh98d312f2012-10-25 15:23:14 +00003923 " -nullvalue TEXT set text string for NULL values. Default ''\n"
mistachkin636bf9f2014-07-19 20:15:16 +00003924 " -rowseparator SEP set output line separator. Default: '\\n'\n"
drh98d312f2012-10-25 15:23:14 +00003925 " -separator SEP set output field separator. Default: '|'\n"
shaneh642d8b82010-07-28 16:05:34 +00003926 " -stats print memory stats before each finalize\n"
drhe1e38c42003-05-04 18:30:59 +00003927 " -version show SQLite version\n"
drha7e61d82011-03-12 17:02:57 +00003928 " -vfs NAME use NAME as the default VFS\n"
drh2b625e22011-03-16 17:05:28 +00003929#ifdef SQLITE_ENABLE_VFSTRACE
3930 " -vfstrace enable tracing of all VFS calls\n"
3931#endif
drhe1e38c42003-05-04 18:30:59 +00003932;
3933static void usage(int showDetail){
drh80e8be92006-08-29 12:04:19 +00003934 fprintf(stderr,
3935 "Usage: %s [OPTIONS] FILENAME [SQL]\n"
3936 "FILENAME is the name of an SQLite database. A new database is created\n"
3937 "if the file does not previously exist.\n", Argv0);
drhe1e38c42003-05-04 18:30:59 +00003938 if( showDetail ){
drh80e8be92006-08-29 12:04:19 +00003939 fprintf(stderr, "OPTIONS include:\n%s", zOptions);
drhe1e38c42003-05-04 18:30:59 +00003940 }else{
3941 fprintf(stderr, "Use the -help option for additional information\n");
3942 }
3943 exit(1);
3944}
3945
3946/*
drh67505e72002-04-19 12:34:06 +00003947** Initialize the state information in data
3948*/
drh0850b532006-01-31 19:31:43 +00003949static void main_init(struct callback_data *data) {
persicom7e2dfdd2002-04-18 02:46:52 +00003950 memset(data, 0, sizeof(*data));
3951 data->mode = MODE_List;
mistachkinfad42082014-07-24 22:13:12 +00003952 memcpy(data->colSeparator,SEP_Column, 2);
3953 memcpy(data->rowSeparator,SEP_Row, 2);
3954 memcpy(data->newline,SEP_CrLf, 3);
persicom7e2dfdd2002-04-18 02:46:52 +00003955 data->showHeader = 0;
drh52784bd2011-05-18 17:15:06 +00003956 sqlite3_config(SQLITE_CONFIG_URI, 1);
drh127f9d72010-02-23 01:47:00 +00003957 sqlite3_config(SQLITE_CONFIG_LOG, shellLog, data);
drh5bb3eb92007-05-04 13:15:55 +00003958 sqlite3_snprintf(sizeof(mainPrompt), mainPrompt,"sqlite> ");
3959 sqlite3_snprintf(sizeof(continuePrompt), continuePrompt," ...> ");
dan0f831772010-03-03 07:23:12 +00003960 sqlite3_config(SQLITE_CONFIG_SINGLETHREAD);
persicom7e2dfdd2002-04-18 02:46:52 +00003961}
3962
drh98d312f2012-10-25 15:23:14 +00003963/*
drh5c7976f2014-02-10 19:59:27 +00003964** Output text to the console in a font that attracts extra attention.
drh1247aa42014-02-10 19:27:05 +00003965*/
3966#ifdef _WIN32
drh5c7976f2014-02-10 19:59:27 +00003967static void printBold(const char *zText){
3968 HANDLE out = GetStdHandle(STD_OUTPUT_HANDLE);
3969 CONSOLE_SCREEN_BUFFER_INFO defaultScreenInfo;
3970 GetConsoleScreenBufferInfo(out, &defaultScreenInfo);
3971 SetConsoleTextAttribute(out,
3972 FOREGROUND_RED|FOREGROUND_INTENSITY
3973 );
3974 printf("%s", zText);
3975 SetConsoleTextAttribute(out, defaultScreenInfo.wAttributes);
drh1247aa42014-02-10 19:27:05 +00003976}
3977#else
drh5c7976f2014-02-10 19:59:27 +00003978static void printBold(const char *zText){
3979 printf("\033[1m%s\033[0m", zText);
drh1247aa42014-02-10 19:27:05 +00003980}
3981#endif
3982
3983/*
drh98d312f2012-10-25 15:23:14 +00003984** Get the argument to an --option. Throw an error and die if no argument
3985** is available.
3986*/
3987static char *cmdline_option_value(int argc, char **argv, int i){
3988 if( i==argc ){
3989 fprintf(stderr, "%s: Error: missing argument to %s\n",
3990 argv[0], argv[argc-1]);
3991 exit(1);
3992 }
3993 return argv[i];
3994}
3995
drh75897232000-05-29 14:26:00 +00003996int main(int argc, char **argv){
drh75897232000-05-29 14:26:00 +00003997 char *zErrMsg = 0;
3998 struct callback_data data;
drh22fbcb82004-02-01 01:22:50 +00003999 const char *zInitFile = 0;
4000 char *zFirstCmd = 0;
drh44c2eb12003-04-30 11:38:26 +00004001 int i;
drhc28490c2006-10-26 14:25:58 +00004002 int rc = 0;
drhb3735912014-02-10 16:13:42 +00004003 int warnInmemoryDb = 0;
drh75897232000-05-29 14:26:00 +00004004
drh69b30ab2014-02-27 15:11:52 +00004005#if USE_SYSTEM_SQLITE+0!=1
drh52784bd2011-05-18 17:15:06 +00004006 if( strcmp(sqlite3_sourceid(),SQLITE_SOURCE_ID)!=0 ){
4007 fprintf(stderr, "SQLite header and source version mismatch\n%s\n%s\n",
4008 sqlite3_sourceid(), SQLITE_SOURCE_ID);
4009 exit(1);
4010 }
drhc7181902014-02-27 15:04:13 +00004011#endif
drhdaffd0e2001-04-11 14:28:42 +00004012 Argv0 = argv[0];
persicom7e2dfdd2002-04-18 02:46:52 +00004013 main_init(&data);
drhc28490c2006-10-26 14:25:58 +00004014 stdin_is_interactive = isatty(0);
persicom7e2dfdd2002-04-18 02:46:52 +00004015
drh44c2eb12003-04-30 11:38:26 +00004016 /* Make sure we have a valid signal handler early, before anything
4017 ** else is done.
4018 */
drh4c504392000-10-16 22:06:40 +00004019#ifdef SIGINT
4020 signal(SIGINT, interrupt_handler);
4021#endif
drh44c2eb12003-04-30 11:38:26 +00004022
drh22fbcb82004-02-01 01:22:50 +00004023 /* Do an initial pass through the command-line argument to locate
4024 ** the name of the database file, the name of the initialization file,
drh9c88d682010-12-17 14:03:01 +00004025 ** the size of the alternative malloc heap,
drh22fbcb82004-02-01 01:22:50 +00004026 ** and the first command to execute.
drh44c2eb12003-04-30 11:38:26 +00004027 */
drh98d312f2012-10-25 15:23:14 +00004028 for(i=1; i<argc; i++){
drhc28490c2006-10-26 14:25:58 +00004029 char *z;
drhc28490c2006-10-26 14:25:58 +00004030 z = argv[i];
drh98d312f2012-10-25 15:23:14 +00004031 if( z[0]!='-' ){
4032 if( data.zDbFilename==0 ){
4033 data.zDbFilename = z;
4034 continue;
4035 }
4036 if( zFirstCmd==0 ){
4037 zFirstCmd = z;
4038 continue;
4039 }
4040 fprintf(stderr,"%s: Error: too many options: \"%s\"\n", Argv0, argv[i]);
4041 fprintf(stderr,"Use -help for a list of options.\n");
4042 return 1;
4043 }
drhcc3b4f82012-02-07 14:13:50 +00004044 if( z[1]=='-' ) z++;
4045 if( strcmp(z,"-separator")==0
4046 || strcmp(z,"-nullvalue")==0
drh6976c212014-07-24 12:09:47 +00004047 || strcmp(z,"-newline")==0
drhcc3b4f82012-02-07 14:13:50 +00004048 || strcmp(z,"-cmd")==0
4049 ){
drh98d312f2012-10-25 15:23:14 +00004050 (void)cmdline_option_value(argc, argv, ++i);
drhcc3b4f82012-02-07 14:13:50 +00004051 }else if( strcmp(z,"-init")==0 ){
drh98d312f2012-10-25 15:23:14 +00004052 zInitFile = cmdline_option_value(argc, argv, ++i);
drhcc3b4f82012-02-07 14:13:50 +00004053 }else if( strcmp(z,"-batch")==0 ){
drh98d312f2012-10-25 15:23:14 +00004054 /* Need to check for batch mode here to so we can avoid printing
4055 ** informational messages (like from process_sqliterc) before
4056 ** we do the actual processing of arguments later in a second pass.
4057 */
shanef69573d2009-10-24 02:06:14 +00004058 stdin_is_interactive = 0;
drhcc3b4f82012-02-07 14:13:50 +00004059 }else if( strcmp(z,"-heap")==0 ){
drhb07028f2011-10-14 21:49:18 +00004060#if defined(SQLITE_ENABLE_MEMSYS3) || defined(SQLITE_ENABLE_MEMSYS5)
drh9c88d682010-12-17 14:03:01 +00004061 const char *zSize;
4062 sqlite3_int64 szHeap;
4063
drh98d312f2012-10-25 15:23:14 +00004064 zSize = cmdline_option_value(argc, argv, ++i);
drh7d9f3942013-04-03 01:26:54 +00004065 szHeap = integerValue(zSize);
drh9c88d682010-12-17 14:03:01 +00004066 if( szHeap>0x7fff0000 ) szHeap = 0x7fff0000;
drh9c88d682010-12-17 14:03:01 +00004067 sqlite3_config(SQLITE_CONFIG_HEAP, malloc((int)szHeap), (int)szHeap, 64);
4068#endif
drh97ae8ff2011-03-16 16:56:29 +00004069#ifdef SQLITE_ENABLE_VFSTRACE
drhcc3b4f82012-02-07 14:13:50 +00004070 }else if( strcmp(z,"-vfstrace")==0 ){
drh97ae8ff2011-03-16 16:56:29 +00004071 extern int vfstrace_register(
4072 const char *zTraceName,
4073 const char *zOldVfsName,
4074 int (*xOut)(const char*,void*),
4075 void *pOutArg,
4076 int makeDefault
4077 );
drh2b625e22011-03-16 17:05:28 +00004078 vfstrace_register("trace",0,(int(*)(const char*,void*))fputs,stderr,1);
drh97ae8ff2011-03-16 16:56:29 +00004079#endif
drh6f25e892011-07-08 17:02:57 +00004080#ifdef SQLITE_ENABLE_MULTIPLEX
drhcc3b4f82012-02-07 14:13:50 +00004081 }else if( strcmp(z,"-multiplex")==0 ){
drh6f25e892011-07-08 17:02:57 +00004082 extern int sqlite3_multiple_initialize(const char*,int);
4083 sqlite3_multiplex_initialize(0, 1);
4084#endif
drh7d9f3942013-04-03 01:26:54 +00004085 }else if( strcmp(z,"-mmap")==0 ){
drh9b4c59f2013-04-15 17:03:42 +00004086 sqlite3_int64 sz = integerValue(cmdline_option_value(argc,argv,++i));
4087 sqlite3_config(SQLITE_CONFIG_MMAP_SIZE, sz, sz);
drhcc3b4f82012-02-07 14:13:50 +00004088 }else if( strcmp(z,"-vfs")==0 ){
drh98d312f2012-10-25 15:23:14 +00004089 sqlite3_vfs *pVfs = sqlite3_vfs_find(cmdline_option_value(argc,argv,++i));
drha7e61d82011-03-12 17:02:57 +00004090 if( pVfs ){
4091 sqlite3_vfs_register(pVfs, 1);
4092 }else{
4093 fprintf(stderr, "no such VFS: \"%s\"\n", argv[i]);
4094 exit(1);
4095 }
drh44c2eb12003-04-30 11:38:26 +00004096 }
4097 }
drh98d312f2012-10-25 15:23:14 +00004098 if( data.zDbFilename==0 ){
danielk197703aded42004-11-22 05:26:27 +00004099#ifndef SQLITE_OMIT_MEMORYDB
drh22fbcb82004-02-01 01:22:50 +00004100 data.zDbFilename = ":memory:";
drh1247aa42014-02-10 19:27:05 +00004101 warnInmemoryDb = argc==1;
danielk197703aded42004-11-22 05:26:27 +00004102#else
shane86f5bdb2009-10-24 02:00:07 +00004103 fprintf(stderr,"%s: Error: no database filename specified\n", Argv0);
4104 return 1;
drh01b41712005-08-29 23:06:23 +00004105#endif
drhc7181902014-02-27 15:04:13 +00004106#ifdef SQLITE_SHELL_DBNAME_PROC
4107 { extern void SQLITE_SHELL_DBNAME_PROC(const char**);
4108 SQLITE_SHELL_DBNAME_PROC(&data.zDbFilename);
4109 warnInmemoryDb = 0; }
4110#endif
drh98d312f2012-10-25 15:23:14 +00004111 }
4112 data.out = stdout;
drh01b41712005-08-29 23:06:23 +00004113
drh44c2eb12003-04-30 11:38:26 +00004114 /* Go ahead and open the database file if it already exists. If the
4115 ** file does not exist, delay opening it. This prevents empty database
4116 ** files from being created if a user mistypes the database name argument
4117 ** to the sqlite command-line tool.
4118 */
drhc8d74412004-08-31 23:41:26 +00004119 if( access(data.zDbFilename, 0)==0 ){
drh05782482013-10-24 15:20:20 +00004120 open_db(&data, 0);
drh44c2eb12003-04-30 11:38:26 +00004121 }
4122
drh22fbcb82004-02-01 01:22:50 +00004123 /* Process the initialization file if there is one. If no -init option
4124 ** is given on the command line, look for a file named ~/.sqliterc and
4125 ** try to process it.
drh44c2eb12003-04-30 11:38:26 +00004126 */
shane86f5bdb2009-10-24 02:00:07 +00004127 rc = process_sqliterc(&data,zInitFile);
4128 if( rc>0 ){
4129 return rc;
4130 }
drh44c2eb12003-04-30 11:38:26 +00004131
drh22fbcb82004-02-01 01:22:50 +00004132 /* Make a second pass through the command-line argument and set
4133 ** options. This second pass is delayed until after the initialization
4134 ** file is processed so that the command-line arguments will override
4135 ** settings in the initialization file.
drh44c2eb12003-04-30 11:38:26 +00004136 */
drh98d312f2012-10-25 15:23:14 +00004137 for(i=1; i<argc; i++){
drh22fbcb82004-02-01 01:22:50 +00004138 char *z = argv[i];
drh98d312f2012-10-25 15:23:14 +00004139 if( z[0]!='-' ) continue;
drhc28490c2006-10-26 14:25:58 +00004140 if( z[1]=='-' ){ z++; }
drh2e584cd2006-09-25 13:09:22 +00004141 if( strcmp(z,"-init")==0 ){
drh22fbcb82004-02-01 01:22:50 +00004142 i++;
4143 }else if( strcmp(z,"-html")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00004144 data.mode = MODE_Html;
drh22fbcb82004-02-01 01:22:50 +00004145 }else if( strcmp(z,"-list")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00004146 data.mode = MODE_List;
drh22fbcb82004-02-01 01:22:50 +00004147 }else if( strcmp(z,"-line")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00004148 data.mode = MODE_Line;
drh22fbcb82004-02-01 01:22:50 +00004149 }else if( strcmp(z,"-column")==0 ){
drh8b32e172002-04-08 02:42:57 +00004150 data.mode = MODE_Column;
drhc49f44e2006-10-26 18:15:42 +00004151 }else if( strcmp(z,"-csv")==0 ){
4152 data.mode = MODE_Csv;
mistachkin636bf9f2014-07-19 20:15:16 +00004153 memcpy(data.colSeparator,",",2);
4154 }else if( strcmp(z,"-ascii")==0 ){
4155 data.mode = MODE_Ascii;
4156 sqlite3_snprintf(sizeof(data.colSeparator), data.colSeparator,
mistachkinfad42082014-07-24 22:13:12 +00004157 SEP_Unit);
mistachkin636bf9f2014-07-19 20:15:16 +00004158 sqlite3_snprintf(sizeof(data.rowSeparator), data.rowSeparator,
mistachkinfad42082014-07-24 22:13:12 +00004159 SEP_Record);
mistachkin636bf9f2014-07-19 20:15:16 +00004160 }else if( strcmp(z,"-separator")==0 || strcmp(z,"-colseparator")==0 ){
4161 sqlite3_snprintf(sizeof(data.colSeparator), data.colSeparator,
4162 "%s",cmdline_option_value(argc,argv,++i));
4163 }else if( strcmp(z,"-rowseparator")==0 ){
4164 sqlite3_snprintf(sizeof(data.rowSeparator), data.rowSeparator,
drh98d312f2012-10-25 15:23:14 +00004165 "%s",cmdline_option_value(argc,argv,++i));
drh6976c212014-07-24 12:09:47 +00004166 }else if( strcmp(z,"-newline")==0 ){
4167 sqlite3_snprintf(sizeof(data.newline), data.newline,
4168 "%s",cmdline_option_value(argc,argv,++i));
drh22fbcb82004-02-01 01:22:50 +00004169 }else if( strcmp(z,"-nullvalue")==0 ){
drh5bb3eb92007-05-04 13:15:55 +00004170 sqlite3_snprintf(sizeof(data.nullvalue), data.nullvalue,
drh98d312f2012-10-25 15:23:14 +00004171 "%s",cmdline_option_value(argc,argv,++i));
drh22fbcb82004-02-01 01:22:50 +00004172 }else if( strcmp(z,"-header")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00004173 data.showHeader = 1;
drh22fbcb82004-02-01 01:22:50 +00004174 }else if( strcmp(z,"-noheader")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00004175 data.showHeader = 0;
drh22fbcb82004-02-01 01:22:50 +00004176 }else if( strcmp(z,"-echo")==0 ){
drhdaffd0e2001-04-11 14:28:42 +00004177 data.echoOn = 1;
drhefbf3b12014-02-28 20:47:24 +00004178 }else if( strcmp(z,"-eqp")==0 ){
4179 data.autoEQP = 1;
shaneh642d8b82010-07-28 16:05:34 +00004180 }else if( strcmp(z,"-stats")==0 ){
4181 data.statsOn = 1;
drhc49f44e2006-10-26 18:15:42 +00004182 }else if( strcmp(z,"-bail")==0 ){
4183 bail_on_error = 1;
drh22fbcb82004-02-01 01:22:50 +00004184 }else if( strcmp(z,"-version")==0 ){
drh9fd301b2011-06-03 13:28:22 +00004185 printf("%s %s\n", sqlite3_libversion(), sqlite3_sourceid());
drh151e3e12006-06-06 12:32:21 +00004186 return 0;
drhc28490c2006-10-26 14:25:58 +00004187 }else if( strcmp(z,"-interactive")==0 ){
4188 stdin_is_interactive = 1;
4189 }else if( strcmp(z,"-batch")==0 ){
4190 stdin_is_interactive = 0;
drh9c88d682010-12-17 14:03:01 +00004191 }else if( strcmp(z,"-heap")==0 ){
4192 i++;
drh7d9f3942013-04-03 01:26:54 +00004193 }else if( strcmp(z,"-mmap")==0 ){
4194 i++;
drha7e61d82011-03-12 17:02:57 +00004195 }else if( strcmp(z,"-vfs")==0 ){
4196 i++;
drh6f25e892011-07-08 17:02:57 +00004197#ifdef SQLITE_ENABLE_VFSTRACE
drh97ae8ff2011-03-16 16:56:29 +00004198 }else if( strcmp(z,"-vfstrace")==0 ){
4199 i++;
drh6f25e892011-07-08 17:02:57 +00004200#endif
4201#ifdef SQLITE_ENABLE_MULTIPLEX
4202 }else if( strcmp(z,"-multiplex")==0 ){
4203 i++;
4204#endif
drhcc3b4f82012-02-07 14:13:50 +00004205 }else if( strcmp(z,"-help")==0 ){
drhe1e38c42003-05-04 18:30:59 +00004206 usage(1);
drhcc3b4f82012-02-07 14:13:50 +00004207 }else if( strcmp(z,"-cmd")==0 ){
4208 if( i==argc-1 ) break;
drh98d312f2012-10-25 15:23:14 +00004209 z = cmdline_option_value(argc,argv,++i);
drhcc3b4f82012-02-07 14:13:50 +00004210 if( z[0]=='.' ){
4211 rc = do_meta_command(z, &data);
drh99b39082013-04-17 12:19:48 +00004212 if( rc && bail_on_error ) return rc==2 ? 0 : rc;
drhcc3b4f82012-02-07 14:13:50 +00004213 }else{
drh05782482013-10-24 15:20:20 +00004214 open_db(&data, 0);
drhcc3b4f82012-02-07 14:13:50 +00004215 rc = shell_exec(data.db, z, shell_callback, &data, &zErrMsg);
4216 if( zErrMsg!=0 ){
4217 fprintf(stderr,"Error: %s\n", zErrMsg);
4218 if( bail_on_error ) return rc!=0 ? rc : 1;
4219 }else if( rc!=0 ){
4220 fprintf(stderr,"Error: unable to process SQL \"%s\"\n", z);
4221 if( bail_on_error ) return rc;
4222 }
4223 }
drh1e5d0e92000-05-31 23:33:17 +00004224 }else{
shane86f5bdb2009-10-24 02:00:07 +00004225 fprintf(stderr,"%s: Error: unknown option: %s\n", Argv0, z);
drhe1e38c42003-05-04 18:30:59 +00004226 fprintf(stderr,"Use -help for a list of options.\n");
drh1e5d0e92000-05-31 23:33:17 +00004227 return 1;
4228 }
4229 }
drh44c2eb12003-04-30 11:38:26 +00004230
drh22fbcb82004-02-01 01:22:50 +00004231 if( zFirstCmd ){
drh44c2eb12003-04-30 11:38:26 +00004232 /* Run just the command that follows the database name
4233 */
drh22fbcb82004-02-01 01:22:50 +00004234 if( zFirstCmd[0]=='.' ){
shane916f9612009-10-23 00:37:15 +00004235 rc = do_meta_command(zFirstCmd, &data);
drh99b39082013-04-17 12:19:48 +00004236 if( rc==2 ) rc = 0;
drh6ff13852001-11-25 13:18:23 +00004237 }else{
drh05782482013-10-24 15:20:20 +00004238 open_db(&data, 0);
shane626a6e42009-10-22 17:30:15 +00004239 rc = shell_exec(data.db, zFirstCmd, shell_callback, &data, &zErrMsg);
shane86f5bdb2009-10-24 02:00:07 +00004240 if( zErrMsg!=0 ){
4241 fprintf(stderr,"Error: %s\n", zErrMsg);
4242 return rc!=0 ? rc : 1;
4243 }else if( rc!=0 ){
4244 fprintf(stderr,"Error: unable to process SQL \"%s\"\n", zFirstCmd);
4245 return rc;
drh6ff13852001-11-25 13:18:23 +00004246 }
drh75897232000-05-29 14:26:00 +00004247 }
4248 }else{
drh44c2eb12003-04-30 11:38:26 +00004249 /* Run commands received from standard input
4250 */
drhc28490c2006-10-26 14:25:58 +00004251 if( stdin_is_interactive ){
drh67505e72002-04-19 12:34:06 +00004252 char *zHome;
4253 char *zHistory = 0;
drh5bb3eb92007-05-04 13:15:55 +00004254 int nHistory;
drh75897232000-05-29 14:26:00 +00004255 printf(
drh743e0032011-12-12 16:51:50 +00004256 "SQLite version %s %.19s\n" /*extra-version-info*/
drh1247aa42014-02-10 19:27:05 +00004257 "Enter \".help\" for usage hints.\n",
drh9fd301b2011-06-03 13:28:22 +00004258 sqlite3_libversion(), sqlite3_sourceid()
drh75897232000-05-29 14:26:00 +00004259 );
drhb3735912014-02-10 16:13:42 +00004260 if( warnInmemoryDb ){
drh1247aa42014-02-10 19:27:05 +00004261 printf("Connected to a ");
mistachkin378d01a2014-03-06 02:15:42 +00004262 printBold("transient in-memory database");
4263 printf(".\nUse \".open FILENAME\" to reopen on a "
drh1247aa42014-02-10 19:27:05 +00004264 "persistent database.\n");
drhb3735912014-02-10 16:13:42 +00004265 }
drh67505e72002-04-19 12:34:06 +00004266 zHome = find_home_dir();
drhea678832008-12-10 19:26:22 +00004267 if( zHome ){
drh4f21c4a2008-12-10 22:15:00 +00004268 nHistory = strlen30(zHome) + 20;
drhea678832008-12-10 19:26:22 +00004269 if( (zHistory = malloc(nHistory))!=0 ){
4270 sqlite3_snprintf(nHistory, zHistory,"%s/.sqlite_history", zHome);
4271 }
drh67505e72002-04-19 12:34:06 +00004272 }
drhaaa21b42014-02-11 14:37:51 +00004273#if defined(HAVE_READLINE)
drh67505e72002-04-19 12:34:06 +00004274 if( zHistory ) read_history(zHistory);
danielk19774af00c62005-01-23 23:43:21 +00004275#endif
drhc28490c2006-10-26 14:25:58 +00004276 rc = process_input(&data, 0);
drh67505e72002-04-19 12:34:06 +00004277 if( zHistory ){
4278 stifle_history(100);
4279 write_history(zHistory);
adamd0a3daa32006-07-28 20:16:14 +00004280 free(zHistory);
drh67505e72002-04-19 12:34:06 +00004281 }
drhdaffd0e2001-04-11 14:28:42 +00004282 }else{
drhc28490c2006-10-26 14:25:58 +00004283 rc = process_input(&data, stdin);
drh75897232000-05-29 14:26:00 +00004284 }
4285 }
drh33048c02001-10-01 14:29:22 +00004286 set_table_name(&data, 0);
drh72af0772010-05-06 20:19:55 +00004287 if( data.db ){
drhe14cd932010-12-08 03:28:17 +00004288 sqlite3_close(data.db);
adamd0a3daa32006-07-28 20:16:14 +00004289 }
drh05782482013-10-24 15:20:20 +00004290 sqlite3_free(data.zFreeOnClose);
drhc28490c2006-10-26 14:25:58 +00004291 return rc;
drh75897232000-05-29 14:26:00 +00004292}