blob: f51ce9a1647750ab8555c623d1f8d7c918ae9c3e [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>
shane18e526c2008-12-10 22:30:24 +000067#define isatty(h) _isatty(h)
drh07901eb2014-02-28 19:37:45 +000068#ifndef access
69# define access(f,m) _access((f),(m))
70#endif
drh67ceaa62012-08-27 21:19:03 +000071#undef popen
drh53371f92013-07-25 17:07:03 +000072#define popen _popen
drh67ceaa62012-08-27 21:19:03 +000073#undef pclose
drh12cd6cf2013-06-29 15:40:22 +000074#define pclose _pclose
adamd2e8464a2006-09-06 21:39:40 +000075#else
drh4328c8b2003-04-26 02:50:11 +000076/* Make sure isatty() has a prototype.
77*/
drhb2acc3b2011-10-13 16:36:29 +000078extern int isatty(int);
drh4328c8b2003-04-26 02:50:11 +000079
drh53371f92013-07-25 17:07:03 +000080/* popen and pclose are not C89 functions and so are sometimes omitted from
81** the <stdio.h> header */
mistachkinf6418892013-08-28 01:54:12 +000082extern FILE *popen(const char*,const char*);
83extern int pclose(FILE*);
84#endif
drh53371f92013-07-25 17:07:03 +000085
chw65d3c132007-11-12 21:09:10 +000086#if defined(_WIN32_WCE)
87/* Windows CE (arm-wince-mingw32ce-gcc) does not provide isatty()
88 * thus we always assume that we have a console. That can be
89 * overridden with the -batch command line option.
90 */
91#define isatty(x) 1
92#endif
93
drhf0693c82011-10-11 20:41:54 +000094/* ctype macros that work with signed characters */
95#define IsSpace(X) isspace((unsigned char)X)
96#define IsDigit(X) isdigit((unsigned char)X)
97#define ToLower(X) (char)tolower((unsigned char)X)
98
drh43408312013-10-30 12:43:36 +000099
100/* True if the timer is enabled */
101static int enableTimer = 0;
102
103/* Return the current wall-clock time */
104static sqlite3_int64 timeOfDay(void){
105 static sqlite3_vfs *clockVfs = 0;
106 sqlite3_int64 t;
107 if( clockVfs==0 ) clockVfs = sqlite3_vfs_find(0);
108 if( clockVfs->iVersion>=1 && clockVfs->xCurrentTimeInt64!=0 ){
109 clockVfs->xCurrentTimeInt64(clockVfs, &t);
110 }else{
111 double r;
112 clockVfs->xCurrentTime(clockVfs, &r);
113 t = (sqlite3_int64)(r*86400000.0);
114 }
115 return t;
116}
117
drhd5d0f642013-02-20 00:54:21 +0000118#if !defined(_WIN32) && !defined(WIN32) && !defined(_WRS_KERNEL) \
119 && !defined(__minux)
drh3b1a9882007-11-02 12:53:03 +0000120#include <sys/time.h>
121#include <sys/resource.h>
122
drhda108222009-02-25 19:07:24 +0000123/* Saved resource information for the beginning of an operation */
drh43408312013-10-30 12:43:36 +0000124static struct rusage sBegin; /* CPU time at start */
125static sqlite3_int64 iBegin; /* Wall-clock time at start */
drhda108222009-02-25 19:07:24 +0000126
drhda108222009-02-25 19:07:24 +0000127/*
128** Begin timing an operation
129*/
130static void beginTimer(void){
131 if( enableTimer ){
132 getrusage(RUSAGE_SELF, &sBegin);
drh43408312013-10-30 12:43:36 +0000133 iBegin = timeOfDay();
drhda108222009-02-25 19:07:24 +0000134 }
135}
136
137/* Return the difference of two time_structs in seconds */
138static double timeDiff(struct timeval *pStart, struct timeval *pEnd){
139 return (pEnd->tv_usec - pStart->tv_usec)*0.000001 +
140 (double)(pEnd->tv_sec - pStart->tv_sec);
141}
142
143/*
144** Print the timing results.
145*/
146static void endTimer(void){
147 if( enableTimer ){
148 struct rusage sEnd;
drh43408312013-10-30 12:43:36 +0000149 sqlite3_int64 iEnd = timeOfDay();
drhda108222009-02-25 19:07:24 +0000150 getrusage(RUSAGE_SELF, &sEnd);
drh43408312013-10-30 12:43:36 +0000151 printf("Run Time: real %.3f user %f sys %f\n",
152 (iEnd - iBegin)*0.001,
drhda108222009-02-25 19:07:24 +0000153 timeDiff(&sBegin.ru_utime, &sEnd.ru_utime),
154 timeDiff(&sBegin.ru_stime, &sEnd.ru_stime));
155 }
156}
shaneb320ccd2009-10-21 03:42:58 +0000157
drhda108222009-02-25 19:07:24 +0000158#define BEGIN_TIMER beginTimer()
159#define END_TIMER endTimer()
160#define HAS_TIMER 1
shaneb320ccd2009-10-21 03:42:58 +0000161
162#elif (defined(_WIN32) || defined(WIN32))
163
164#include <windows.h>
165
166/* Saved resource information for the beginning of an operation */
167static HANDLE hProcess;
168static FILETIME ftKernelBegin;
169static FILETIME ftUserBegin;
drh43408312013-10-30 12:43:36 +0000170static sqlite3_int64 ftWallBegin;
shaneb320ccd2009-10-21 03:42:58 +0000171typedef BOOL (WINAPI *GETPROCTIMES)(HANDLE, LPFILETIME, LPFILETIME, LPFILETIME, LPFILETIME);
172static GETPROCTIMES getProcessTimesAddr = NULL;
173
shaneb320ccd2009-10-21 03:42:58 +0000174/*
175** Check to see if we have timer support. Return 1 if necessary
176** support found (or found previously).
177*/
178static int hasTimer(void){
179 if( getProcessTimesAddr ){
180 return 1;
181 } else {
182 /* GetProcessTimes() isn't supported in WIN95 and some other Windows versions.
183 ** See if the version we are running on has it, and if it does, save off
184 ** a pointer to it and the current process handle.
185 */
186 hProcess = GetCurrentProcess();
187 if( hProcess ){
188 HINSTANCE hinstLib = LoadLibrary(TEXT("Kernel32.dll"));
189 if( NULL != hinstLib ){
190 getProcessTimesAddr = (GETPROCTIMES) GetProcAddress(hinstLib, "GetProcessTimes");
191 if( NULL != getProcessTimesAddr ){
192 return 1;
193 }
194 FreeLibrary(hinstLib);
195 }
196 }
197 }
198 return 0;
199}
200
201/*
202** Begin timing an operation
203*/
204static void beginTimer(void){
205 if( enableTimer && getProcessTimesAddr ){
206 FILETIME ftCreation, ftExit;
207 getProcessTimesAddr(hProcess, &ftCreation, &ftExit, &ftKernelBegin, &ftUserBegin);
drh43408312013-10-30 12:43:36 +0000208 ftWallBegin = timeOfDay();
shaneb320ccd2009-10-21 03:42:58 +0000209 }
210}
211
212/* Return the difference of two FILETIME structs in seconds */
213static double timeDiff(FILETIME *pStart, FILETIME *pEnd){
214 sqlite_int64 i64Start = *((sqlite_int64 *) pStart);
215 sqlite_int64 i64End = *((sqlite_int64 *) pEnd);
216 return (double) ((i64End - i64Start) / 10000000.0);
217}
218
219/*
220** Print the timing results.
221*/
222static void endTimer(void){
223 if( enableTimer && getProcessTimesAddr){
224 FILETIME ftCreation, ftExit, ftKernelEnd, ftUserEnd;
drh43408312013-10-30 12:43:36 +0000225 sqlite3_int64 ftWallEnd = timeOfDay();
shaneb320ccd2009-10-21 03:42:58 +0000226 getProcessTimesAddr(hProcess, &ftCreation, &ftExit, &ftKernelEnd, &ftUserEnd);
drh43408312013-10-30 12:43:36 +0000227 printf("Run Time: real %.3f user %f sys %f\n",
228 (ftWallEnd - ftWallBegin)*0.001,
shaneb320ccd2009-10-21 03:42:58 +0000229 timeDiff(&ftUserBegin, &ftUserEnd),
230 timeDiff(&ftKernelBegin, &ftKernelEnd));
231 }
232}
233
234#define BEGIN_TIMER beginTimer()
235#define END_TIMER endTimer()
236#define HAS_TIMER hasTimer()
237
drhda108222009-02-25 19:07:24 +0000238#else
239#define BEGIN_TIMER
240#define END_TIMER
241#define HAS_TIMER 0
242#endif
243
shanec0688ea2009-03-05 03:48:06 +0000244/*
245** Used to prevent warnings about unused parameters
246*/
247#define UNUSED_PARAMETER(x) (void)(x)
248
drhe91d16b2008-12-08 18:27:31 +0000249/*
drhc49f44e2006-10-26 18:15:42 +0000250** If the following flag is set, then command execution stops
251** at an error if we are not interactive.
252*/
253static int bail_on_error = 0;
254
255/*
drhc28490c2006-10-26 14:25:58 +0000256** Threat stdin as an interactive input if the following variable
257** is true. Otherwise, assume stdin is connected to a file or pipe.
258*/
259static int stdin_is_interactive = 1;
260
261/*
drh4c504392000-10-16 22:06:40 +0000262** The following is the open SQLite database. We make a pointer
263** to this database a static variable so that it can be accessed
264** by the SIGINT handler to interrupt database processing.
265*/
danielk197792f9a1b2004-06-19 09:08:16 +0000266static sqlite3 *db = 0;
drh4c504392000-10-16 22:06:40 +0000267
268/*
drh67505e72002-04-19 12:34:06 +0000269** True if an interrupt (Control-C) has been received.
270*/
drh43617e92006-03-06 20:55:46 +0000271static volatile int seenInterrupt = 0;
drh67505e72002-04-19 12:34:06 +0000272
273/*
persicom7e2dfdd2002-04-18 02:46:52 +0000274** This is the name of our program. It is set in main(), used
275** in a number of other places, mostly for error messages.
276*/
277static char *Argv0;
278
279/*
280** Prompt strings. Initialized in main. Settable with
281** .prompt main continue
282*/
283static char mainPrompt[20]; /* First line prompt. default: "sqlite> "*/
284static char continuePrompt[20]; /* Continuation prompt. default: " ...> " */
285
drhb0603412007-02-28 04:47:26 +0000286/*
287** Write I/O traces to the following stream.
288*/
rsebe0a9092007-07-30 18:24:38 +0000289#ifdef SQLITE_ENABLE_IOTRACE
drhb0603412007-02-28 04:47:26 +0000290static FILE *iotrace = 0;
rsebe0a9092007-07-30 18:24:38 +0000291#endif
drhb0603412007-02-28 04:47:26 +0000292
293/*
294** This routine works like printf in that its first argument is a
295** format string and subsequent arguments are values to be substituted
296** in place of % fields. The result of formatting this string
297** is written to iotrace.
298*/
rsebe0a9092007-07-30 18:24:38 +0000299#ifdef SQLITE_ENABLE_IOTRACE
drhb0603412007-02-28 04:47:26 +0000300static void iotracePrintf(const char *zFormat, ...){
301 va_list ap;
drhf075cd02007-02-28 06:14:25 +0000302 char *z;
drhb0603412007-02-28 04:47:26 +0000303 if( iotrace==0 ) return;
304 va_start(ap, zFormat);
drhf075cd02007-02-28 06:14:25 +0000305 z = sqlite3_vmprintf(zFormat, ap);
drhb0603412007-02-28 04:47:26 +0000306 va_end(ap);
drhf075cd02007-02-28 06:14:25 +0000307 fprintf(iotrace, "%s", z);
308 sqlite3_free(z);
drhb0603412007-02-28 04:47:26 +0000309}
rsebe0a9092007-07-30 18:24:38 +0000310#endif
drhb0603412007-02-28 04:47:26 +0000311
drh44c2eb12003-04-30 11:38:26 +0000312
persicom7e2dfdd2002-04-18 02:46:52 +0000313/*
drh83965662003-04-17 02:54:13 +0000314** Determines if a string is a number of not.
315*/
danielk19772e588c72005-12-09 14:25:08 +0000316static int isNumber(const char *z, int *realnum){
drhc8d74412004-08-31 23:41:26 +0000317 if( *z=='-' || *z=='+' ) z++;
drhf0693c82011-10-11 20:41:54 +0000318 if( !IsDigit(*z) ){
drhc8d74412004-08-31 23:41:26 +0000319 return 0;
320 }
321 z++;
322 if( realnum ) *realnum = 0;
drhf0693c82011-10-11 20:41:54 +0000323 while( IsDigit(*z) ){ z++; }
drhc8d74412004-08-31 23:41:26 +0000324 if( *z=='.' ){
325 z++;
drhf0693c82011-10-11 20:41:54 +0000326 if( !IsDigit(*z) ) return 0;
327 while( IsDigit(*z) ){ z++; }
drhc8d74412004-08-31 23:41:26 +0000328 if( realnum ) *realnum = 1;
329 }
330 if( *z=='e' || *z=='E' ){
331 z++;
332 if( *z=='+' || *z=='-' ) z++;
drhf0693c82011-10-11 20:41:54 +0000333 if( !IsDigit(*z) ) return 0;
334 while( IsDigit(*z) ){ z++; }
drhc8d74412004-08-31 23:41:26 +0000335 if( realnum ) *realnum = 1;
336 }
337 return *z==0;
338}
drh83965662003-04-17 02:54:13 +0000339
340/*
danielk1977bc6ada42004-06-30 08:20:16 +0000341** A global char* and an SQL function to access its current value
342** from within an SQL statement. This program used to use the
343** sqlite_exec_printf() API to substitue a string into an SQL statement.
344** The correct way to do this with sqlite3 is to use the bind API, but
345** since the shell is built around the callback paradigm it would be a lot
346** of work. Instead just use this hack, which is quite harmless.
347*/
348static const char *zShellStatic = 0;
349static void shellstaticFunc(
350 sqlite3_context *context,
351 int argc,
352 sqlite3_value **argv
353){
354 assert( 0==argc );
355 assert( zShellStatic );
shaned87897d2009-01-30 05:40:27 +0000356 UNUSED_PARAMETER(argc);
drh902b9ee2008-12-05 17:17:07 +0000357 UNUSED_PARAMETER(argv);
danielk1977bc6ada42004-06-30 08:20:16 +0000358 sqlite3_result_text(context, zShellStatic, -1, SQLITE_STATIC);
359}
360
361
362/*
drhfeac5f82004-08-01 00:10:45 +0000363** This routine reads a line of text from FILE in, stores
drh8e7e7a22000-05-30 18:45:23 +0000364** the text in memory obtained from malloc() and returns a pointer
365** to the text. NULL is returned at end of file, or if malloc()
366** fails.
367**
drh9f099fd2013-08-06 14:01:46 +0000368** If zLine is not NULL then it is a malloced buffer returned from
369** a previous call to this routine that may be reused.
drh8e7e7a22000-05-30 18:45:23 +0000370*/
drh9f099fd2013-08-06 14:01:46 +0000371static char *local_getline(char *zLine, FILE *in){
372 int nLine = zLine==0 ? 0 : 100;
373 int n = 0;
drh8e7e7a22000-05-30 18:45:23 +0000374
drhb07028f2011-10-14 21:49:18 +0000375 while( 1 ){
drh8e7e7a22000-05-30 18:45:23 +0000376 if( n+100>nLine ){
377 nLine = nLine*2 + 100;
378 zLine = realloc(zLine, nLine);
379 if( zLine==0 ) return 0;
380 }
drhdaffd0e2001-04-11 14:28:42 +0000381 if( fgets(&zLine[n], nLine - n, in)==0 ){
drh8e7e7a22000-05-30 18:45:23 +0000382 if( n==0 ){
383 free(zLine);
384 return 0;
385 }
386 zLine[n] = 0;
drh8e7e7a22000-05-30 18:45:23 +0000387 break;
388 }
drh9f099fd2013-08-06 14:01:46 +0000389 while( zLine[n] ) n++;
390 if( n>0 && zLine[n-1]=='\n' ){
drh8e7e7a22000-05-30 18:45:23 +0000391 n--;
shaneh13b36022009-12-17 21:07:15 +0000392 if( n>0 && zLine[n-1]=='\r' ) n--;
drh8e7e7a22000-05-30 18:45:23 +0000393 zLine[n] = 0;
drhb07028f2011-10-14 21:49:18 +0000394 break;
drh8e7e7a22000-05-30 18:45:23 +0000395 }
396 }
drh8e7e7a22000-05-30 18:45:23 +0000397 return zLine;
398}
399
400/*
drhc28490c2006-10-26 14:25:58 +0000401** Retrieve a single line of input text.
drh8e7e7a22000-05-30 18:45:23 +0000402**
drh9f099fd2013-08-06 14:01:46 +0000403** If in==0 then read from standard input and prompt before each line.
404** If isContinuation is true, then a continuation prompt is appropriate.
405** If isContinuation is zero, then the main prompt should be used.
406**
407** If zPrior is not NULL then it is a buffer from a prior call to this
408** routine that can be reused.
409**
410** The result is stored in space obtained from malloc() and must either
411** be freed by the caller or else passed back into this routine via the
412** zPrior argument for reuse.
drh8e7e7a22000-05-30 18:45:23 +0000413*/
drh9f099fd2013-08-06 14:01:46 +0000414static char *one_input_line(FILE *in, char *zPrior, int isContinuation){
drh8e7e7a22000-05-30 18:45:23 +0000415 char *zPrompt;
416 char *zResult;
drhdaffd0e2001-04-11 14:28:42 +0000417 if( in!=0 ){
drh9f099fd2013-08-06 14:01:46 +0000418 zResult = local_getline(zPrior, in);
drh8e7e7a22000-05-30 18:45:23 +0000419 }else{
drh9f099fd2013-08-06 14:01:46 +0000420 zPrompt = isContinuation ? continuePrompt : mainPrompt;
drhaaa21b42014-02-11 14:37:51 +0000421#if defined(HAVE_READLINE)
drh9f099fd2013-08-06 14:01:46 +0000422 free(zPrior);
423 zResult = readline(zPrompt);
424 if( zResult && *zResult ) add_history(zResult);
425#else
426 printf("%s", zPrompt);
427 fflush(stdout);
428 zResult = local_getline(zPrior, stdin);
danielk19774af00c62005-01-23 23:43:21 +0000429#endif
drh9f099fd2013-08-06 14:01:46 +0000430 }
drh8e7e7a22000-05-30 18:45:23 +0000431 return zResult;
432}
433
persicom7e2dfdd2002-04-18 02:46:52 +0000434struct previous_mode_data {
435 int valid; /* Is there legit data in here? */
436 int mode;
437 int showHeader;
438 int colWidth[100];
439};
drh45e29d82006-11-20 16:21:10 +0000440
drh8e7e7a22000-05-30 18:45:23 +0000441/*
drh75897232000-05-29 14:26:00 +0000442** An pointer to an instance of this structure is passed from
443** the main program to the callback. This is used to communicate
444** state and mode information.
445*/
446struct callback_data {
shane626a6e42009-10-22 17:30:15 +0000447 sqlite3 *db; /* The database */
drhdaffd0e2001-04-11 14:28:42 +0000448 int echoOn; /* True to echo input commands */
drhefbf3b12014-02-28 20:47:24 +0000449 int autoEQP; /* Run EXPLAIN QUERY PLAN prior to seach SQL statement */
shaneh642d8b82010-07-28 16:05:34 +0000450 int statsOn; /* True to display memory stats before each finalize */
drh28bd4bc2000-06-15 15:57:22 +0000451 int cnt; /* Number of records displayed so far */
452 FILE *out; /* Write results here */
drh42f64e52012-04-04 16:56:23 +0000453 FILE *traceOut; /* Output for sqlite3_trace() */
drh2f464a02011-10-13 00:41:49 +0000454 int nErr; /* Number of errors seen */
drh28bd4bc2000-06-15 15:57:22 +0000455 int mode; /* An output mode setting */
drh45e29d82006-11-20 16:21:10 +0000456 int writableSchema; /* True if PRAGMA writable_schema=ON */
drh28bd4bc2000-06-15 15:57:22 +0000457 int showHeader; /* True to show column names in List or Column mode */
drh33048c02001-10-01 14:29:22 +0000458 char *zDestTable; /* Name of destination table when MODE_Insert */
drh28bd4bc2000-06-15 15:57:22 +0000459 char separator[20]; /* Separator character for MODE_List */
drha0c66f52000-07-29 13:20:21 +0000460 int colWidth[100]; /* Requested width of each column when in column mode*/
461 int actualWidth[100]; /* Actual width of each column */
drh83965662003-04-17 02:54:13 +0000462 char nullvalue[20]; /* The text to print when a NULL comes back from
463 ** the database */
persicom7e2dfdd2002-04-18 02:46:52 +0000464 struct previous_mode_data explainPrev;
drh83965662003-04-17 02:54:13 +0000465 /* Holds the mode information just before
466 ** .explain ON */
drh44c2eb12003-04-30 11:38:26 +0000467 char outfile[FILENAME_MAX]; /* Filename for *out */
468 const char *zDbFilename; /* name of the database file */
drh05782482013-10-24 15:20:20 +0000469 char *zFreeOnClose; /* Filename to free when closing */
drha7e61d82011-03-12 17:02:57 +0000470 const char *zVfs; /* Name of VFS to use */
shane626a6e42009-10-22 17:30:15 +0000471 sqlite3_stmt *pStmt; /* Current statement if any. */
drh127f9d72010-02-23 01:47:00 +0000472 FILE *pLog; /* Write log output here */
dana98bf362013-11-13 18:35:01 +0000473 int *aiIndent; /* Array of indents used in MODE_Explain */
474 int nIndent; /* Size of array aiIndent[] */
danc4650bb2013-11-18 08:41:06 +0000475 int iIndent; /* Index of current op in aiIndent[] */
drh75897232000-05-29 14:26:00 +0000476};
477
478/*
479** These are the allowed modes.
480*/
drh967e8b72000-06-21 13:59:10 +0000481#define MODE_Line 0 /* One column per line. Blank line between records */
drh75897232000-05-29 14:26:00 +0000482#define MODE_Column 1 /* One record per line in neat columns */
483#define MODE_List 2 /* One record per line with a separator */
drhe3710332000-09-29 13:30:53 +0000484#define MODE_Semi 3 /* Same as MODE_List but append ";" to each line */
485#define MODE_Html 4 /* Generate an XHTML table */
486#define MODE_Insert 5 /* Generate SQL "insert" statements */
drhfeac5f82004-08-01 00:10:45 +0000487#define MODE_Tcl 6 /* Generate ANSI-C or TCL quoted elements */
drh8e64d1c2004-10-07 00:32:39 +0000488#define MODE_Csv 7 /* Quote strings, numbers are plain */
drh66ce4d02008-02-15 17:38:06 +0000489#define MODE_Explain 8 /* Like MODE_Column, but do not truncate data */
persicom7e2dfdd2002-04-18 02:46:52 +0000490
drh66ce4d02008-02-15 17:38:06 +0000491static const char *modeDescr[] = {
persicom7e2dfdd2002-04-18 02:46:52 +0000492 "line",
493 "column",
494 "list",
495 "semi",
496 "html",
drhfeac5f82004-08-01 00:10:45 +0000497 "insert",
498 "tcl",
drh8e64d1c2004-10-07 00:32:39 +0000499 "csv",
drh66ce4d02008-02-15 17:38:06 +0000500 "explain",
persicom7e2dfdd2002-04-18 02:46:52 +0000501};
drh75897232000-05-29 14:26:00 +0000502
503/*
504** Number of elements in an array
505*/
drh902b9ee2008-12-05 17:17:07 +0000506#define ArraySize(X) (int)(sizeof(X)/sizeof(X[0]))
drh75897232000-05-29 14:26:00 +0000507
508/*
drhea678832008-12-10 19:26:22 +0000509** Compute a string length that is limited to what can be stored in
510** lower 30 bits of a 32-bit signed integer.
511*/
drh4f21c4a2008-12-10 22:15:00 +0000512static int strlen30(const char *z){
drhea678832008-12-10 19:26:22 +0000513 const char *z2 = z;
514 while( *z2 ){ z2++; }
515 return 0x3fffffff & (int)(z2 - z);
516}
517
518/*
drh127f9d72010-02-23 01:47:00 +0000519** A callback for the sqlite3_log() interface.
520*/
521static void shellLog(void *pArg, int iErrCode, const char *zMsg){
522 struct callback_data *p = (struct callback_data*)pArg;
523 if( p->pLog==0 ) return;
524 fprintf(p->pLog, "(%d) %s\n", iErrCode, zMsg);
525 fflush(p->pLog);
526}
527
528/*
shane626a6e42009-10-22 17:30:15 +0000529** Output the given string as a hex-encoded blob (eg. X'1234' )
530*/
531static void output_hex_blob(FILE *out, const void *pBlob, int nBlob){
532 int i;
533 char *zBlob = (char *)pBlob;
534 fprintf(out,"X'");
drhb202d702012-04-24 12:12:57 +0000535 for(i=0; i<nBlob; i++){ fprintf(out,"%02x",zBlob[i]&0xff); }
shane626a6e42009-10-22 17:30:15 +0000536 fprintf(out,"'");
537}
538
539/*
drh28bd4bc2000-06-15 15:57:22 +0000540** Output the given string as a quoted string using SQL quoting conventions.
541*/
542static void output_quoted_string(FILE *out, const char *z){
543 int i;
544 int nSingle = 0;
drh28bd4bc2000-06-15 15:57:22 +0000545 for(i=0; z[i]; i++){
546 if( z[i]=='\'' ) nSingle++;
drh28bd4bc2000-06-15 15:57:22 +0000547 }
548 if( nSingle==0 ){
549 fprintf(out,"'%s'",z);
drh28bd4bc2000-06-15 15:57:22 +0000550 }else{
551 fprintf(out,"'");
552 while( *z ){
553 for(i=0; z[i] && z[i]!='\''; i++){}
554 if( i==0 ){
555 fprintf(out,"''");
556 z++;
557 }else if( z[i]=='\'' ){
558 fprintf(out,"%.*s''",i,z);
559 z += i+1;
560 }else{
drhcd7d2732002-02-26 23:24:26 +0000561 fprintf(out,"%s",z);
drh28bd4bc2000-06-15 15:57:22 +0000562 break;
563 }
564 }
drhcd7d2732002-02-26 23:24:26 +0000565 fprintf(out,"'");
drh28bd4bc2000-06-15 15:57:22 +0000566 }
567}
568
569/*
drhfeac5f82004-08-01 00:10:45 +0000570** Output the given string as a quoted according to C or TCL quoting rules.
571*/
572static void output_c_string(FILE *out, const char *z){
573 unsigned int c;
574 fputc('"', out);
575 while( (c = *(z++))!=0 ){
576 if( c=='\\' ){
577 fputc(c, out);
578 fputc(c, out);
mistachkin585dcb22012-12-04 00:23:43 +0000579 }else if( c=='"' ){
580 fputc('\\', out);
581 fputc('"', out);
drhfeac5f82004-08-01 00:10:45 +0000582 }else if( c=='\t' ){
583 fputc('\\', out);
584 fputc('t', out);
585 }else if( c=='\n' ){
586 fputc('\\', out);
587 fputc('n', out);
588 }else if( c=='\r' ){
589 fputc('\\', out);
590 fputc('r', out);
mistachkinf6418892013-08-28 01:54:12 +0000591 }else if( !isprint(c&0xff) ){
drh0a8640d2005-08-30 20:12:02 +0000592 fprintf(out, "\\%03o", c&0xff);
drhfeac5f82004-08-01 00:10:45 +0000593 }else{
594 fputc(c, out);
595 }
596 }
597 fputc('"', out);
598}
599
600/*
drhc08a4f12000-06-15 16:49:48 +0000601** Output the given string with characters that are special to
602** HTML escaped.
603*/
604static void output_html_string(FILE *out, const char *z){
605 int i;
drhc3d6ba42014-01-13 20:38:35 +0000606 if( z==0 ) z = "";
drhc08a4f12000-06-15 16:49:48 +0000607 while( *z ){
shane43d9cb22009-10-21 14:11:48 +0000608 for(i=0; z[i]
609 && z[i]!='<'
610 && z[i]!='&'
611 && z[i]!='>'
612 && z[i]!='\"'
613 && z[i]!='\'';
614 i++){}
drhc08a4f12000-06-15 16:49:48 +0000615 if( i>0 ){
616 fprintf(out,"%.*s",i,z);
617 }
618 if( z[i]=='<' ){
619 fprintf(out,"&lt;");
620 }else if( z[i]=='&' ){
621 fprintf(out,"&amp;");
shane43d9cb22009-10-21 14:11:48 +0000622 }else if( z[i]=='>' ){
623 fprintf(out,"&gt;");
624 }else if( z[i]=='\"' ){
625 fprintf(out,"&quot;");
626 }else if( z[i]=='\'' ){
627 fprintf(out,"&#39;");
drhc08a4f12000-06-15 16:49:48 +0000628 }else{
629 break;
630 }
631 z += i + 1;
632 }
633}
634
635/*
drhc49f44e2006-10-26 18:15:42 +0000636** If a field contains any character identified by a 1 in the following
637** array, then the string must be quoted for CSV.
638*/
639static const char needCsvQuote[] = {
640 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
641 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
642 1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0,
643 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
644 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
645 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
646 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
647 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1,
648 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
649 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
650 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
651 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
652 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
653 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
654 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
655 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
656};
657
658/*
drh8e64d1c2004-10-07 00:32:39 +0000659** Output a single term of CSV. Actually, p->separator is used for
660** the separator, which may or may not be a comma. p->nullvalue is
drh18f52e02012-01-16 16:56:31 +0000661** the null value. Strings are quoted if necessary.
drh8e64d1c2004-10-07 00:32:39 +0000662*/
663static void output_csv(struct callback_data *p, const char *z, int bSep){
drhc49f44e2006-10-26 18:15:42 +0000664 FILE *out = p->out;
drh8e64d1c2004-10-07 00:32:39 +0000665 if( z==0 ){
drhc49f44e2006-10-26 18:15:42 +0000666 fprintf(out,"%s",p->nullvalue);
drh8e64d1c2004-10-07 00:32:39 +0000667 }else{
drhc49f44e2006-10-26 18:15:42 +0000668 int i;
drh4f21c4a2008-12-10 22:15:00 +0000669 int nSep = strlen30(p->separator);
drhc49f44e2006-10-26 18:15:42 +0000670 for(i=0; z[i]; i++){
drhc85375d2007-12-18 15:41:44 +0000671 if( needCsvQuote[((unsigned char*)z)[i]]
672 || (z[i]==p->separator[0] &&
673 (nSep==1 || memcmp(z, p->separator, nSep)==0)) ){
drhc49f44e2006-10-26 18:15:42 +0000674 i = 0;
675 break;
676 }
677 }
678 if( i==0 ){
679 putc('"', out);
680 for(i=0; z[i]; i++){
681 if( z[i]=='"' ) putc('"', out);
682 putc(z[i], out);
683 }
684 putc('"', out);
685 }else{
686 fprintf(out, "%s", z);
687 }
drh8e64d1c2004-10-07 00:32:39 +0000688 }
689 if( bSep ){
drhd0e77882008-01-14 15:20:08 +0000690 fprintf(p->out, "%s", p->separator);
drh8e64d1c2004-10-07 00:32:39 +0000691 }
692}
693
danielk19774af00c62005-01-23 23:43:21 +0000694#ifdef SIGINT
drh8e64d1c2004-10-07 00:32:39 +0000695/*
drh4c504392000-10-16 22:06:40 +0000696** This routine runs when the user presses Ctrl-C
697*/
698static void interrupt_handler(int NotUsed){
drh902b9ee2008-12-05 17:17:07 +0000699 UNUSED_PARAMETER(NotUsed);
drh43ae8f62014-05-23 12:03:47 +0000700 seenInterrupt++;
701 if( seenInterrupt>2 ) exit(1);
danielk19776f8a5032004-05-10 10:34:51 +0000702 if( db ) sqlite3_interrupt(db);
drh4c504392000-10-16 22:06:40 +0000703}
danielk19774af00c62005-01-23 23:43:21 +0000704#endif
drh4c504392000-10-16 22:06:40 +0000705
706/*
shane626a6e42009-10-22 17:30:15 +0000707** This is the callback routine that the shell
drh75897232000-05-29 14:26:00 +0000708** invokes for each row of a query result.
709*/
shane626a6e42009-10-22 17:30:15 +0000710static int shell_callback(void *pArg, int nArg, char **azArg, char **azCol, int *aiType){
drh75897232000-05-29 14:26:00 +0000711 int i;
712 struct callback_data *p = (struct callback_data*)pArg;
shaneb9fc17d2009-10-22 21:23:35 +0000713
drh75897232000-05-29 14:26:00 +0000714 switch( p->mode ){
715 case MODE_Line: {
drhe3710332000-09-29 13:30:53 +0000716 int w = 5;
drh6a535342001-10-19 16:44:56 +0000717 if( azArg==0 ) break;
drhe3710332000-09-29 13:30:53 +0000718 for(i=0; i<nArg; i++){
drh4f21c4a2008-12-10 22:15:00 +0000719 int len = strlen30(azCol[i] ? azCol[i] : "");
drhe3710332000-09-29 13:30:53 +0000720 if( len>w ) w = len;
721 }
drh75897232000-05-29 14:26:00 +0000722 if( p->cnt++>0 ) fprintf(p->out,"\n");
723 for(i=0; i<nArg; i++){
drh2cc55692006-06-27 20:39:04 +0000724 fprintf(p->out,"%*s = %s\n", w, azCol[i],
drha69d9162003-04-17 22:57:53 +0000725 azArg[i] ? azArg[i] : p->nullvalue);
drh75897232000-05-29 14:26:00 +0000726 }
727 break;
728 }
danielk19770d78bae2008-01-03 07:09:48 +0000729 case MODE_Explain:
drh75897232000-05-29 14:26:00 +0000730 case MODE_Column: {
drha0c66f52000-07-29 13:20:21 +0000731 if( p->cnt++==0 ){
drh75897232000-05-29 14:26:00 +0000732 for(i=0; i<nArg; i++){
drha0c66f52000-07-29 13:20:21 +0000733 int w, n;
734 if( i<ArraySize(p->colWidth) ){
danielk19770d78bae2008-01-03 07:09:48 +0000735 w = p->colWidth[i];
drh75897232000-05-29 14:26:00 +0000736 }else{
danielk19770d78bae2008-01-03 07:09:48 +0000737 w = 0;
drh75897232000-05-29 14:26:00 +0000738 }
drh078b1fd2012-09-21 13:40:02 +0000739 if( w==0 ){
drh4f21c4a2008-12-10 22:15:00 +0000740 w = strlen30(azCol[i] ? azCol[i] : "");
drha0c66f52000-07-29 13:20:21 +0000741 if( w<10 ) w = 10;
drh4f21c4a2008-12-10 22:15:00 +0000742 n = strlen30(azArg && azArg[i] ? azArg[i] : p->nullvalue);
drha0c66f52000-07-29 13:20:21 +0000743 if( w<n ) w = n;
744 }
745 if( i<ArraySize(p->actualWidth) ){
persicom1d0b8722002-04-18 02:53:04 +0000746 p->actualWidth[i] = w;
drha0c66f52000-07-29 13:20:21 +0000747 }
748 if( p->showHeader ){
drh078b1fd2012-09-21 13:40:02 +0000749 if( w<0 ){
750 fprintf(p->out,"%*.*s%s",-w,-w,azCol[i], i==nArg-1 ? "\n": " ");
751 }else{
752 fprintf(p->out,"%-*.*s%s",w,w,azCol[i], i==nArg-1 ? "\n": " ");
753 }
drha0c66f52000-07-29 13:20:21 +0000754 }
755 }
756 if( p->showHeader ){
757 for(i=0; i<nArg; i++){
758 int w;
759 if( i<ArraySize(p->actualWidth) ){
760 w = p->actualWidth[i];
drh078b1fd2012-09-21 13:40:02 +0000761 if( w<0 ) w = -w;
drha0c66f52000-07-29 13:20:21 +0000762 }else{
763 w = 10;
764 }
765 fprintf(p->out,"%-*.*s%s",w,w,"-----------------------------------"
766 "----------------------------------------------------------",
767 i==nArg-1 ? "\n": " ");
768 }
drh75897232000-05-29 14:26:00 +0000769 }
770 }
drh6a535342001-10-19 16:44:56 +0000771 if( azArg==0 ) break;
drh75897232000-05-29 14:26:00 +0000772 for(i=0; i<nArg; i++){
773 int w;
drha0c66f52000-07-29 13:20:21 +0000774 if( i<ArraySize(p->actualWidth) ){
775 w = p->actualWidth[i];
drh75897232000-05-29 14:26:00 +0000776 }else{
777 w = 10;
778 }
dana98bf362013-11-13 18:35:01 +0000779 if( p->mode==MODE_Explain && azArg[i] && strlen30(azArg[i])>w ){
drh4f21c4a2008-12-10 22:15:00 +0000780 w = strlen30(azArg[i]);
danielk19770d78bae2008-01-03 07:09:48 +0000781 }
dana98bf362013-11-13 18:35:01 +0000782 if( i==1 && p->aiIndent && p->pStmt ){
danc4650bb2013-11-18 08:41:06 +0000783 if( p->iIndent<p->nIndent ){
784 fprintf(p->out, "%*.s", p->aiIndent[p->iIndent], "");
dana98bf362013-11-13 18:35:01 +0000785 }
danc4650bb2013-11-18 08:41:06 +0000786 p->iIndent++;
dana98bf362013-11-13 18:35:01 +0000787 }
drh078b1fd2012-09-21 13:40:02 +0000788 if( w<0 ){
789 fprintf(p->out,"%*.*s%s",-w,-w,
790 azArg[i] ? azArg[i] : p->nullvalue, i==nArg-1 ? "\n": " ");
791 }else{
792 fprintf(p->out,"%-*.*s%s",w,w,
793 azArg[i] ? azArg[i] : p->nullvalue, i==nArg-1 ? "\n": " ");
794 }
drh75897232000-05-29 14:26:00 +0000795 }
796 break;
797 }
drhe3710332000-09-29 13:30:53 +0000798 case MODE_Semi:
drh75897232000-05-29 14:26:00 +0000799 case MODE_List: {
800 if( p->cnt++==0 && p->showHeader ){
801 for(i=0; i<nArg; i++){
802 fprintf(p->out,"%s%s",azCol[i], i==nArg-1 ? "\n" : p->separator);
803 }
804 }
drh6a535342001-10-19 16:44:56 +0000805 if( azArg==0 ) break;
drh75897232000-05-29 14:26:00 +0000806 for(i=0; i<nArg; i++){
drh4c653a02000-06-07 01:27:47 +0000807 char *z = azArg[i];
persicom7e2dfdd2002-04-18 02:46:52 +0000808 if( z==0 ) z = p->nullvalue;
drh71172c52002-01-24 00:00:21 +0000809 fprintf(p->out, "%s", z);
drhe3710332000-09-29 13:30:53 +0000810 if( i<nArg-1 ){
811 fprintf(p->out, "%s", p->separator);
812 }else if( p->mode==MODE_Semi ){
813 fprintf(p->out, ";\n");
814 }else{
815 fprintf(p->out, "\n");
816 }
drh75897232000-05-29 14:26:00 +0000817 }
818 break;
819 }
drh1e5d0e92000-05-31 23:33:17 +0000820 case MODE_Html: {
821 if( p->cnt++==0 && p->showHeader ){
mihailim57c591a2008-06-23 21:26:05 +0000822 fprintf(p->out,"<TR>");
drh1e5d0e92000-05-31 23:33:17 +0000823 for(i=0; i<nArg; i++){
shane43d9cb22009-10-21 14:11:48 +0000824 fprintf(p->out,"<TH>");
825 output_html_string(p->out, azCol[i]);
826 fprintf(p->out,"</TH>\n");
drh1e5d0e92000-05-31 23:33:17 +0000827 }
mihailim57c591a2008-06-23 21:26:05 +0000828 fprintf(p->out,"</TR>\n");
drh1e5d0e92000-05-31 23:33:17 +0000829 }
drh6a535342001-10-19 16:44:56 +0000830 if( azArg==0 ) break;
mihailim57c591a2008-06-23 21:26:05 +0000831 fprintf(p->out,"<TR>");
drh1e5d0e92000-05-31 23:33:17 +0000832 for(i=0; i<nArg; i++){
mihailim57c591a2008-06-23 21:26:05 +0000833 fprintf(p->out,"<TD>");
persicom7e2dfdd2002-04-18 02:46:52 +0000834 output_html_string(p->out, azArg[i] ? azArg[i] : p->nullvalue);
mihailim57c591a2008-06-23 21:26:05 +0000835 fprintf(p->out,"</TD>\n");
drh1e5d0e92000-05-31 23:33:17 +0000836 }
mihailim57c591a2008-06-23 21:26:05 +0000837 fprintf(p->out,"</TR>\n");
drh1e5d0e92000-05-31 23:33:17 +0000838 break;
839 }
drhfeac5f82004-08-01 00:10:45 +0000840 case MODE_Tcl: {
841 if( p->cnt++==0 && p->showHeader ){
842 for(i=0; i<nArg; i++){
drh2cc55692006-06-27 20:39:04 +0000843 output_c_string(p->out,azCol[i] ? azCol[i] : "");
mistachkin585dcb22012-12-04 00:23:43 +0000844 if(i<nArg-1) fprintf(p->out, "%s", p->separator);
drhfeac5f82004-08-01 00:10:45 +0000845 }
846 fprintf(p->out,"\n");
847 }
848 if( azArg==0 ) break;
849 for(i=0; i<nArg; i++){
850 output_c_string(p->out, azArg[i] ? azArg[i] : p->nullvalue);
mistachkin585dcb22012-12-04 00:23:43 +0000851 if(i<nArg-1) fprintf(p->out, "%s", p->separator);
drhfeac5f82004-08-01 00:10:45 +0000852 }
853 fprintf(p->out,"\n");
854 break;
855 }
drh8e64d1c2004-10-07 00:32:39 +0000856 case MODE_Csv: {
857 if( p->cnt++==0 && p->showHeader ){
858 for(i=0; i<nArg; i++){
drh2cc55692006-06-27 20:39:04 +0000859 output_csv(p, azCol[i] ? azCol[i] : "", i<nArg-1);
drh8e64d1c2004-10-07 00:32:39 +0000860 }
861 fprintf(p->out,"\n");
862 }
863 if( azArg==0 ) break;
864 for(i=0; i<nArg; i++){
865 output_csv(p, azArg[i], i<nArg-1);
866 }
867 fprintf(p->out,"\n");
868 break;
869 }
drh28bd4bc2000-06-15 15:57:22 +0000870 case MODE_Insert: {
shaneb9fc17d2009-10-22 21:23:35 +0000871 p->cnt++;
drh6a535342001-10-19 16:44:56 +0000872 if( azArg==0 ) break;
drh33048c02001-10-01 14:29:22 +0000873 fprintf(p->out,"INSERT INTO %s VALUES(",p->zDestTable);
drh28bd4bc2000-06-15 15:57:22 +0000874 for(i=0; i<nArg; i++){
875 char *zSep = i>0 ? ",": "";
shanead6b8d02009-10-22 18:12:58 +0000876 if( (azArg[i]==0) || (aiType && aiType[i]==SQLITE_NULL) ){
drh28bd4bc2000-06-15 15:57:22 +0000877 fprintf(p->out,"%sNULL",zSep);
shanead6b8d02009-10-22 18:12:58 +0000878 }else if( aiType && aiType[i]==SQLITE_TEXT ){
879 if( zSep[0] ) fprintf(p->out,"%s",zSep);
880 output_quoted_string(p->out, azArg[i]);
881 }else if( aiType && (aiType[i]==SQLITE_INTEGER || aiType[i]==SQLITE_FLOAT) ){
882 fprintf(p->out,"%s%s",zSep, azArg[i]);
shane626a6e42009-10-22 17:30:15 +0000883 }else if( aiType && aiType[i]==SQLITE_BLOB && p->pStmt ){
884 const void *pBlob = sqlite3_column_blob(p->pStmt, i);
885 int nBlob = sqlite3_column_bytes(p->pStmt, i);
886 if( zSep[0] ) fprintf(p->out,"%s",zSep);
887 output_hex_blob(p->out, pBlob, nBlob);
drhc8d74412004-08-31 23:41:26 +0000888 }else if( isNumber(azArg[i], 0) ){
drh28bd4bc2000-06-15 15:57:22 +0000889 fprintf(p->out,"%s%s",zSep, azArg[i]);
890 }else{
891 if( zSep[0] ) fprintf(p->out,"%s",zSep);
892 output_quoted_string(p->out, azArg[i]);
893 }
894 }
895 fprintf(p->out,");\n");
drh6a535342001-10-19 16:44:56 +0000896 break;
drh28bd4bc2000-06-15 15:57:22 +0000897 }
persicom1d0b8722002-04-18 02:53:04 +0000898 }
drh75897232000-05-29 14:26:00 +0000899 return 0;
900}
901
902/*
shane626a6e42009-10-22 17:30:15 +0000903** This is the callback routine that the SQLite library
904** invokes for each row of a query result.
905*/
906static int callback(void *pArg, int nArg, char **azArg, char **azCol){
907 /* since we don't have type info, call the shell_callback with a NULL value */
908 return shell_callback(pArg, nArg, azArg, azCol, NULL);
909}
910
911/*
drh33048c02001-10-01 14:29:22 +0000912** Set the destination table field of the callback_data structure to
913** the name of the table given. Escape any quote characters in the
914** table name.
915*/
916static void set_table_name(struct callback_data *p, const char *zName){
917 int i, n;
918 int needQuote;
919 char *z;
920
921 if( p->zDestTable ){
922 free(p->zDestTable);
923 p->zDestTable = 0;
924 }
925 if( zName==0 ) return;
drh4c755c02004-08-08 20:22:17 +0000926 needQuote = !isalpha((unsigned char)*zName) && *zName!='_';
drh33048c02001-10-01 14:29:22 +0000927 for(i=n=0; zName[i]; i++, n++){
drh4c755c02004-08-08 20:22:17 +0000928 if( !isalnum((unsigned char)zName[i]) && zName[i]!='_' ){
drh33048c02001-10-01 14:29:22 +0000929 needQuote = 1;
930 if( zName[i]=='\'' ) n++;
931 }
932 }
933 if( needQuote ) n += 2;
934 z = p->zDestTable = malloc( n+1 );
935 if( z==0 ){
shane86f5bdb2009-10-24 02:00:07 +0000936 fprintf(stderr,"Error: out of memory\n");
drh33048c02001-10-01 14:29:22 +0000937 exit(1);
938 }
939 n = 0;
940 if( needQuote ) z[n++] = '\'';
941 for(i=0; zName[i]; i++){
942 z[n++] = zName[i];
943 if( zName[i]=='\'' ) z[n++] = '\'';
944 }
945 if( needQuote ) z[n++] = '\'';
946 z[n] = 0;
947}
948
danielk19772a02e332004-06-05 08:04:36 +0000949/* zIn is either a pointer to a NULL-terminated string in memory obtained
950** from malloc(), or a NULL pointer. The string pointed to by zAppend is
951** added to zIn, and the result returned in memory obtained from malloc().
952** zIn, if it was not NULL, is freed.
953**
954** If the third argument, quote, is not '\0', then it is used as a
955** quote character for zAppend.
956*/
drhc28490c2006-10-26 14:25:58 +0000957static char *appendText(char *zIn, char const *zAppend, char quote){
danielk19772a02e332004-06-05 08:04:36 +0000958 int len;
959 int i;
drh4f21c4a2008-12-10 22:15:00 +0000960 int nAppend = strlen30(zAppend);
961 int nIn = (zIn?strlen30(zIn):0);
danielk19772a02e332004-06-05 08:04:36 +0000962
963 len = nAppend+nIn+1;
964 if( quote ){
965 len += 2;
966 for(i=0; i<nAppend; i++){
967 if( zAppend[i]==quote ) len++;
968 }
969 }
970
971 zIn = (char *)realloc(zIn, len);
972 if( !zIn ){
973 return 0;
974 }
975
976 if( quote ){
977 char *zCsr = &zIn[nIn];
978 *zCsr++ = quote;
979 for(i=0; i<nAppend; i++){
980 *zCsr++ = zAppend[i];
981 if( zAppend[i]==quote ) *zCsr++ = quote;
982 }
983 *zCsr++ = quote;
984 *zCsr++ = '\0';
985 assert( (zCsr-zIn)==len );
986 }else{
987 memcpy(&zIn[nIn], zAppend, nAppend);
988 zIn[len-1] = '\0';
989 }
990
991 return zIn;
992}
993
drhdd3d4592004-08-30 01:54:05 +0000994
995/*
drhb21a8e42012-01-28 21:08:51 +0000996** Execute a query statement that will generate SQL output. Print
997** the result columns, comma-separated, on a line and then add a
998** semicolon terminator to the end of that line.
drh45e29d82006-11-20 16:21:10 +0000999**
drhb21a8e42012-01-28 21:08:51 +00001000** If the number of columns is 1 and that column contains text "--"
1001** then write the semicolon on a separate line. That way, if a
1002** "--" comment occurs at the end of the statement, the comment
1003** won't consume the semicolon terminator.
drhdd3d4592004-08-30 01:54:05 +00001004*/
drh157e29a2009-05-21 15:15:00 +00001005static int run_table_dump_query(
drh2f464a02011-10-13 00:41:49 +00001006 struct callback_data *p, /* Query context */
1007 const char *zSelect, /* SELECT statement to extract content */
1008 const char *zFirstRow /* Print before first row, if not NULL */
drh157e29a2009-05-21 15:15:00 +00001009){
drhdd3d4592004-08-30 01:54:05 +00001010 sqlite3_stmt *pSelect;
1011 int rc;
drhb21a8e42012-01-28 21:08:51 +00001012 int nResult;
1013 int i;
1014 const char *z;
drhc7181902014-02-27 15:04:13 +00001015 rc = sqlite3_prepare_v2(p->db, zSelect, -1, &pSelect, 0);
drhdd3d4592004-08-30 01:54:05 +00001016 if( rc!=SQLITE_OK || !pSelect ){
drh2f464a02011-10-13 00:41:49 +00001017 fprintf(p->out, "/**** ERROR: (%d) %s *****/\n", rc, sqlite3_errmsg(p->db));
drh4384e982013-10-01 15:30:05 +00001018 if( (rc&0xff)!=SQLITE_CORRUPT ) p->nErr++;
drhdd3d4592004-08-30 01:54:05 +00001019 return rc;
1020 }
1021 rc = sqlite3_step(pSelect);
drhb21a8e42012-01-28 21:08:51 +00001022 nResult = sqlite3_column_count(pSelect);
drhdd3d4592004-08-30 01:54:05 +00001023 while( rc==SQLITE_ROW ){
drh157e29a2009-05-21 15:15:00 +00001024 if( zFirstRow ){
drh2f464a02011-10-13 00:41:49 +00001025 fprintf(p->out, "%s", zFirstRow);
drh157e29a2009-05-21 15:15:00 +00001026 zFirstRow = 0;
1027 }
drhb21a8e42012-01-28 21:08:51 +00001028 z = (const char*)sqlite3_column_text(pSelect, 0);
1029 fprintf(p->out, "%s", z);
1030 for(i=1; i<nResult; i++){
1031 fprintf(p->out, ",%s", sqlite3_column_text(pSelect, i));
1032 }
1033 if( z==0 ) z = "";
1034 while( z[0] && (z[0]!='-' || z[1]!='-') ) z++;
1035 if( z[0] ){
1036 fprintf(p->out, "\n;\n");
1037 }else{
1038 fprintf(p->out, ";\n");
1039 }
drhdd3d4592004-08-30 01:54:05 +00001040 rc = sqlite3_step(pSelect);
1041 }
drh2f464a02011-10-13 00:41:49 +00001042 rc = sqlite3_finalize(pSelect);
1043 if( rc!=SQLITE_OK ){
1044 fprintf(p->out, "/**** ERROR: (%d) %s *****/\n", rc, sqlite3_errmsg(p->db));
drh4384e982013-10-01 15:30:05 +00001045 if( (rc&0xff)!=SQLITE_CORRUPT ) p->nErr++;
drh2f464a02011-10-13 00:41:49 +00001046 }
1047 return rc;
drhdd3d4592004-08-30 01:54:05 +00001048}
1049
shane626a6e42009-10-22 17:30:15 +00001050/*
1051** Allocate space and save off current error string.
1052*/
1053static char *save_err_msg(
1054 sqlite3 *db /* Database to query */
1055){
1056 int nErrMsg = 1+strlen30(sqlite3_errmsg(db));
1057 char *zErrMsg = sqlite3_malloc(nErrMsg);
1058 if( zErrMsg ){
1059 memcpy(zErrMsg, sqlite3_errmsg(db), nErrMsg);
1060 }
1061 return zErrMsg;
1062}
1063
1064/*
shaneh642d8b82010-07-28 16:05:34 +00001065** Display memory stats.
1066*/
1067static int display_stats(
1068 sqlite3 *db, /* Database to query */
1069 struct callback_data *pArg, /* Pointer to struct callback_data */
1070 int bReset /* True to reset the stats */
1071){
1072 int iCur;
1073 int iHiwtr;
1074
1075 if( pArg && pArg->out ){
1076
1077 iHiwtr = iCur = -1;
1078 sqlite3_status(SQLITE_STATUS_MEMORY_USED, &iCur, &iHiwtr, bReset);
drh29dfbe32010-07-28 17:01:24 +00001079 fprintf(pArg->out, "Memory Used: %d (max %d) bytes\n", iCur, iHiwtr);
shaneh642d8b82010-07-28 16:05:34 +00001080 iHiwtr = iCur = -1;
1081 sqlite3_status(SQLITE_STATUS_MALLOC_COUNT, &iCur, &iHiwtr, bReset);
drh2a58e9c2010-12-21 21:28:38 +00001082 fprintf(pArg->out, "Number of Outstanding Allocations: %d (max %d)\n", iCur, iHiwtr);
shaneh642d8b82010-07-28 16:05:34 +00001083/*
1084** Not currently used by the CLI.
1085** iHiwtr = iCur = -1;
1086** sqlite3_status(SQLITE_STATUS_PAGECACHE_USED, &iCur, &iHiwtr, bReset);
1087** fprintf(pArg->out, "Number of Pcache Pages Used: %d (max %d) pages\n", iCur, iHiwtr);
1088*/
1089 iHiwtr = iCur = -1;
1090 sqlite3_status(SQLITE_STATUS_PAGECACHE_OVERFLOW, &iCur, &iHiwtr, bReset);
1091 fprintf(pArg->out, "Number of Pcache Overflow Bytes: %d (max %d) bytes\n", iCur, iHiwtr);
1092/*
1093** Not currently used by the CLI.
1094** iHiwtr = iCur = -1;
1095** sqlite3_status(SQLITE_STATUS_SCRATCH_USED, &iCur, &iHiwtr, bReset);
1096** fprintf(pArg->out, "Number of Scratch Allocations Used: %d (max %d)\n", iCur, iHiwtr);
1097*/
1098 iHiwtr = iCur = -1;
1099 sqlite3_status(SQLITE_STATUS_SCRATCH_OVERFLOW, &iCur, &iHiwtr, bReset);
1100 fprintf(pArg->out, "Number of Scratch Overflow Bytes: %d (max %d) bytes\n", iCur, iHiwtr);
1101 iHiwtr = iCur = -1;
1102 sqlite3_status(SQLITE_STATUS_MALLOC_SIZE, &iCur, &iHiwtr, bReset);
1103 fprintf(pArg->out, "Largest Allocation: %d bytes\n", iHiwtr);
1104 iHiwtr = iCur = -1;
1105 sqlite3_status(SQLITE_STATUS_PAGECACHE_SIZE, &iCur, &iHiwtr, bReset);
1106 fprintf(pArg->out, "Largest Pcache Allocation: %d bytes\n", iHiwtr);
1107 iHiwtr = iCur = -1;
1108 sqlite3_status(SQLITE_STATUS_SCRATCH_SIZE, &iCur, &iHiwtr, bReset);
1109 fprintf(pArg->out, "Largest Scratch Allocation: %d bytes\n", iHiwtr);
1110#ifdef YYTRACKMAXSTACKDEPTH
1111 iHiwtr = iCur = -1;
1112 sqlite3_status(SQLITE_STATUS_PARSER_STACK, &iCur, &iHiwtr, bReset);
1113 fprintf(pArg->out, "Deepest Parser Stack: %d (max %d)\n", iCur, iHiwtr);
1114#endif
1115 }
1116
1117 if( pArg && pArg->out && db ){
1118 iHiwtr = iCur = -1;
1119 sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_USED, &iCur, &iHiwtr, bReset);
1120 fprintf(pArg->out, "Lookaside Slots Used: %d (max %d)\n", iCur, iHiwtr);
drh2a58e9c2010-12-21 21:28:38 +00001121 sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_HIT, &iCur, &iHiwtr, bReset);
1122 fprintf(pArg->out, "Successful lookaside attempts: %d\n", iHiwtr);
1123 sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_MISS_SIZE, &iCur, &iHiwtr, bReset);
1124 fprintf(pArg->out, "Lookaside failures due to size: %d\n", iHiwtr);
1125 sqlite3_db_status(db, SQLITE_DBSTATUS_LOOKASIDE_MISS_FULL, &iCur, &iHiwtr, bReset);
1126 fprintf(pArg->out, "Lookaside failures due to OOM: %d\n", iHiwtr);
shaneh642d8b82010-07-28 16:05:34 +00001127 iHiwtr = iCur = -1;
1128 sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_USED, &iCur, &iHiwtr, bReset);
drhc78e6e42011-09-23 18:58:23 +00001129 fprintf(pArg->out, "Pager Heap Usage: %d bytes\n", iCur); iHiwtr = iCur = -1;
1130 sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_HIT, &iCur, &iHiwtr, 1);
1131 fprintf(pArg->out, "Page cache hits: %d\n", iCur);
1132 iHiwtr = iCur = -1;
1133 sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_MISS, &iCur, &iHiwtr, 1);
1134 fprintf(pArg->out, "Page cache misses: %d\n", iCur);
shaneh642d8b82010-07-28 16:05:34 +00001135 iHiwtr = iCur = -1;
drhfbbcd5d2012-03-24 20:09:33 +00001136 sqlite3_db_status(db, SQLITE_DBSTATUS_CACHE_WRITE, &iCur, &iHiwtr, 1);
1137 fprintf(pArg->out, "Page cache writes: %d\n", iCur);
1138 iHiwtr = iCur = -1;
shaneh642d8b82010-07-28 16:05:34 +00001139 sqlite3_db_status(db, SQLITE_DBSTATUS_SCHEMA_USED, &iCur, &iHiwtr, bReset);
1140 fprintf(pArg->out, "Schema Heap Usage: %d bytes\n", iCur);
1141 iHiwtr = iCur = -1;
1142 sqlite3_db_status(db, SQLITE_DBSTATUS_STMT_USED, &iCur, &iHiwtr, bReset);
1143 fprintf(pArg->out, "Statement Heap/Lookaside Usage: %d bytes\n", iCur);
1144 }
1145
1146 if( pArg && pArg->out && db && pArg->pStmt ){
1147 iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_FULLSCAN_STEP, bReset);
1148 fprintf(pArg->out, "Fullscan Steps: %d\n", iCur);
1149 iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_SORT, bReset);
1150 fprintf(pArg->out, "Sort Operations: %d\n", iCur);
1151 iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_AUTOINDEX, bReset);
1152 fprintf(pArg->out, "Autoindex Inserts: %d\n", iCur);
drhbf159fa2013-06-25 22:01:22 +00001153 iCur = sqlite3_stmt_status(pArg->pStmt, SQLITE_STMTSTATUS_VM_STEP, bReset);
1154 fprintf(pArg->out, "Virtual Machine Steps: %d\n", iCur);
shaneh642d8b82010-07-28 16:05:34 +00001155 }
1156
1157 return 0;
1158}
1159
1160/*
dana98bf362013-11-13 18:35:01 +00001161** Parameter azArray points to a zero-terminated array of strings. zStr
1162** points to a single nul-terminated string. Return non-zero if zStr
1163** is equal, according to strcmp(), to any of the strings in the array.
1164** Otherwise, return zero.
1165*/
1166static int str_in_array(const char *zStr, const char **azArray){
1167 int i;
1168 for(i=0; azArray[i]; i++){
1169 if( 0==strcmp(zStr, azArray[i]) ) return 1;
1170 }
1171 return 0;
1172}
1173
1174/*
1175** If compiled statement pSql appears to be an EXPLAIN statement, allocate
1176** and populate the callback_data.aiIndent[] array with the number of
1177** spaces each opcode should be indented before it is output.
1178**
1179** The indenting rules are:
1180**
1181** * For each "Next", "Prev", "VNext" or "VPrev" instruction, indent
1182** all opcodes that occur between the p2 jump destination and the opcode
1183** itself by 2 spaces.
1184**
drh01752bc2013-11-14 23:59:33 +00001185** * For each "Goto", if the jump destination is earlier in the program
1186** and ends on one of:
drhe73f0592014-01-21 22:25:45 +00001187** Yield SeekGt SeekLt RowSetRead Rewind
drhfe705102014-03-06 13:38:37 +00001188** or if the P1 parameter is one instead of zero,
drh01752bc2013-11-14 23:59:33 +00001189** then indent all opcodes between the earlier instruction
drhd2447442013-11-13 19:01:41 +00001190** and "Goto" by 2 spaces.
dana98bf362013-11-13 18:35:01 +00001191*/
1192static void explain_data_prepare(struct callback_data *p, sqlite3_stmt *pSql){
1193 const char *zSql; /* The text of the SQL statement */
1194 const char *z; /* Used to check if this is an EXPLAIN */
1195 int *abYield = 0; /* True if op is an OP_Yield */
1196 int nAlloc = 0; /* Allocated size of p->aiIndent[], abYield */
danc4650bb2013-11-18 08:41:06 +00001197 int iOp; /* Index of operation in p->aiIndent[] */
dana98bf362013-11-13 18:35:01 +00001198
drh8ad0de32014-03-20 18:45:27 +00001199 const char *azNext[] = { "Next", "Prev", "VPrev", "VNext", "SorterNext",
1200 "NextIfOpen", "PrevIfOpen", 0 };
drhe73f0592014-01-21 22:25:45 +00001201 const char *azYield[] = { "Yield", "SeekLt", "SeekGt", "RowSetRead", "Rewind", 0 };
dana98bf362013-11-13 18:35:01 +00001202 const char *azGoto[] = { "Goto", 0 };
1203
1204 /* Try to figure out if this is really an EXPLAIN statement. If this
1205 ** cannot be verified, return early. */
1206 zSql = sqlite3_sql(pSql);
1207 if( zSql==0 ) return;
1208 for(z=zSql; *z==' ' || *z=='\t' || *z=='\n' || *z=='\f' || *z=='\r'; z++);
1209 if( sqlite3_strnicmp(z, "explain", 7) ) return;
1210
1211 for(iOp=0; SQLITE_ROW==sqlite3_step(pSql); iOp++){
1212 int i;
danc4650bb2013-11-18 08:41:06 +00001213 int iAddr = sqlite3_column_int(pSql, 0);
dana98bf362013-11-13 18:35:01 +00001214 const char *zOp = (const char*)sqlite3_column_text(pSql, 1);
danc4650bb2013-11-18 08:41:06 +00001215
1216 /* Set p2 to the P2 field of the current opcode. Then, assuming that
1217 ** p2 is an instruction address, set variable p2op to the index of that
1218 ** instruction in the aiIndent[] array. p2 and p2op may be different if
1219 ** the current instruction is part of a sub-program generated by an
1220 ** SQL trigger or foreign key. */
dana98bf362013-11-13 18:35:01 +00001221 int p2 = sqlite3_column_int(pSql, 3);
danc4650bb2013-11-18 08:41:06 +00001222 int p2op = (p2 + (iOp-iAddr));
dana98bf362013-11-13 18:35:01 +00001223
1224 /* Grow the p->aiIndent array as required */
1225 if( iOp>=nAlloc ){
1226 nAlloc += 100;
1227 p->aiIndent = (int*)sqlite3_realloc(p->aiIndent, nAlloc*sizeof(int));
1228 abYield = (int*)sqlite3_realloc(abYield, nAlloc*sizeof(int));
1229 }
1230 abYield[iOp] = str_in_array(zOp, azYield);
1231 p->aiIndent[iOp] = 0;
1232 p->nIndent = iOp+1;
1233
1234 if( str_in_array(zOp, azNext) ){
danc4650bb2013-11-18 08:41:06 +00001235 for(i=p2op; i<iOp; i++) p->aiIndent[i] += 2;
dana98bf362013-11-13 18:35:01 +00001236 }
drhfe705102014-03-06 13:38:37 +00001237 if( str_in_array(zOp, azGoto) && p2op<p->nIndent
1238 && (abYield[p2op] || sqlite3_column_int(pSql, 2))
1239 ){
drhe73f0592014-01-21 22:25:45 +00001240 for(i=p2op+1; i<iOp; i++) p->aiIndent[i] += 2;
dana98bf362013-11-13 18:35:01 +00001241 }
1242 }
1243
danc4650bb2013-11-18 08:41:06 +00001244 p->iIndent = 0;
dana98bf362013-11-13 18:35:01 +00001245 sqlite3_free(abYield);
1246 sqlite3_reset(pSql);
1247}
1248
1249/*
1250** Free the array allocated by explain_data_prepare().
1251*/
1252static void explain_data_delete(struct callback_data *p){
1253 sqlite3_free(p->aiIndent);
1254 p->aiIndent = 0;
1255 p->nIndent = 0;
danc4650bb2013-11-18 08:41:06 +00001256 p->iIndent = 0;
dana98bf362013-11-13 18:35:01 +00001257}
1258
1259/*
shane626a6e42009-10-22 17:30:15 +00001260** Execute a statement or set of statements. Print
1261** any result rows/columns depending on the current mode
1262** set via the supplied callback.
1263**
1264** This is very similar to SQLite's built-in sqlite3_exec()
1265** function except it takes a slightly different callback
1266** and callback data argument.
1267*/
1268static int shell_exec(
1269 sqlite3 *db, /* An open database */
1270 const char *zSql, /* SQL to be evaluated */
1271 int (*xCallback)(void*,int,char**,char**,int*), /* Callback function */
1272 /* (not the same as sqlite3_exec) */
1273 struct callback_data *pArg, /* Pointer to struct callback_data */
1274 char **pzErrMsg /* Error msg written here */
1275){
dan4564ced2010-01-05 04:59:56 +00001276 sqlite3_stmt *pStmt = NULL; /* Statement to execute. */
1277 int rc = SQLITE_OK; /* Return Code */
drhb07028f2011-10-14 21:49:18 +00001278 int rc2;
dan4564ced2010-01-05 04:59:56 +00001279 const char *zLeftover; /* Tail of unprocessed SQL */
shane626a6e42009-10-22 17:30:15 +00001280
1281 if( pzErrMsg ){
1282 *pzErrMsg = NULL;
1283 }
1284
shaneb9fc17d2009-10-22 21:23:35 +00001285 while( zSql[0] && (SQLITE_OK == rc) ){
1286 rc = sqlite3_prepare_v2(db, zSql, -1, &pStmt, &zLeftover);
1287 if( SQLITE_OK != rc ){
shane626a6e42009-10-22 17:30:15 +00001288 if( pzErrMsg ){
1289 *pzErrMsg = save_err_msg(db);
1290 }
1291 }else{
shaneb9fc17d2009-10-22 21:23:35 +00001292 if( !pStmt ){
1293 /* this happens for a comment or white-space */
1294 zSql = zLeftover;
drhf0693c82011-10-11 20:41:54 +00001295 while( IsSpace(zSql[0]) ) zSql++;
shaneb9fc17d2009-10-22 21:23:35 +00001296 continue;
1297 }
shane626a6e42009-10-22 17:30:15 +00001298
shaneh642d8b82010-07-28 16:05:34 +00001299 /* save off the prepared statment handle and reset row count */
1300 if( pArg ){
1301 pArg->pStmt = pStmt;
1302 pArg->cnt = 0;
1303 }
1304
shanehb7977c52010-01-18 18:17:10 +00001305 /* echo the sql statement if echo on */
shaneh642d8b82010-07-28 16:05:34 +00001306 if( pArg && pArg->echoOn ){
drha8c62df2010-02-15 15:47:18 +00001307 const char *zStmtSql = sqlite3_sql(pStmt);
shaneh642d8b82010-07-28 16:05:34 +00001308 fprintf(pArg->out, "%s\n", zStmtSql ? zStmtSql : zSql);
drha8c62df2010-02-15 15:47:18 +00001309 }
shanehb7977c52010-01-18 18:17:10 +00001310
drhefbf3b12014-02-28 20:47:24 +00001311 /* Show the EXPLAIN QUERY PLAN if .eqp is on */
1312 if( pArg && pArg->autoEQP ){
1313 sqlite3_stmt *pExplain;
1314 char *zEQP = sqlite3_mprintf("EXPLAIN QUERY PLAN %s", sqlite3_sql(pStmt));
1315 rc = sqlite3_prepare_v2(db, zEQP, -1, &pExplain, 0);
1316 if( rc==SQLITE_OK ){
1317 while( sqlite3_step(pExplain)==SQLITE_ROW ){
1318 fprintf(pArg->out,"--EQP-- %d,", sqlite3_column_int(pExplain, 0));
1319 fprintf(pArg->out,"%d,", sqlite3_column_int(pExplain, 1));
1320 fprintf(pArg->out,"%d,", sqlite3_column_int(pExplain, 2));
1321 fprintf(pArg->out,"%s\n", sqlite3_column_text(pExplain, 3));
1322 }
1323 }
1324 sqlite3_finalize(pExplain);
1325 sqlite3_free(zEQP);
1326 }
1327
drh7e02e5e2011-12-06 19:44:51 +00001328 /* Output TESTCTRL_EXPLAIN text of requested */
1329 if( pArg && pArg->mode==MODE_Explain ){
1330 const char *zExplain = 0;
1331 sqlite3_test_control(SQLITE_TESTCTRL_EXPLAIN_STMT, pStmt, &zExplain);
1332 if( zExplain && zExplain[0] ){
1333 fprintf(pArg->out, "%s", zExplain);
1334 }
1335 }
1336
dana98bf362013-11-13 18:35:01 +00001337 /* If the shell is currently in ".explain" mode, gather the extra
1338 ** data required to add indents to the output.*/
drh0a305922013-11-21 23:37:02 +00001339 if( pArg && pArg->mode==MODE_Explain ){
dana98bf362013-11-13 18:35:01 +00001340 explain_data_prepare(pArg, pStmt);
1341 }
1342
shaneb9fc17d2009-10-22 21:23:35 +00001343 /* perform the first step. this will tell us if we
1344 ** have a result set or not and how wide it is.
1345 */
1346 rc = sqlite3_step(pStmt);
1347 /* if we have a result set... */
1348 if( SQLITE_ROW == rc ){
1349 /* if we have a callback... */
1350 if( xCallback ){
1351 /* allocate space for col name ptr, value ptr, and type */
1352 int nCol = sqlite3_column_count(pStmt);
1353 void *pData = sqlite3_malloc(3*nCol*sizeof(const char*) + 1);
1354 if( !pData ){
1355 rc = SQLITE_NOMEM;
1356 }else{
1357 char **azCols = (char **)pData; /* Names of result columns */
1358 char **azVals = &azCols[nCol]; /* Results */
1359 int *aiTypes = (int *)&azVals[nCol]; /* Result types */
drh55a1b302013-09-04 16:08:50 +00001360 int i, x;
shaneb9fc17d2009-10-22 21:23:35 +00001361 assert(sizeof(int) <= sizeof(char *));
1362 /* save off ptrs to column names */
1363 for(i=0; i<nCol; i++){
1364 azCols[i] = (char *)sqlite3_column_name(pStmt, i);
1365 }
shaneb9fc17d2009-10-22 21:23:35 +00001366 do{
1367 /* extract the data and data types */
1368 for(i=0; i<nCol; i++){
drh55a1b302013-09-04 16:08:50 +00001369 aiTypes[i] = x = sqlite3_column_type(pStmt, i);
drh3432daa2013-10-11 16:35:49 +00001370 if( x==SQLITE_BLOB && pArg && pArg->mode==MODE_Insert ){
drh55a1b302013-09-04 16:08:50 +00001371 azVals[i] = "";
1372 }else{
1373 azVals[i] = (char*)sqlite3_column_text(pStmt, i);
1374 }
shaneb9fc17d2009-10-22 21:23:35 +00001375 if( !azVals[i] && (aiTypes[i]!=SQLITE_NULL) ){
1376 rc = SQLITE_NOMEM;
1377 break; /* from for */
1378 }
1379 } /* end for */
1380
1381 /* if data and types extracted successfully... */
1382 if( SQLITE_ROW == rc ){
1383 /* call the supplied callback with the result row data */
1384 if( xCallback(pArg, nCol, azVals, azCols, aiTypes) ){
1385 rc = SQLITE_ABORT;
1386 }else{
1387 rc = sqlite3_step(pStmt);
1388 }
1389 }
1390 } while( SQLITE_ROW == rc );
1391 sqlite3_free(pData);
shaneb9fc17d2009-10-22 21:23:35 +00001392 }
1393 }else{
1394 do{
1395 rc = sqlite3_step(pStmt);
1396 } while( rc == SQLITE_ROW );
1397 }
1398 }
1399
dana98bf362013-11-13 18:35:01 +00001400 explain_data_delete(pArg);
1401
shaneh642d8b82010-07-28 16:05:34 +00001402 /* print usage stats if stats on */
1403 if( pArg && pArg->statsOn ){
1404 display_stats(db, pArg, 0);
1405 }
1406
dan4564ced2010-01-05 04:59:56 +00001407 /* Finalize the statement just executed. If this fails, save a
1408 ** copy of the error message. Otherwise, set zSql to point to the
1409 ** next statement to execute. */
drhb07028f2011-10-14 21:49:18 +00001410 rc2 = sqlite3_finalize(pStmt);
1411 if( rc!=SQLITE_NOMEM ) rc = rc2;
dan4564ced2010-01-05 04:59:56 +00001412 if( rc==SQLITE_OK ){
shaneb9fc17d2009-10-22 21:23:35 +00001413 zSql = zLeftover;
drhf0693c82011-10-11 20:41:54 +00001414 while( IsSpace(zSql[0]) ) zSql++;
dan4564ced2010-01-05 04:59:56 +00001415 }else if( pzErrMsg ){
1416 *pzErrMsg = save_err_msg(db);
shane626a6e42009-10-22 17:30:15 +00001417 }
shaneh642d8b82010-07-28 16:05:34 +00001418
1419 /* clear saved stmt handle */
1420 if( pArg ){
1421 pArg->pStmt = NULL;
1422 }
shane626a6e42009-10-22 17:30:15 +00001423 }
shaneb9fc17d2009-10-22 21:23:35 +00001424 } /* end while */
shane626a6e42009-10-22 17:30:15 +00001425
1426 return rc;
1427}
1428
drhdd3d4592004-08-30 01:54:05 +00001429
drh33048c02001-10-01 14:29:22 +00001430/*
drh4c653a02000-06-07 01:27:47 +00001431** This is a different callback routine used for dumping the database.
1432** Each row received by this callback consists of a table name,
1433** the table type ("index" or "table") and SQL to create the table.
1434** This routine should print text sufficient to recreate the table.
1435*/
1436static int dump_callback(void *pArg, int nArg, char **azArg, char **azCol){
danielk19772a02e332004-06-05 08:04:36 +00001437 int rc;
1438 const char *zTable;
1439 const char *zType;
1440 const char *zSql;
drh157e29a2009-05-21 15:15:00 +00001441 const char *zPrepStmt = 0;
drhdaffd0e2001-04-11 14:28:42 +00001442 struct callback_data *p = (struct callback_data *)pArg;
danielk19772a02e332004-06-05 08:04:36 +00001443
drh902b9ee2008-12-05 17:17:07 +00001444 UNUSED_PARAMETER(azCol);
drh4c653a02000-06-07 01:27:47 +00001445 if( nArg!=3 ) return 1;
danielk19772a02e332004-06-05 08:04:36 +00001446 zTable = azArg[0];
1447 zType = azArg[1];
1448 zSql = azArg[2];
1449
drh00b950d2005-09-11 02:03:03 +00001450 if( strcmp(zTable, "sqlite_sequence")==0 ){
drh157e29a2009-05-21 15:15:00 +00001451 zPrepStmt = "DELETE FROM sqlite_sequence;\n";
drh7ed10322013-08-07 16:04:27 +00001452 }else if( sqlite3_strglob("sqlite_stat?", zTable)==0 ){
drh00b950d2005-09-11 02:03:03 +00001453 fprintf(p->out, "ANALYZE sqlite_master;\n");
1454 }else if( strncmp(zTable, "sqlite_", 7)==0 ){
1455 return 0;
drh45e29d82006-11-20 16:21:10 +00001456 }else if( strncmp(zSql, "CREATE VIRTUAL TABLE", 20)==0 ){
1457 char *zIns;
1458 if( !p->writableSchema ){
1459 fprintf(p->out, "PRAGMA writable_schema=ON;\n");
1460 p->writableSchema = 1;
1461 }
1462 zIns = sqlite3_mprintf(
1463 "INSERT INTO sqlite_master(type,name,tbl_name,rootpage,sql)"
1464 "VALUES('table','%q','%q',0,'%q');",
1465 zTable, zTable, zSql);
1466 fprintf(p->out, "%s\n", zIns);
1467 sqlite3_free(zIns);
1468 return 0;
drh00b950d2005-09-11 02:03:03 +00001469 }else{
1470 fprintf(p->out, "%s;\n", zSql);
drhf8eb96a2005-02-03 00:42:34 +00001471 }
danielk19772a02e332004-06-05 08:04:36 +00001472
1473 if( strcmp(zType, "table")==0 ){
1474 sqlite3_stmt *pTableInfo = 0;
danielk19772a02e332004-06-05 08:04:36 +00001475 char *zSelect = 0;
1476 char *zTableInfo = 0;
1477 char *zTmp = 0;
drh157e29a2009-05-21 15:15:00 +00001478 int nRow = 0;
danielk19772a02e332004-06-05 08:04:36 +00001479
1480 zTableInfo = appendText(zTableInfo, "PRAGMA table_info(", 0);
1481 zTableInfo = appendText(zTableInfo, zTable, '"');
1482 zTableInfo = appendText(zTableInfo, ");", 0);
1483
drhc7181902014-02-27 15:04:13 +00001484 rc = sqlite3_prepare_v2(p->db, zTableInfo, -1, &pTableInfo, 0);
drh157e29a2009-05-21 15:15:00 +00001485 free(zTableInfo);
danielk19772a02e332004-06-05 08:04:36 +00001486 if( rc!=SQLITE_OK || !pTableInfo ){
1487 return 1;
1488 }
1489
1490 zSelect = appendText(zSelect, "SELECT 'INSERT INTO ' || ", 0);
drhbf92ec02012-03-22 12:50:34 +00001491 /* Always quote the table name, even if it appears to be pure ascii,
1492 ** in case it is a keyword. Ex: INSERT INTO "table" ... */
1493 zTmp = appendText(zTmp, zTable, '"');
danielk19772a02e332004-06-05 08:04:36 +00001494 if( zTmp ){
1495 zSelect = appendText(zSelect, zTmp, '\'');
drh85e72432012-04-11 11:38:53 +00001496 free(zTmp);
danielk19772a02e332004-06-05 08:04:36 +00001497 }
1498 zSelect = appendText(zSelect, " || ' VALUES(' || ", 0);
1499 rc = sqlite3_step(pTableInfo);
1500 while( rc==SQLITE_ROW ){
danielk19772e588c72005-12-09 14:25:08 +00001501 const char *zText = (const char *)sqlite3_column_text(pTableInfo, 1);
danielk19773f41e972004-06-08 00:39:01 +00001502 zSelect = appendText(zSelect, "quote(", 0);
danielk19772e588c72005-12-09 14:25:08 +00001503 zSelect = appendText(zSelect, zText, '"');
danielk19772a02e332004-06-05 08:04:36 +00001504 rc = sqlite3_step(pTableInfo);
1505 if( rc==SQLITE_ROW ){
drhb21a8e42012-01-28 21:08:51 +00001506 zSelect = appendText(zSelect, "), ", 0);
danielk19772a02e332004-06-05 08:04:36 +00001507 }else{
1508 zSelect = appendText(zSelect, ") ", 0);
1509 }
drh157e29a2009-05-21 15:15:00 +00001510 nRow++;
danielk19772a02e332004-06-05 08:04:36 +00001511 }
1512 rc = sqlite3_finalize(pTableInfo);
drh157e29a2009-05-21 15:15:00 +00001513 if( rc!=SQLITE_OK || nRow==0 ){
1514 free(zSelect);
danielk19772a02e332004-06-05 08:04:36 +00001515 return 1;
1516 }
1517 zSelect = appendText(zSelect, "|| ')' FROM ", 0);
1518 zSelect = appendText(zSelect, zTable, '"');
1519
drh2f464a02011-10-13 00:41:49 +00001520 rc = run_table_dump_query(p, zSelect, zPrepStmt);
drhdd3d4592004-08-30 01:54:05 +00001521 if( rc==SQLITE_CORRUPT ){
1522 zSelect = appendText(zSelect, " ORDER BY rowid DESC", 0);
drh2f464a02011-10-13 00:41:49 +00001523 run_table_dump_query(p, zSelect, 0);
drhdd3d4592004-08-30 01:54:05 +00001524 }
drh85e72432012-04-11 11:38:53 +00001525 free(zSelect);
drh4c653a02000-06-07 01:27:47 +00001526 }
drh4c653a02000-06-07 01:27:47 +00001527 return 0;
1528}
1529
1530/*
drh45e29d82006-11-20 16:21:10 +00001531** Run zQuery. Use dump_callback() as the callback routine so that
1532** the contents of the query are output as SQL statements.
1533**
drhdd3d4592004-08-30 01:54:05 +00001534** If we get a SQLITE_CORRUPT error, rerun the query after appending
1535** "ORDER BY rowid DESC" to the end.
1536*/
1537static int run_schema_dump_query(
1538 struct callback_data *p,
drh2f464a02011-10-13 00:41:49 +00001539 const char *zQuery
drhdd3d4592004-08-30 01:54:05 +00001540){
1541 int rc;
drh2f464a02011-10-13 00:41:49 +00001542 char *zErr = 0;
1543 rc = sqlite3_exec(p->db, zQuery, dump_callback, p, &zErr);
drhdd3d4592004-08-30 01:54:05 +00001544 if( rc==SQLITE_CORRUPT ){
1545 char *zQ2;
drh4f21c4a2008-12-10 22:15:00 +00001546 int len = strlen30(zQuery);
drh2f464a02011-10-13 00:41:49 +00001547 fprintf(p->out, "/****** CORRUPTION ERROR *******/\n");
1548 if( zErr ){
1549 fprintf(p->out, "/****** %s ******/\n", zErr);
1550 sqlite3_free(zErr);
1551 zErr = 0;
1552 }
drhdd3d4592004-08-30 01:54:05 +00001553 zQ2 = malloc( len+100 );
1554 if( zQ2==0 ) return rc;
drh8c5058b2012-04-16 17:22:30 +00001555 sqlite3_snprintf(len+100, zQ2, "%s ORDER BY rowid DESC", zQuery);
drh2f464a02011-10-13 00:41:49 +00001556 rc = sqlite3_exec(p->db, zQ2, dump_callback, p, &zErr);
1557 if( rc ){
1558 fprintf(p->out, "/****** ERROR: %s ******/\n", zErr);
1559 }else{
1560 rc = SQLITE_CORRUPT;
1561 }
1562 sqlite3_free(zErr);
drhdd3d4592004-08-30 01:54:05 +00001563 free(zQ2);
1564 }
1565 return rc;
1566}
1567
1568/*
drh75897232000-05-29 14:26:00 +00001569** Text of a help message
1570*/
persicom1d0b8722002-04-18 02:53:04 +00001571static char zHelp[] =
drh9ff849f2009-02-04 20:55:57 +00001572 ".backup ?DB? FILE Backup DB (default \"main\") to FILE\n"
drh20f99c42007-01-08 14:31:35 +00001573 ".bail ON|OFF Stop after hitting an error. Default OFF\n"
drh4bbcf102014-02-06 02:46:08 +00001574 ".clone NEWDB Clone data into NEWDB from the existing database\n"
jplyon6a65bb32003-05-04 07:25:57 +00001575 ".databases List names and files of attached databases\n"
drhb860bc92004-08-04 15:16:55 +00001576 ".dump ?TABLE? ... Dump the database in an SQL text format\n"
shane86f5bdb2009-10-24 02:00:07 +00001577 " If TABLE specified, only dump tables matching\n"
1578 " LIKE pattern TABLE.\n"
drhdaffd0e2001-04-11 14:28:42 +00001579 ".echo ON|OFF Turn command echo on or off\n"
drh75897232000-05-29 14:26:00 +00001580 ".exit Exit this program\n"
shanehe2aa9d72009-11-06 17:20:17 +00001581 ".explain ?ON|OFF? Turn output mode suitable for EXPLAIN on or off.\n"
1582 " With no args, it turns EXPLAIN on.\n"
drh62cdde52014-05-28 20:22:28 +00001583 ".headers ON|OFF Turn display of headers on or off\n"
drh75897232000-05-29 14:26:00 +00001584 ".help Show this message\n"
drhb860bc92004-08-04 15:16:55 +00001585 ".import FILE TABLE Import data from FILE into TABLE\n"
shane86f5bdb2009-10-24 02:00:07 +00001586 ".indices ?TABLE? Show names of all indices\n"
1587 " If TABLE specified, only show indices for tables\n"
1588 " matching LIKE pattern TABLE.\n"
drhae5e4452007-05-03 17:18:36 +00001589#ifdef SQLITE_ENABLE_IOTRACE
1590 ".iotrace FILE Enable I/O diagnostic logging to FILE\n"
1591#endif
drh70df4fe2006-06-13 15:12:21 +00001592#ifndef SQLITE_OMIT_LOAD_EXTENSION
drh1e397f82006-06-08 15:28:43 +00001593 ".load FILE ?ENTRY? Load an extension library\n"
drh70df4fe2006-06-13 15:12:21 +00001594#endif
drh127f9d72010-02-23 01:47:00 +00001595 ".log FILE|off Turn logging on or off. FILE can be stderr/stdout\n"
danielk19776b77a362005-01-13 11:10:25 +00001596 ".mode MODE ?TABLE? Set output mode where MODE is one of:\n"
drh3b584fa2004-09-24 12:50:03 +00001597 " csv Comma-separated values\n"
drhb860bc92004-08-04 15:16:55 +00001598 " column Left-aligned columns. (See .width)\n"
1599 " html HTML <table> code\n"
1600 " insert SQL insert statements for TABLE\n"
1601 " line One value per line\n"
1602 " list Values delimited by .separator string\n"
1603 " tabs Tab-separated values\n"
1604 " tcl TCL list elements\n"
drh078b1fd2012-09-21 13:40:02 +00001605 ".nullvalue STRING Use STRING in place of NULL values\n"
drh05782482013-10-24 15:20:20 +00001606 ".open ?FILENAME? Close existing database and reopen FILENAME\n"
drh75897232000-05-29 14:26:00 +00001607 ".output FILENAME Send output to FILENAME\n"
1608 ".output stdout Send output to the screen\n"
drh078b1fd2012-09-21 13:40:02 +00001609 ".print STRING... Print literal STRING\n"
persicom7e2dfdd2002-04-18 02:46:52 +00001610 ".prompt MAIN CONTINUE Replace the standard prompts\n"
persicom7e2dfdd2002-04-18 02:46:52 +00001611 ".quit Exit this program\n"
drhdaffd0e2001-04-11 14:28:42 +00001612 ".read FILENAME Execute SQL in FILENAME\n"
drh9ff849f2009-02-04 20:55:57 +00001613 ".restore ?DB? FILE Restore content of DB (default \"main\") from FILE\n"
drh5c7976f2014-02-10 19:59:27 +00001614 ".save FILE Write in-memory database into FILE\n"
drh75897232000-05-29 14:26:00 +00001615 ".schema ?TABLE? Show the CREATE statements\n"
shane86f5bdb2009-10-24 02:00:07 +00001616 " If TABLE specified, only show tables matching\n"
1617 " LIKE pattern TABLE.\n"
drhb860bc92004-08-04 15:16:55 +00001618 ".separator STRING Change separator used by output mode and .import\n"
drh62cdde52014-05-28 20:22:28 +00001619 ".shell CMD ARGS... Run CMD ARGS... in a system shell\n"
drhdd45df82002-04-18 12:39:03 +00001620 ".show Show the current values for various settings\n"
shaneh642d8b82010-07-28 16:05:34 +00001621 ".stats ON|OFF Turn stats on or off\n"
drh62cdde52014-05-28 20:22:28 +00001622 ".system CMD ARGS... Run CMD ARGS... in a system shell\n"
shane86f5bdb2009-10-24 02:00:07 +00001623 ".tables ?TABLE? List names of tables\n"
1624 " If TABLE specified, only list tables matching\n"
1625 " LIKE pattern TABLE.\n"
drh2dfbbca2000-07-28 14:32:48 +00001626 ".timeout MS Try opening locked tables for MS milliseconds\n"
drh42f64e52012-04-04 16:56:23 +00001627 ".trace FILE|off Output each SQL statement as it is run\n"
drhde60fc22011-12-14 17:53:36 +00001628 ".vfsname ?AUX? Print the name of the VFS stack\n"
shanehe2aa9d72009-11-06 17:20:17 +00001629 ".width NUM1 NUM2 ... Set column widths for \"column\" mode\n"
drh62cdde52014-05-28 20:22:28 +00001630 " Negative values right-justify\n"
drh75897232000-05-29 14:26:00 +00001631;
1632
shaneb320ccd2009-10-21 03:42:58 +00001633static char zTimerHelp[] =
1634 ".timer ON|OFF Turn the CPU timer measurement on or off\n"
1635;
1636
drhdaffd0e2001-04-11 14:28:42 +00001637/* Forward reference */
drhc28490c2006-10-26 14:25:58 +00001638static int process_input(struct callback_data *p, FILE *in);
drhdaffd0e2001-04-11 14:28:42 +00001639
drh75897232000-05-29 14:26:00 +00001640/*
drh44c2eb12003-04-30 11:38:26 +00001641** Make sure the database is open. If it is not, then open it. If
1642** the database fails to open, print an error message and exit.
1643*/
drh05782482013-10-24 15:20:20 +00001644static void open_db(struct callback_data *p, int keepAlive){
drh44c2eb12003-04-30 11:38:26 +00001645 if( p->db==0 ){
drhbbb0be82012-06-27 16:12:27 +00001646 sqlite3_initialize();
danielk19774f057f92004-06-08 00:02:33 +00001647 sqlite3_open(p->zDbFilename, &p->db);
danielk197780290862004-05-22 09:21:21 +00001648 db = p->db;
drh4cea5ba2008-05-05 16:27:24 +00001649 if( db && sqlite3_errcode(db)==SQLITE_OK ){
1650 sqlite3_create_function(db, "shellstatic", 0, SQLITE_UTF8, 0,
1651 shellstaticFunc, 0, 0);
1652 }
1653 if( db==0 || SQLITE_OK!=sqlite3_errcode(db) ){
shane86f5bdb2009-10-24 02:00:07 +00001654 fprintf(stderr,"Error: unable to open database \"%s\": %s\n",
danielk197780290862004-05-22 09:21:21 +00001655 p->zDbFilename, sqlite3_errmsg(db));
drh05782482013-10-24 15:20:20 +00001656 if( keepAlive ) return;
drh22fbcb82004-02-01 01:22:50 +00001657 exit(1);
drh44c2eb12003-04-30 11:38:26 +00001658 }
drhc2e87a32006-06-27 15:16:14 +00001659#ifndef SQLITE_OMIT_LOAD_EXTENSION
1660 sqlite3_enable_load_extension(p->db, 1);
1661#endif
drh44c2eb12003-04-30 11:38:26 +00001662 }
1663}
1664
1665/*
drhfeac5f82004-08-01 00:10:45 +00001666** Do C-language style dequoting.
1667**
1668** \t -> tab
1669** \n -> newline
1670** \r -> carriage return
drh4c56b992013-06-27 13:26:55 +00001671** \" -> "
drhfeac5f82004-08-01 00:10:45 +00001672** \NNN -> ascii character NNN in octal
1673** \\ -> backslash
1674*/
1675static void resolve_backslashes(char *z){
shane7d3846a2008-12-11 02:58:26 +00001676 int i, j;
1677 char c;
drhfeac5f82004-08-01 00:10:45 +00001678 for(i=j=0; (c = z[i])!=0; i++, j++){
1679 if( c=='\\' ){
1680 c = z[++i];
1681 if( c=='n' ){
1682 c = '\n';
1683 }else if( c=='t' ){
1684 c = '\t';
1685 }else if( c=='r' ){
1686 c = '\r';
drh4c56b992013-06-27 13:26:55 +00001687 }else if( c=='\\' ){
1688 c = '\\';
drhfeac5f82004-08-01 00:10:45 +00001689 }else if( c>='0' && c<='7' ){
drhaa816082005-12-29 12:53:09 +00001690 c -= '0';
drhfeac5f82004-08-01 00:10:45 +00001691 if( z[i+1]>='0' && z[i+1]<='7' ){
1692 i++;
1693 c = (c<<3) + z[i] - '0';
1694 if( z[i+1]>='0' && z[i+1]<='7' ){
1695 i++;
1696 c = (c<<3) + z[i] - '0';
1697 }
1698 }
1699 }
1700 }
1701 z[j] = c;
1702 }
1703 z[j] = 0;
1704}
1705
1706/*
drh348d19c2013-06-03 12:47:43 +00001707** Return the value of a hexadecimal digit. Return -1 if the input
1708** is not a hex digit.
drhc28490c2006-10-26 14:25:58 +00001709*/
drh348d19c2013-06-03 12:47:43 +00001710static int hexDigitValue(char c){
1711 if( c>='0' && c<='9' ) return c - '0';
1712 if( c>='a' && c<='f' ) return c - 'a' + 10;
1713 if( c>='A' && c<='F' ) return c - 'A' + 10;
1714 return -1;
drhc28490c2006-10-26 14:25:58 +00001715}
1716
1717/*
drh7d9f3942013-04-03 01:26:54 +00001718** Interpret zArg as an integer value, possibly with suffixes.
1719*/
1720static sqlite3_int64 integerValue(const char *zArg){
1721 sqlite3_int64 v = 0;
1722 static const struct { char *zSuffix; int iMult; } aMult[] = {
1723 { "KiB", 1024 },
1724 { "MiB", 1024*1024 },
1725 { "GiB", 1024*1024*1024 },
1726 { "KB", 1000 },
1727 { "MB", 1000000 },
1728 { "GB", 1000000000 },
1729 { "K", 1000 },
1730 { "M", 1000000 },
1731 { "G", 1000000000 },
1732 };
1733 int i;
1734 int isNeg = 0;
1735 if( zArg[0]=='-' ){
1736 isNeg = 1;
1737 zArg++;
1738 }else if( zArg[0]=='+' ){
1739 zArg++;
1740 }
drh348d19c2013-06-03 12:47:43 +00001741 if( zArg[0]=='0' && zArg[1]=='x' ){
1742 int x;
1743 zArg += 2;
1744 while( (x = hexDigitValue(zArg[0]))>=0 ){
1745 v = (v<<4) + x;
1746 zArg++;
1747 }
1748 }else{
1749 while( IsDigit(zArg[0]) ){
1750 v = v*10 + zArg[0] - '0';
1751 zArg++;
1752 }
drh7d9f3942013-04-03 01:26:54 +00001753 }
drhc2bed0a2013-05-24 11:57:50 +00001754 for(i=0; i<ArraySize(aMult); i++){
drh7d9f3942013-04-03 01:26:54 +00001755 if( sqlite3_stricmp(aMult[i].zSuffix, zArg)==0 ){
1756 v *= aMult[i].iMult;
1757 break;
1758 }
1759 }
1760 return isNeg? -v : v;
1761}
1762
1763/*
drh348d19c2013-06-03 12:47:43 +00001764** Interpret zArg as either an integer or a boolean value. Return 1 or 0
1765** for TRUE and FALSE. Return the integer value if appropriate.
1766*/
1767static int booleanValue(char *zArg){
1768 int i;
1769 if( zArg[0]=='0' && zArg[1]=='x' ){
1770 for(i=2; hexDigitValue(zArg[i])>=0; i++){}
1771 }else{
1772 for(i=0; zArg[i]>='0' && zArg[i]<='9'; i++){}
1773 }
1774 if( i>0 && zArg[i]==0 ) return (int)(integerValue(zArg) & 0xffffffff);
1775 if( sqlite3_stricmp(zArg, "on")==0 || sqlite3_stricmp(zArg,"yes")==0 ){
1776 return 1;
1777 }
1778 if( sqlite3_stricmp(zArg, "off")==0 || sqlite3_stricmp(zArg,"no")==0 ){
1779 return 0;
1780 }
1781 fprintf(stderr, "ERROR: Not a boolean value: \"%s\". Assuming \"no\".\n",
1782 zArg);
1783 return 0;
1784}
1785
1786/*
drh42f64e52012-04-04 16:56:23 +00001787** Close an output file, assuming it is not stderr or stdout
1788*/
1789static void output_file_close(FILE *f){
1790 if( f && f!=stdout && f!=stderr ) fclose(f);
1791}
1792
1793/*
1794** Try to open an output file. The names "stdout" and "stderr" are
1795** recognized and do the right thing. NULL is returned if the output
1796** filename is "off".
1797*/
1798static FILE *output_file_open(const char *zFile){
1799 FILE *f;
1800 if( strcmp(zFile,"stdout")==0 ){
1801 f = stdout;
1802 }else if( strcmp(zFile, "stderr")==0 ){
1803 f = stderr;
1804 }else if( strcmp(zFile, "off")==0 ){
1805 f = 0;
1806 }else{
1807 f = fopen(zFile, "wb");
1808 if( f==0 ){
1809 fprintf(stderr, "Error: cannot open \"%s\"\n", zFile);
1810 }
1811 }
1812 return f;
1813}
1814
1815/*
1816** A routine for handling output from sqlite3_trace().
1817*/
1818static void sql_trace_callback(void *pArg, const char *z){
1819 FILE *f = (FILE*)pArg;
1820 if( f ) fprintf(f, "%s\n", z);
1821}
1822
1823/*
drhd8621b92012-04-17 09:09:33 +00001824** A no-op routine that runs with the ".breakpoint" doc-command. This is
1825** a useful spot to set a debugger breakpoint.
1826*/
1827static void test_breakpoint(void){
1828 static int nCall = 0;
1829 nCall++;
1830}
1831
1832/*
drhdb95f682013-06-26 22:46:00 +00001833** An object used to read a CSV file
1834*/
1835typedef struct CSVReader CSVReader;
1836struct CSVReader {
1837 const char *zFile; /* Name of the input file */
1838 FILE *in; /* Read the CSV text from this input stream */
1839 char *z; /* Accumulated text for a field */
1840 int n; /* Number of bytes in z */
1841 int nAlloc; /* Space allocated for z[] */
1842 int nLine; /* Current line number */
1843 int cTerm; /* Character that terminated the most recent field */
1844 int cSeparator; /* The separator character. (Usually ",") */
1845};
1846
1847/* Append a single byte to z[] */
1848static void csv_append_char(CSVReader *p, int c){
1849 if( p->n+1>=p->nAlloc ){
1850 p->nAlloc += p->nAlloc + 100;
1851 p->z = sqlite3_realloc(p->z, p->nAlloc);
1852 if( p->z==0 ){
1853 fprintf(stderr, "out of memory\n");
1854 exit(1);
1855 }
1856 }
1857 p->z[p->n++] = (char)c;
1858}
1859
1860/* Read a single field of CSV text. Compatible with rfc4180 and extended
1861** with the option of having a separator other than ",".
1862**
1863** + Input comes from p->in.
1864** + Store results in p->z of length p->n. Space to hold p->z comes
1865** from sqlite3_malloc().
1866** + Use p->cSep as the separator. The default is ",".
1867** + Keep track of the line number in p->nLine.
1868** + Store the character that terminates the field in p->cTerm. Store
1869** EOF on end-of-file.
1870** + Report syntax errors on stderr
1871*/
1872static char *csv_read_one_field(CSVReader *p){
drha81ad172013-12-11 14:00:04 +00001873 int c, pc, ppc;
drhdb95f682013-06-26 22:46:00 +00001874 int cSep = p->cSeparator;
1875 p->n = 0;
1876 c = fgetc(p->in);
1877 if( c==EOF || seenInterrupt ){
1878 p->cTerm = EOF;
1879 return 0;
1880 }
1881 if( c=='"' ){
1882 int startLine = p->nLine;
1883 int cQuote = c;
drha81ad172013-12-11 14:00:04 +00001884 pc = ppc = 0;
drhdb95f682013-06-26 22:46:00 +00001885 while( 1 ){
1886 c = fgetc(p->in);
1887 if( c=='\n' ) p->nLine++;
1888 if( c==cQuote ){
1889 if( pc==cQuote ){
1890 pc = 0;
1891 continue;
1892 }
1893 }
1894 if( (c==cSep && pc==cQuote)
1895 || (c=='\n' && pc==cQuote)
drha81ad172013-12-11 14:00:04 +00001896 || (c=='\n' && pc=='\r' && ppc==cQuote)
drhdb95f682013-06-26 22:46:00 +00001897 || (c==EOF && pc==cQuote)
1898 ){
1899 do{ p->n--; }while( p->z[p->n]!=cQuote );
drhdb95f682013-06-26 22:46:00 +00001900 p->cTerm = c;
1901 break;
1902 }
1903 if( pc==cQuote && c!='\r' ){
1904 fprintf(stderr, "%s:%d: unescaped %c character\n",
1905 p->zFile, p->nLine, cQuote);
1906 }
1907 if( c==EOF ){
1908 fprintf(stderr, "%s:%d: unterminated %c-quoted field\n",
1909 p->zFile, startLine, cQuote);
drhdb95f682013-06-26 22:46:00 +00001910 p->cTerm = EOF;
1911 break;
1912 }
1913 csv_append_char(p, c);
drha81ad172013-12-11 14:00:04 +00001914 ppc = pc;
drhdb95f682013-06-26 22:46:00 +00001915 pc = c;
drhd0a64dc2013-06-30 20:24:26 +00001916 }
drhdb95f682013-06-26 22:46:00 +00001917 }else{
drhd0a64dc2013-06-30 20:24:26 +00001918 while( c!=EOF && c!=cSep && c!='\n' ){
drhdb95f682013-06-26 22:46:00 +00001919 csv_append_char(p, c);
drhd0a64dc2013-06-30 20:24:26 +00001920 c = fgetc(p->in);
drhdb95f682013-06-26 22:46:00 +00001921 }
1922 if( c=='\n' ){
1923 p->nLine++;
drh3852b682014-02-26 13:53:34 +00001924 if( p->n>0 && p->z[p->n-1]=='\r' ) p->n--;
drhdb95f682013-06-26 22:46:00 +00001925 }
drhdb95f682013-06-26 22:46:00 +00001926 p->cTerm = c;
1927 }
drh8dd675e2013-07-12 21:09:24 +00001928 if( p->z ) p->z[p->n] = 0;
drhdb95f682013-06-26 22:46:00 +00001929 return p->z;
1930}
1931
1932/*
drh4bbcf102014-02-06 02:46:08 +00001933** Try to transfer data for table zTable. If an error is seen while
1934** moving forward, try to go backwards. The backwards movement won't
1935** work for WITHOUT ROWID tables.
drh3350ce92014-02-06 00:49:12 +00001936*/
mistachkine31ae902014-02-06 01:15:29 +00001937static void tryToCloneData(
drh3350ce92014-02-06 00:49:12 +00001938 struct callback_data *p,
1939 sqlite3 *newDb,
1940 const char *zTable
1941){
1942 sqlite3_stmt *pQuery = 0;
1943 sqlite3_stmt *pInsert = 0;
1944 char *zQuery = 0;
1945 char *zInsert = 0;
1946 int rc;
1947 int i, j, n;
1948 int nTable = (int)strlen(zTable);
1949 int k = 0;
drh4bbcf102014-02-06 02:46:08 +00001950 int cnt = 0;
1951 const int spinRate = 10000;
drh3350ce92014-02-06 00:49:12 +00001952
1953 zQuery = sqlite3_mprintf("SELECT * FROM \"%w\"", zTable);
1954 rc = sqlite3_prepare_v2(p->db, zQuery, -1, &pQuery, 0);
1955 if( rc ){
drh4bbcf102014-02-06 02:46:08 +00001956 fprintf(stderr, "Error %d: %s on [%s]\n",
drh3350ce92014-02-06 00:49:12 +00001957 sqlite3_extended_errcode(p->db), sqlite3_errmsg(p->db),
1958 zQuery);
1959 goto end_data_xfer;
1960 }
1961 n = sqlite3_column_count(pQuery);
1962 zInsert = sqlite3_malloc(200 + nTable + n*3);
1963 if( zInsert==0 ){
1964 fprintf(stderr, "out of memory\n");
1965 goto end_data_xfer;
1966 }
1967 sqlite3_snprintf(200+nTable,zInsert,
1968 "INSERT OR IGNORE INTO \"%s\" VALUES(?", zTable);
1969 i = (int)strlen(zInsert);
1970 for(j=1; j<n; j++){
1971 memcpy(zInsert+i, ",?", 2);
1972 i += 2;
1973 }
1974 memcpy(zInsert+i, ");", 3);
1975 rc = sqlite3_prepare_v2(newDb, zInsert, -1, &pInsert, 0);
1976 if( rc ){
drh4bbcf102014-02-06 02:46:08 +00001977 fprintf(stderr, "Error %d: %s on [%s]\n",
drh3350ce92014-02-06 00:49:12 +00001978 sqlite3_extended_errcode(newDb), sqlite3_errmsg(newDb),
1979 zQuery);
1980 goto end_data_xfer;
1981 }
1982 for(k=0; k<2; k++){
1983 while( (rc = sqlite3_step(pQuery))==SQLITE_ROW ){
1984 for(i=0; i<n; i++){
1985 switch( sqlite3_column_type(pQuery, i) ){
1986 case SQLITE_NULL: {
1987 sqlite3_bind_null(pInsert, i+1);
1988 break;
1989 }
1990 case SQLITE_INTEGER: {
1991 sqlite3_bind_int64(pInsert, i+1, sqlite3_column_int64(pQuery,i));
1992 break;
1993 }
1994 case SQLITE_FLOAT: {
1995 sqlite3_bind_double(pInsert, i+1, sqlite3_column_double(pQuery,i));
1996 break;
1997 }
1998 case SQLITE_TEXT: {
1999 sqlite3_bind_text(pInsert, i+1,
2000 (const char*)sqlite3_column_text(pQuery,i),
2001 -1, SQLITE_STATIC);
2002 break;
2003 }
2004 case SQLITE_BLOB: {
2005 sqlite3_bind_blob(pInsert, i+1, sqlite3_column_blob(pQuery,i),
2006 sqlite3_column_bytes(pQuery,i),
2007 SQLITE_STATIC);
2008 break;
2009 }
2010 }
2011 } /* End for */
drh4bbcf102014-02-06 02:46:08 +00002012 rc = sqlite3_step(pInsert);
2013 if( rc!=SQLITE_OK && rc!=SQLITE_ROW && rc!=SQLITE_DONE ){
2014 fprintf(stderr, "Error %d: %s\n", sqlite3_extended_errcode(newDb),
2015 sqlite3_errmsg(newDb));
2016 }
drh3350ce92014-02-06 00:49:12 +00002017 sqlite3_reset(pInsert);
drh4bbcf102014-02-06 02:46:08 +00002018 cnt++;
2019 if( (cnt%spinRate)==0 ){
2020 printf("%c\b", "|/-\\"[(cnt/spinRate)%4]);
2021 fflush(stdout);
2022 }
drh3350ce92014-02-06 00:49:12 +00002023 } /* End while */
2024 if( rc==SQLITE_DONE ) break;
2025 sqlite3_finalize(pQuery);
2026 sqlite3_free(zQuery);
2027 zQuery = sqlite3_mprintf("SELECT * FROM \"%w\" ORDER BY rowid DESC;",
2028 zTable);
2029 rc = sqlite3_prepare_v2(p->db, zQuery, -1, &pQuery, 0);
2030 if( rc ){
drh4bbcf102014-02-06 02:46:08 +00002031 fprintf(stderr, "Warning: cannot step \"%s\" backwards", zTable);
2032 break;
drh3350ce92014-02-06 00:49:12 +00002033 }
2034 } /* End for(k=0...) */
2035
2036end_data_xfer:
2037 sqlite3_finalize(pQuery);
2038 sqlite3_finalize(pInsert);
2039 sqlite3_free(zQuery);
2040 sqlite3_free(zInsert);
2041}
2042
2043
2044/*
2045** Try to transfer all rows of the schema that match zWhere. For
2046** each row, invoke xForEach() on the object defined by that row.
drh4bbcf102014-02-06 02:46:08 +00002047** If an error is encountered while moving forward through the
2048** sqlite_master table, try again moving backwards.
drh3350ce92014-02-06 00:49:12 +00002049*/
mistachkine31ae902014-02-06 01:15:29 +00002050static void tryToCloneSchema(
drh3350ce92014-02-06 00:49:12 +00002051 struct callback_data *p,
2052 sqlite3 *newDb,
2053 const char *zWhere,
2054 void (*xForEach)(struct callback_data*,sqlite3*,const char*)
2055){
2056 sqlite3_stmt *pQuery = 0;
2057 char *zQuery = 0;
2058 int rc;
2059 const unsigned char *zName;
2060 const unsigned char *zSql;
drh4bbcf102014-02-06 02:46:08 +00002061 char *zErrMsg = 0;
drh3350ce92014-02-06 00:49:12 +00002062
2063 zQuery = sqlite3_mprintf("SELECT name, sql FROM sqlite_master"
2064 " WHERE %s", zWhere);
2065 rc = sqlite3_prepare_v2(p->db, zQuery, -1, &pQuery, 0);
2066 if( rc ){
2067 fprintf(stderr, "Error: (%d) %s on [%s]\n",
2068 sqlite3_extended_errcode(p->db), sqlite3_errmsg(p->db),
2069 zQuery);
2070 goto end_schema_xfer;
2071 }
2072 while( (rc = sqlite3_step(pQuery))==SQLITE_ROW ){
2073 zName = sqlite3_column_text(pQuery, 0);
2074 zSql = sqlite3_column_text(pQuery, 1);
2075 printf("%s... ", zName); fflush(stdout);
drh4bbcf102014-02-06 02:46:08 +00002076 sqlite3_exec(newDb, (const char*)zSql, 0, 0, &zErrMsg);
2077 if( zErrMsg ){
2078 fprintf(stderr, "Error: %s\nSQL: [%s]\n", zErrMsg, zSql);
2079 sqlite3_free(zErrMsg);
2080 zErrMsg = 0;
2081 }
drh3350ce92014-02-06 00:49:12 +00002082 if( xForEach ){
2083 xForEach(p, newDb, (const char*)zName);
2084 }
2085 printf("done\n");
2086 }
2087 if( rc!=SQLITE_DONE ){
2088 sqlite3_finalize(pQuery);
2089 sqlite3_free(zQuery);
2090 zQuery = sqlite3_mprintf("SELECT name, sql FROM sqlite_master"
2091 " WHERE %s ORDER BY rowid DESC", zWhere);
2092 rc = sqlite3_prepare_v2(p->db, zQuery, -1, &pQuery, 0);
2093 if( rc ){
2094 fprintf(stderr, "Error: (%d) %s on [%s]\n",
2095 sqlite3_extended_errcode(p->db), sqlite3_errmsg(p->db),
2096 zQuery);
2097 goto end_schema_xfer;
2098 }
2099 while( (rc = sqlite3_step(pQuery))==SQLITE_ROW ){
2100 zName = sqlite3_column_text(pQuery, 0);
2101 zSql = sqlite3_column_text(pQuery, 1);
2102 printf("%s... ", zName); fflush(stdout);
drh4bbcf102014-02-06 02:46:08 +00002103 sqlite3_exec(newDb, (const char*)zSql, 0, 0, &zErrMsg);
2104 if( zErrMsg ){
2105 fprintf(stderr, "Error: %s\nSQL: [%s]\n", zErrMsg, zSql);
2106 sqlite3_free(zErrMsg);
2107 zErrMsg = 0;
2108 }
drh3350ce92014-02-06 00:49:12 +00002109 if( xForEach ){
2110 xForEach(p, newDb, (const char*)zName);
2111 }
2112 printf("done\n");
2113 }
2114 }
2115end_schema_xfer:
2116 sqlite3_finalize(pQuery);
2117 sqlite3_free(zQuery);
2118}
2119
2120/*
2121** Open a new database file named "zNewDb". Try to recover as much information
2122** as possible out of the main database (which might be corrupt) and write it
2123** into zNewDb.
2124*/
mistachkine31ae902014-02-06 01:15:29 +00002125static void tryToClone(struct callback_data *p, const char *zNewDb){
drh3350ce92014-02-06 00:49:12 +00002126 int rc;
2127 sqlite3 *newDb = 0;
2128 if( access(zNewDb,0)==0 ){
2129 fprintf(stderr, "File \"%s\" already exists.\n", zNewDb);
2130 return;
2131 }
2132 rc = sqlite3_open(zNewDb, &newDb);
2133 if( rc ){
2134 fprintf(stderr, "Cannot create output database: %s\n",
2135 sqlite3_errmsg(newDb));
2136 }else{
drh54d0d2d2014-04-03 00:32:13 +00002137 sqlite3_exec(p->db, "PRAGMA writable_schema=ON;", 0, 0, 0);
drh3350ce92014-02-06 00:49:12 +00002138 sqlite3_exec(newDb, "BEGIN EXCLUSIVE;", 0, 0, 0);
mistachkine31ae902014-02-06 01:15:29 +00002139 tryToCloneSchema(p, newDb, "type='table'", tryToCloneData);
2140 tryToCloneSchema(p, newDb, "type!='table'", 0);
drh3350ce92014-02-06 00:49:12 +00002141 sqlite3_exec(newDb, "COMMIT;", 0, 0, 0);
drh54d0d2d2014-04-03 00:32:13 +00002142 sqlite3_exec(p->db, "PRAGMA writable_schema=OFF;", 0, 0, 0);
drh3350ce92014-02-06 00:49:12 +00002143 }
2144 sqlite3_close(newDb);
2145}
2146
2147/*
drh75897232000-05-29 14:26:00 +00002148** If an input line begins with "." then invoke this routine to
2149** process that line.
drh67505e72002-04-19 12:34:06 +00002150**
drh47ad6842006-11-08 12:25:42 +00002151** Return 1 on error, 2 to exit, and 0 otherwise.
drh75897232000-05-29 14:26:00 +00002152*/
drh44c2eb12003-04-30 11:38:26 +00002153static int do_meta_command(char *zLine, struct callback_data *p){
drh75897232000-05-29 14:26:00 +00002154 int i = 1;
2155 int nArg = 0;
2156 int n, c;
drh67505e72002-04-19 12:34:06 +00002157 int rc = 0;
drh75897232000-05-29 14:26:00 +00002158 char *azArg[50];
2159
2160 /* Parse the input line into tokens.
2161 */
2162 while( zLine[i] && nArg<ArraySize(azArg) ){
drhf0693c82011-10-11 20:41:54 +00002163 while( IsSpace(zLine[i]) ){ i++; }
drh06333682004-03-09 13:37:45 +00002164 if( zLine[i]==0 ) break;
drh75897232000-05-29 14:26:00 +00002165 if( zLine[i]=='\'' || zLine[i]=='"' ){
2166 int delim = zLine[i++];
2167 azArg[nArg++] = &zLine[i];
drh4c56b992013-06-27 13:26:55 +00002168 while( zLine[i] && zLine[i]!=delim ){
2169 if( zLine[i]=='\\' && delim=='"' && zLine[i+1]!=0 ) i++;
2170 i++;
2171 }
drh75897232000-05-29 14:26:00 +00002172 if( zLine[i]==delim ){
2173 zLine[i++] = 0;
2174 }
drhfeac5f82004-08-01 00:10:45 +00002175 if( delim=='"' ) resolve_backslashes(azArg[nArg-1]);
drh75897232000-05-29 14:26:00 +00002176 }else{
2177 azArg[nArg++] = &zLine[i];
drhf0693c82011-10-11 20:41:54 +00002178 while( zLine[i] && !IsSpace(zLine[i]) ){ i++; }
drh75897232000-05-29 14:26:00 +00002179 if( zLine[i] ) zLine[i++] = 0;
drhfeac5f82004-08-01 00:10:45 +00002180 resolve_backslashes(azArg[nArg-1]);
drh75897232000-05-29 14:26:00 +00002181 }
2182 }
2183
2184 /* Process the input line.
2185 */
shane9bd1b442009-10-23 01:27:39 +00002186 if( nArg==0 ) return 0; /* no tokens, no error */
drh4f21c4a2008-12-10 22:15:00 +00002187 n = strlen30(azArg[0]);
drh75897232000-05-29 14:26:00 +00002188 c = azArg[0][0];
drh5c7976f2014-02-10 19:59:27 +00002189 if( (c=='b' && n>=3 && strncmp(azArg[0], "backup", n)==0)
2190 || (c=='s' && n>=3 && strncmp(azArg[0], "save", n)==0)
2191 ){
drhbc46f022013-01-23 18:53:23 +00002192 const char *zDestFile = 0;
2193 const char *zDb = 0;
drh9ff849f2009-02-04 20:55:57 +00002194 sqlite3 *pDest;
2195 sqlite3_backup *pBackup;
drhbc46f022013-01-23 18:53:23 +00002196 int j;
2197 for(j=1; j<nArg; j++){
2198 const char *z = azArg[j];
2199 if( z[0]=='-' ){
2200 while( z[0]=='-' ) z++;
drhaf664332013-07-18 20:28:29 +00002201 /* No options to process at this time */
drhbc46f022013-01-23 18:53:23 +00002202 {
2203 fprintf(stderr, "unknown option: %s\n", azArg[j]);
2204 return 1;
2205 }
2206 }else if( zDestFile==0 ){
2207 zDestFile = azArg[j];
2208 }else if( zDb==0 ){
2209 zDb = zDestFile;
2210 zDestFile = azArg[j];
2211 }else{
2212 fprintf(stderr, "too many arguments to .backup\n");
2213 return 1;
2214 }
drh9ff849f2009-02-04 20:55:57 +00002215 }
drhbc46f022013-01-23 18:53:23 +00002216 if( zDestFile==0 ){
2217 fprintf(stderr, "missing FILENAME argument on .backup\n");
2218 return 1;
2219 }
2220 if( zDb==0 ) zDb = "main";
drh9ff849f2009-02-04 20:55:57 +00002221 rc = sqlite3_open(zDestFile, &pDest);
2222 if( rc!=SQLITE_OK ){
shane9bd1b442009-10-23 01:27:39 +00002223 fprintf(stderr, "Error: cannot open \"%s\"\n", zDestFile);
drh9ff849f2009-02-04 20:55:57 +00002224 sqlite3_close(pDest);
2225 return 1;
2226 }
drh05782482013-10-24 15:20:20 +00002227 open_db(p, 0);
drh9ff849f2009-02-04 20:55:57 +00002228 pBackup = sqlite3_backup_init(pDest, "main", p->db, zDb);
2229 if( pBackup==0 ){
2230 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(pDest));
2231 sqlite3_close(pDest);
2232 return 1;
2233 }
2234 while( (rc = sqlite3_backup_step(pBackup,100))==SQLITE_OK ){}
2235 sqlite3_backup_finish(pBackup);
2236 if( rc==SQLITE_DONE ){
shane9bd1b442009-10-23 01:27:39 +00002237 rc = 0;
drh9ff849f2009-02-04 20:55:57 +00002238 }else{
2239 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(pDest));
shane9bd1b442009-10-23 01:27:39 +00002240 rc = 1;
drh9ff849f2009-02-04 20:55:57 +00002241 }
2242 sqlite3_close(pDest);
2243 }else
2244
shanehe2aa9d72009-11-06 17:20:17 +00002245 if( c=='b' && n>=3 && strncmp(azArg[0], "bail", n)==0 && nArg>1 && nArg<3 ){
drhc49f44e2006-10-26 18:15:42 +00002246 bail_on_error = booleanValue(azArg[1]);
2247 }else
2248
drhd8621b92012-04-17 09:09:33 +00002249 /* The undocumented ".breakpoint" command causes a call to the no-op
2250 ** routine named test_breakpoint().
2251 */
2252 if( c=='b' && n>=3 && strncmp(azArg[0], "breakpoint", n)==0 ){
2253 test_breakpoint();
2254 }else
2255
mistachkine31ae902014-02-06 01:15:29 +00002256 if( c=='c' && strncmp(azArg[0], "clone", n)==0 && nArg>1 && nArg<3 ){
2257 tryToClone(p, azArg[1]);
2258 }else
2259
shanehe2aa9d72009-11-06 17:20:17 +00002260 if( c=='d' && n>1 && strncmp(azArg[0], "databases", n)==0 && nArg==1 ){
jplyon672a1ed2003-05-11 20:07:05 +00002261 struct callback_data data;
2262 char *zErrMsg = 0;
drh05782482013-10-24 15:20:20 +00002263 open_db(p, 0);
jplyon672a1ed2003-05-11 20:07:05 +00002264 memcpy(&data, p, sizeof(data));
drhd8885442004-03-17 23:42:12 +00002265 data.showHeader = 1;
jplyon672a1ed2003-05-11 20:07:05 +00002266 data.mode = MODE_Column;
drhd8885442004-03-17 23:42:12 +00002267 data.colWidth[0] = 3;
2268 data.colWidth[1] = 15;
2269 data.colWidth[2] = 58;
drh0b2110c2004-10-26 00:08:10 +00002270 data.cnt = 0;
danielk19776f8a5032004-05-10 10:34:51 +00002271 sqlite3_exec(p->db, "PRAGMA database_list; ", callback, &data, &zErrMsg);
jplyon672a1ed2003-05-11 20:07:05 +00002272 if( zErrMsg ){
2273 fprintf(stderr,"Error: %s\n", zErrMsg);
drh3f4fedb2004-05-31 19:34:33 +00002274 sqlite3_free(zErrMsg);
shane9bd1b442009-10-23 01:27:39 +00002275 rc = 1;
jplyon6a65bb32003-05-04 07:25:57 +00002276 }
2277 }else
2278
shanehe2aa9d72009-11-06 17:20:17 +00002279 if( c=='d' && strncmp(azArg[0], "dump", n)==0 && nArg<3 ){
drh05782482013-10-24 15:20:20 +00002280 open_db(p, 0);
drhf1dfc4f2009-09-23 15:51:35 +00002281 /* When playing back a "dump", the content might appear in an order
2282 ** which causes immediate foreign key constraints to be violated.
2283 ** So disable foreign-key constraint enforcement to prevent problems. */
2284 fprintf(p->out, "PRAGMA foreign_keys=OFF;\n");
drh33048c02001-10-01 14:29:22 +00002285 fprintf(p->out, "BEGIN TRANSACTION;\n");
drh45e29d82006-11-20 16:21:10 +00002286 p->writableSchema = 0;
drh56197952011-10-13 16:30:13 +00002287 sqlite3_exec(p->db, "SAVEPOINT dump; PRAGMA writable_schema=ON", 0, 0, 0);
drh2f464a02011-10-13 00:41:49 +00002288 p->nErr = 0;
drh4c653a02000-06-07 01:27:47 +00002289 if( nArg==1 ){
drhdd3d4592004-08-30 01:54:05 +00002290 run_schema_dump_query(p,
drha18c5682000-10-08 22:20:57 +00002291 "SELECT name, type, sql FROM sqlite_master "
drh2f464a02011-10-13 00:41:49 +00002292 "WHERE sql NOT NULL AND type=='table' AND name!='sqlite_sequence'"
drh4f324762009-05-21 14:51:03 +00002293 );
2294 run_schema_dump_query(p,
2295 "SELECT name, type, sql FROM sqlite_master "
drh2f464a02011-10-13 00:41:49 +00002296 "WHERE name=='sqlite_sequence'"
drh0b9a5942006-09-13 20:22:02 +00002297 );
drh2f464a02011-10-13 00:41:49 +00002298 run_table_dump_query(p,
drh0b9a5942006-09-13 20:22:02 +00002299 "SELECT sql FROM sqlite_master "
drh157e29a2009-05-21 15:15:00 +00002300 "WHERE sql NOT NULL AND type IN ('index','trigger','view')", 0
drha18c5682000-10-08 22:20:57 +00002301 );
drh4c653a02000-06-07 01:27:47 +00002302 }else{
2303 int i;
drhdd3d4592004-08-30 01:54:05 +00002304 for(i=1; i<nArg; i++){
danielk1977bc6ada42004-06-30 08:20:16 +00002305 zShellStatic = azArg[i];
drhdd3d4592004-08-30 01:54:05 +00002306 run_schema_dump_query(p,
drha18c5682000-10-08 22:20:57 +00002307 "SELECT name, type, sql FROM sqlite_master "
drhdd3d4592004-08-30 01:54:05 +00002308 "WHERE tbl_name LIKE shellstatic() AND type=='table'"
drh2f464a02011-10-13 00:41:49 +00002309 " AND sql NOT NULL");
2310 run_table_dump_query(p,
drh0b9a5942006-09-13 20:22:02 +00002311 "SELECT sql FROM sqlite_master "
drh45e29d82006-11-20 16:21:10 +00002312 "WHERE sql NOT NULL"
2313 " AND type IN ('index','trigger','view')"
drh157e29a2009-05-21 15:15:00 +00002314 " AND tbl_name LIKE shellstatic()", 0
drh0b9a5942006-09-13 20:22:02 +00002315 );
danielk1977bc6ada42004-06-30 08:20:16 +00002316 zShellStatic = 0;
drh4c653a02000-06-07 01:27:47 +00002317 }
2318 }
drh45e29d82006-11-20 16:21:10 +00002319 if( p->writableSchema ){
drh56197952011-10-13 16:30:13 +00002320 fprintf(p->out, "PRAGMA writable_schema=OFF;\n");
drh45e29d82006-11-20 16:21:10 +00002321 p->writableSchema = 0;
2322 }
drh56197952011-10-13 16:30:13 +00002323 sqlite3_exec(p->db, "PRAGMA writable_schema=OFF;", 0, 0, 0);
2324 sqlite3_exec(p->db, "RELEASE dump;", 0, 0, 0);
drh2f464a02011-10-13 00:41:49 +00002325 fprintf(p->out, p->nErr ? "ROLLBACK; -- due to errors\n" : "COMMIT;\n");
drh4c653a02000-06-07 01:27:47 +00002326 }else
drh75897232000-05-29 14:26:00 +00002327
shanehe2aa9d72009-11-06 17:20:17 +00002328 if( c=='e' && strncmp(azArg[0], "echo", n)==0 && nArg>1 && nArg<3 ){
drhc28490c2006-10-26 14:25:58 +00002329 p->echoOn = booleanValue(azArg[1]);
drhdaffd0e2001-04-11 14:28:42 +00002330 }else
2331
drhefbf3b12014-02-28 20:47:24 +00002332 if( c=='e' && strncmp(azArg[0], "eqp", n)==0 && nArg>1 && nArg<3 ){
2333 p->autoEQP = booleanValue(azArg[1]);
2334 }else
2335
drhd3ac7d92013-01-25 18:33:43 +00002336 if( c=='e' && strncmp(azArg[0], "exit", n)==0 ){
drh348d19c2013-06-03 12:47:43 +00002337 if( nArg>1 && (rc = (int)integerValue(azArg[1]))!=0 ) exit(rc);
drh47ad6842006-11-08 12:25:42 +00002338 rc = 2;
drh75897232000-05-29 14:26:00 +00002339 }else
2340
shanehe2aa9d72009-11-06 17:20:17 +00002341 if( c=='e' && strncmp(azArg[0], "explain", n)==0 && nArg<3 ){
drhc28490c2006-10-26 14:25:58 +00002342 int val = nArg>=2 ? booleanValue(azArg[1]) : 1;
persicom7e2dfdd2002-04-18 02:46:52 +00002343 if(val == 1) {
2344 if(!p->explainPrev.valid) {
2345 p->explainPrev.valid = 1;
2346 p->explainPrev.mode = p->mode;
2347 p->explainPrev.showHeader = p->showHeader;
2348 memcpy(p->explainPrev.colWidth,p->colWidth,sizeof(p->colWidth));
2349 }
2350 /* We could put this code under the !p->explainValid
2351 ** condition so that it does not execute if we are already in
2352 ** explain mode. However, always executing it allows us an easy
2353 ** was to reset to explain mode in case the user previously
2354 ** did an .explain followed by a .width, .mode or .header
2355 ** command.
2356 */
danielk19770d78bae2008-01-03 07:09:48 +00002357 p->mode = MODE_Explain;
persicom7e2dfdd2002-04-18 02:46:52 +00002358 p->showHeader = 1;
drhac68ced2013-11-27 13:24:18 +00002359 memset(p->colWidth,0,sizeof(p->colWidth));
danielk19770d78bae2008-01-03 07:09:48 +00002360 p->colWidth[0] = 4; /* addr */
drh60a713c2008-01-21 16:22:45 +00002361 p->colWidth[1] = 13; /* opcode */
2362 p->colWidth[2] = 4; /* P1 */
2363 p->colWidth[3] = 4; /* P2 */
2364 p->colWidth[4] = 4; /* P3 */
2365 p->colWidth[5] = 13; /* P4 */
danielk19770d78bae2008-01-03 07:09:48 +00002366 p->colWidth[6] = 2; /* P5 */
drh60a713c2008-01-21 16:22:45 +00002367 p->colWidth[7] = 13; /* Comment */
persicom7e2dfdd2002-04-18 02:46:52 +00002368 }else if (p->explainPrev.valid) {
2369 p->explainPrev.valid = 0;
2370 p->mode = p->explainPrev.mode;
2371 p->showHeader = p->explainPrev.showHeader;
2372 memcpy(p->colWidth,p->explainPrev.colWidth,sizeof(p->colWidth));
2373 }
drh75897232000-05-29 14:26:00 +00002374 }else
2375
drhc28490c2006-10-26 14:25:58 +00002376 if( c=='h' && (strncmp(azArg[0], "header", n)==0 ||
shanehe2aa9d72009-11-06 17:20:17 +00002377 strncmp(azArg[0], "headers", n)==0) && nArg>1 && nArg<3 ){
drhc28490c2006-10-26 14:25:58 +00002378 p->showHeader = booleanValue(azArg[1]);
drh75897232000-05-29 14:26:00 +00002379 }else
2380
2381 if( c=='h' && strncmp(azArg[0], "help", n)==0 ){
drha81c64a2009-01-14 23:38:02 +00002382 fprintf(stderr,"%s",zHelp);
shaneb320ccd2009-10-21 03:42:58 +00002383 if( HAS_TIMER ){
2384 fprintf(stderr,"%s",zTimerHelp);
2385 }
drh75897232000-05-29 14:26:00 +00002386 }else
2387
shanehe2aa9d72009-11-06 17:20:17 +00002388 if( c=='i' && strncmp(azArg[0], "import", n)==0 && nArg==3 ){
drhfeac5f82004-08-01 00:10:45 +00002389 char *zTable = azArg[2]; /* Insert data into this table */
drh5bde8162013-06-27 14:07:53 +00002390 char *zFile = azArg[1]; /* Name of file to extra content from */
shane916f9612009-10-23 00:37:15 +00002391 sqlite3_stmt *pStmt = NULL; /* A statement */
drhfeac5f82004-08-01 00:10:45 +00002392 int nCol; /* Number of columns in the table */
2393 int nByte; /* Number of bytes in an SQL string */
2394 int i, j; /* Loop counters */
drh2d463112013-08-06 14:36:36 +00002395 int needCommit; /* True to COMMIT or ROLLBACK at end */
drhfeac5f82004-08-01 00:10:45 +00002396 int nSep; /* Number of bytes in p->separator[] */
2397 char *zSql; /* An SQL statement */
drhdb95f682013-06-26 22:46:00 +00002398 CSVReader sCsv; /* Reader context */
drh5bde8162013-06-27 14:07:53 +00002399 int (*xCloser)(FILE*); /* Procedure to close th3 connection */
drhfeac5f82004-08-01 00:10:45 +00002400
drhdb95f682013-06-26 22:46:00 +00002401 seenInterrupt = 0;
2402 memset(&sCsv, 0, sizeof(sCsv));
drh05782482013-10-24 15:20:20 +00002403 open_db(p, 0);
drh4f21c4a2008-12-10 22:15:00 +00002404 nSep = strlen30(p->separator);
drhfeac5f82004-08-01 00:10:45 +00002405 if( nSep==0 ){
shane916f9612009-10-23 00:37:15 +00002406 fprintf(stderr, "Error: non-null separator required for import\n");
2407 return 1;
drhfeac5f82004-08-01 00:10:45 +00002408 }
drhdb95f682013-06-26 22:46:00 +00002409 if( nSep>1 ){
2410 fprintf(stderr, "Error: multi-character separators not allowed"
2411 " for import\n");
2412 return 1;
2413 }
drh5bde8162013-06-27 14:07:53 +00002414 sCsv.zFile = zFile;
2415 sCsv.nLine = 1;
2416 if( sCsv.zFile[0]=='|' ){
2417 sCsv.in = popen(sCsv.zFile+1, "r");
2418 sCsv.zFile = "<pipe>";
2419 xCloser = pclose;
2420 }else{
2421 sCsv.in = fopen(sCsv.zFile, "rb");
2422 xCloser = fclose;
2423 }
drhdb95f682013-06-26 22:46:00 +00002424 if( sCsv.in==0 ){
drh5bde8162013-06-27 14:07:53 +00002425 fprintf(stderr, "Error: cannot open \"%s\"\n", zFile);
drhdb95f682013-06-26 22:46:00 +00002426 return 1;
2427 }
2428 sCsv.cSeparator = p->separator[0];
drh7b075e32011-09-28 01:10:00 +00002429 zSql = sqlite3_mprintf("SELECT * FROM %s", zTable);
shane916f9612009-10-23 00:37:15 +00002430 if( zSql==0 ){
2431 fprintf(stderr, "Error: out of memory\n");
drh5bde8162013-06-27 14:07:53 +00002432 xCloser(sCsv.in);
shane916f9612009-10-23 00:37:15 +00002433 return 1;
2434 }
drh4f21c4a2008-12-10 22:15:00 +00002435 nByte = strlen30(zSql);
drhc7181902014-02-27 15:04:13 +00002436 rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
dan6a8ac852014-05-26 18:27:12 +00002437 csv_append_char(&sCsv, 0); /* To ensure sCsv.z is allocated */
drhdb95f682013-06-26 22:46:00 +00002438 if( rc && sqlite3_strglob("no such table: *", sqlite3_errmsg(db))==0 ){
2439 char *zCreate = sqlite3_mprintf("CREATE TABLE %s", zTable);
2440 char cSep = '(';
2441 while( csv_read_one_field(&sCsv) ){
2442 zCreate = sqlite3_mprintf("%z%c\n \"%s\" TEXT", zCreate, cSep, sCsv.z);
2443 cSep = ',';
2444 if( sCsv.cTerm!=sCsv.cSeparator ) break;
2445 }
drh5bde8162013-06-27 14:07:53 +00002446 if( cSep=='(' ){
2447 sqlite3_free(zCreate);
2448 sqlite3_free(sCsv.z);
2449 xCloser(sCsv.in);
2450 fprintf(stderr,"%s: empty file\n", sCsv.zFile);
2451 return 1;
2452 }
drhdb95f682013-06-26 22:46:00 +00002453 zCreate = sqlite3_mprintf("%z\n)", zCreate);
2454 rc = sqlite3_exec(p->db, zCreate, 0, 0, 0);
2455 sqlite3_free(zCreate);
2456 if( rc ){
2457 fprintf(stderr, "CREATE TABLE %s(...) failed: %s\n", zTable,
2458 sqlite3_errmsg(db));
2459 sqlite3_free(sCsv.z);
drh5bde8162013-06-27 14:07:53 +00002460 xCloser(sCsv.in);
drhdb95f682013-06-26 22:46:00 +00002461 return 1;
2462 }
drhc7181902014-02-27 15:04:13 +00002463 rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
drhdb95f682013-06-26 22:46:00 +00002464 }
drhfeac5f82004-08-01 00:10:45 +00002465 sqlite3_free(zSql);
2466 if( rc ){
shane916f9612009-10-23 00:37:15 +00002467 if (pStmt) sqlite3_finalize(pStmt);
drhfeac5f82004-08-01 00:10:45 +00002468 fprintf(stderr,"Error: %s\n", sqlite3_errmsg(db));
drh5bde8162013-06-27 14:07:53 +00002469 xCloser(sCsv.in);
shane916f9612009-10-23 00:37:15 +00002470 return 1;
drhfeac5f82004-08-01 00:10:45 +00002471 }
shane916f9612009-10-23 00:37:15 +00002472 nCol = sqlite3_column_count(pStmt);
drhfeac5f82004-08-01 00:10:45 +00002473 sqlite3_finalize(pStmt);
shane916f9612009-10-23 00:37:15 +00002474 pStmt = 0;
shane9bd1b442009-10-23 01:27:39 +00002475 if( nCol==0 ) return 0; /* no columns, no error */
drhdb95f682013-06-26 22:46:00 +00002476 zSql = sqlite3_malloc( nByte*2 + 20 + nCol*2 );
shane916f9612009-10-23 00:37:15 +00002477 if( zSql==0 ){
2478 fprintf(stderr, "Error: out of memory\n");
drh5bde8162013-06-27 14:07:53 +00002479 xCloser(sCsv.in);
shane916f9612009-10-23 00:37:15 +00002480 return 1;
2481 }
drhdb95f682013-06-26 22:46:00 +00002482 sqlite3_snprintf(nByte+20, zSql, "INSERT INTO \"%w\" VALUES(?", zTable);
drh4f21c4a2008-12-10 22:15:00 +00002483 j = strlen30(zSql);
drhfeac5f82004-08-01 00:10:45 +00002484 for(i=1; i<nCol; i++){
2485 zSql[j++] = ',';
2486 zSql[j++] = '?';
2487 }
2488 zSql[j++] = ')';
2489 zSql[j] = 0;
drhc7181902014-02-27 15:04:13 +00002490 rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
drhdb95f682013-06-26 22:46:00 +00002491 sqlite3_free(zSql);
drhfeac5f82004-08-01 00:10:45 +00002492 if( rc ){
2493 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(db));
shane916f9612009-10-23 00:37:15 +00002494 if (pStmt) sqlite3_finalize(pStmt);
drh5bde8162013-06-27 14:07:53 +00002495 xCloser(sCsv.in);
drh47ad6842006-11-08 12:25:42 +00002496 return 1;
drhfeac5f82004-08-01 00:10:45 +00002497 }
drh2d463112013-08-06 14:36:36 +00002498 needCommit = sqlite3_get_autocommit(db);
2499 if( needCommit ) sqlite3_exec(db, "BEGIN", 0, 0, 0);
drhdb95f682013-06-26 22:46:00 +00002500 do{
2501 int startLine = sCsv.nLine;
drhfeac5f82004-08-01 00:10:45 +00002502 for(i=0; i<nCol; i++){
drhdb95f682013-06-26 22:46:00 +00002503 char *z = csv_read_one_field(&sCsv);
2504 if( z==0 && i==0 ) break;
2505 sqlite3_bind_text(pStmt, i+1, z, -1, SQLITE_TRANSIENT);
2506 if( i<nCol-1 && sCsv.cTerm!=sCsv.cSeparator ){
2507 fprintf(stderr, "%s:%d: expected %d columns but found %d - "
2508 "filling the rest with NULL\n",
2509 sCsv.zFile, startLine, nCol, i+1);
2510 i++;
2511 while( i<nCol ){ sqlite3_bind_null(pStmt, i); i++; }
drh18f52e02012-01-16 16:56:31 +00002512 }
drhfeac5f82004-08-01 00:10:45 +00002513 }
drhdb95f682013-06-26 22:46:00 +00002514 if( sCsv.cTerm==sCsv.cSeparator ){
2515 do{
2516 csv_read_one_field(&sCsv);
2517 i++;
2518 }while( sCsv.cTerm==sCsv.cSeparator );
2519 fprintf(stderr, "%s:%d: expected %d columns but found %d - "
2520 "extras ignored\n",
2521 sCsv.zFile, startLine, nCol, i);
drhfeac5f82004-08-01 00:10:45 +00002522 }
drhdb95f682013-06-26 22:46:00 +00002523 if( i>=nCol ){
2524 sqlite3_step(pStmt);
2525 rc = sqlite3_reset(pStmt);
2526 if( rc!=SQLITE_OK ){
2527 fprintf(stderr, "%s:%d: INSERT failed: %s\n", sCsv.zFile, startLine,
2528 sqlite3_errmsg(db));
2529 }
2530 }
2531 }while( sCsv.cTerm!=EOF );
2532
drh5bde8162013-06-27 14:07:53 +00002533 xCloser(sCsv.in);
drhdb95f682013-06-26 22:46:00 +00002534 sqlite3_free(sCsv.z);
drhfeac5f82004-08-01 00:10:45 +00002535 sqlite3_finalize(pStmt);
drh2d463112013-08-06 14:36:36 +00002536 if( needCommit ) sqlite3_exec(db, "COMMIT", 0, 0, 0);
drhfeac5f82004-08-01 00:10:45 +00002537 }else
2538
shanehe2aa9d72009-11-06 17:20:17 +00002539 if( c=='i' && strncmp(azArg[0], "indices", n)==0 && nArg<3 ){
drh75897232000-05-29 14:26:00 +00002540 struct callback_data data;
2541 char *zErrMsg = 0;
drh05782482013-10-24 15:20:20 +00002542 open_db(p, 0);
drh75897232000-05-29 14:26:00 +00002543 memcpy(&data, p, sizeof(data));
2544 data.showHeader = 0;
2545 data.mode = MODE_List;
shane86f5bdb2009-10-24 02:00:07 +00002546 if( nArg==1 ){
2547 rc = sqlite3_exec(p->db,
2548 "SELECT name FROM sqlite_master "
2549 "WHERE type='index' AND name NOT LIKE 'sqlite_%' "
2550 "UNION ALL "
2551 "SELECT name FROM sqlite_temp_master "
2552 "WHERE type='index' "
2553 "ORDER BY 1",
2554 callback, &data, &zErrMsg
2555 );
2556 }else{
2557 zShellStatic = azArg[1];
2558 rc = sqlite3_exec(p->db,
2559 "SELECT name FROM sqlite_master "
2560 "WHERE type='index' AND tbl_name LIKE shellstatic() "
2561 "UNION ALL "
2562 "SELECT name FROM sqlite_temp_master "
2563 "WHERE type='index' AND tbl_name LIKE shellstatic() "
2564 "ORDER BY 1",
2565 callback, &data, &zErrMsg
2566 );
2567 zShellStatic = 0;
2568 }
drh75897232000-05-29 14:26:00 +00002569 if( zErrMsg ){
2570 fprintf(stderr,"Error: %s\n", zErrMsg);
drh3f4fedb2004-05-31 19:34:33 +00002571 sqlite3_free(zErrMsg);
shane9bd1b442009-10-23 01:27:39 +00002572 rc = 1;
shane86f5bdb2009-10-24 02:00:07 +00002573 }else if( rc != SQLITE_OK ){
2574 fprintf(stderr,"Error: querying sqlite_master and sqlite_temp_master\n");
2575 rc = 1;
drh75897232000-05-29 14:26:00 +00002576 }
2577 }else
2578
drhae5e4452007-05-03 17:18:36 +00002579#ifdef SQLITE_ENABLE_IOTRACE
drhb0603412007-02-28 04:47:26 +00002580 if( c=='i' && strncmp(azArg[0], "iotrace", n)==0 ){
mlcreech3a00f902008-03-04 17:45:01 +00002581 extern void (*sqlite3IoTrace)(const char*, ...);
drhb0603412007-02-28 04:47:26 +00002582 if( iotrace && iotrace!=stdout ) fclose(iotrace);
2583 iotrace = 0;
2584 if( nArg<2 ){
mlcreech3a00f902008-03-04 17:45:01 +00002585 sqlite3IoTrace = 0;
drhb0603412007-02-28 04:47:26 +00002586 }else if( strcmp(azArg[1], "-")==0 ){
mlcreech3a00f902008-03-04 17:45:01 +00002587 sqlite3IoTrace = iotracePrintf;
drhb0603412007-02-28 04:47:26 +00002588 iotrace = stdout;
2589 }else{
2590 iotrace = fopen(azArg[1], "w");
2591 if( iotrace==0 ){
shane9bd1b442009-10-23 01:27:39 +00002592 fprintf(stderr, "Error: cannot open \"%s\"\n", azArg[1]);
mlcreech3a00f902008-03-04 17:45:01 +00002593 sqlite3IoTrace = 0;
shane9bd1b442009-10-23 01:27:39 +00002594 rc = 1;
drhb0603412007-02-28 04:47:26 +00002595 }else{
mlcreech3a00f902008-03-04 17:45:01 +00002596 sqlite3IoTrace = iotracePrintf;
drhb0603412007-02-28 04:47:26 +00002597 }
2598 }
2599 }else
drhae5e4452007-05-03 17:18:36 +00002600#endif
drhb0603412007-02-28 04:47:26 +00002601
drh70df4fe2006-06-13 15:12:21 +00002602#ifndef SQLITE_OMIT_LOAD_EXTENSION
drh1e397f82006-06-08 15:28:43 +00002603 if( c=='l' && strncmp(azArg[0], "load", n)==0 && nArg>=2 ){
2604 const char *zFile, *zProc;
2605 char *zErrMsg = 0;
drh1e397f82006-06-08 15:28:43 +00002606 zFile = azArg[1];
2607 zProc = nArg>=3 ? azArg[2] : 0;
drh05782482013-10-24 15:20:20 +00002608 open_db(p, 0);
drh1e397f82006-06-08 15:28:43 +00002609 rc = sqlite3_load_extension(p->db, zFile, zProc, &zErrMsg);
2610 if( rc!=SQLITE_OK ){
shane9bd1b442009-10-23 01:27:39 +00002611 fprintf(stderr, "Error: %s\n", zErrMsg);
drh1e397f82006-06-08 15:28:43 +00002612 sqlite3_free(zErrMsg);
drh47ad6842006-11-08 12:25:42 +00002613 rc = 1;
drh1e397f82006-06-08 15:28:43 +00002614 }
2615 }else
drh70df4fe2006-06-13 15:12:21 +00002616#endif
drh1e397f82006-06-08 15:28:43 +00002617
drhc8ba2122011-03-23 11:16:22 +00002618 if( c=='l' && strncmp(azArg[0], "log", n)==0 && nArg>=2 ){
drh127f9d72010-02-23 01:47:00 +00002619 const char *zFile = azArg[1];
drh42f64e52012-04-04 16:56:23 +00002620 output_file_close(p->pLog);
2621 p->pLog = output_file_open(zFile);
drh127f9d72010-02-23 01:47:00 +00002622 }else
2623
shanehe2aa9d72009-11-06 17:20:17 +00002624 if( c=='m' && strncmp(azArg[0], "mode", n)==0 && nArg==2 ){
drh4f21c4a2008-12-10 22:15:00 +00002625 int n2 = strlen30(azArg[1]);
shanehe2aa9d72009-11-06 17:20:17 +00002626 if( (n2==4 && strncmp(azArg[1],"line",n2)==0)
persicom7e2dfdd2002-04-18 02:46:52 +00002627 ||
shanehe2aa9d72009-11-06 17:20:17 +00002628 (n2==5 && strncmp(azArg[1],"lines",n2)==0) ){
drh75897232000-05-29 14:26:00 +00002629 p->mode = MODE_Line;
shanehe2aa9d72009-11-06 17:20:17 +00002630 }else if( (n2==6 && strncmp(azArg[1],"column",n2)==0)
persicom7e2dfdd2002-04-18 02:46:52 +00002631 ||
shanehe2aa9d72009-11-06 17:20:17 +00002632 (n2==7 && strncmp(azArg[1],"columns",n2)==0) ){
drh75897232000-05-29 14:26:00 +00002633 p->mode = MODE_Column;
shanehe2aa9d72009-11-06 17:20:17 +00002634 }else if( n2==4 && strncmp(azArg[1],"list",n2)==0 ){
drh75897232000-05-29 14:26:00 +00002635 p->mode = MODE_List;
shanehe2aa9d72009-11-06 17:20:17 +00002636 }else if( n2==4 && strncmp(azArg[1],"html",n2)==0 ){
drh1e5d0e92000-05-31 23:33:17 +00002637 p->mode = MODE_Html;
shanehe2aa9d72009-11-06 17:20:17 +00002638 }else if( n2==3 && strncmp(azArg[1],"tcl",n2)==0 ){
drhfeac5f82004-08-01 00:10:45 +00002639 p->mode = MODE_Tcl;
mistachkin585dcb22012-12-04 00:23:43 +00002640 sqlite3_snprintf(sizeof(p->separator), p->separator, " ");
shanehe2aa9d72009-11-06 17:20:17 +00002641 }else if( n2==3 && strncmp(azArg[1],"csv",n2)==0 ){
drh8e64d1c2004-10-07 00:32:39 +00002642 p->mode = MODE_Csv;
drh5bb3eb92007-05-04 13:15:55 +00002643 sqlite3_snprintf(sizeof(p->separator), p->separator, ",");
shanehe2aa9d72009-11-06 17:20:17 +00002644 }else if( n2==4 && strncmp(azArg[1],"tabs",n2)==0 ){
drhfeac5f82004-08-01 00:10:45 +00002645 p->mode = MODE_List;
drh5bb3eb92007-05-04 13:15:55 +00002646 sqlite3_snprintf(sizeof(p->separator), p->separator, "\t");
shanehe2aa9d72009-11-06 17:20:17 +00002647 }else if( n2==6 && strncmp(azArg[1],"insert",n2)==0 ){
drh28bd4bc2000-06-15 15:57:22 +00002648 p->mode = MODE_Insert;
shanehe2aa9d72009-11-06 17:20:17 +00002649 set_table_name(p, "table");
drhdaffd0e2001-04-11 14:28:42 +00002650 }else {
shane9bd1b442009-10-23 01:27:39 +00002651 fprintf(stderr,"Error: mode should be one of: "
drhfeac5f82004-08-01 00:10:45 +00002652 "column csv html insert line list tabs tcl\n");
shane9bd1b442009-10-23 01:27:39 +00002653 rc = 1;
drh75897232000-05-29 14:26:00 +00002654 }
2655 }else
2656
shanehe2aa9d72009-11-06 17:20:17 +00002657 if( c=='m' && strncmp(azArg[0], "mode", n)==0 && nArg==3 ){
2658 int n2 = strlen30(azArg[1]);
2659 if( n2==6 && strncmp(azArg[1],"insert",n2)==0 ){
2660 p->mode = MODE_Insert;
2661 set_table_name(p, azArg[2]);
2662 }else {
2663 fprintf(stderr, "Error: invalid arguments: "
2664 " \"%s\". Enter \".help\" for help\n", azArg[2]);
2665 rc = 1;
2666 }
2667 }else
2668
persicom7e2dfdd2002-04-18 02:46:52 +00002669 if( c=='n' && strncmp(azArg[0], "nullvalue", n)==0 && nArg==2 ) {
drh5bb3eb92007-05-04 13:15:55 +00002670 sqlite3_snprintf(sizeof(p->nullvalue), p->nullvalue,
2671 "%.*s", (int)ArraySize(p->nullvalue)-1, azArg[1]);
persicom7e2dfdd2002-04-18 02:46:52 +00002672 }else
2673
drh05782482013-10-24 15:20:20 +00002674 if( c=='o' && strncmp(azArg[0], "open", n)==0 && n>=2 ){
2675 sqlite3 *savedDb = p->db;
2676 const char *zSavedFilename = p->zDbFilename;
2677 char *zNewFilename = 0;
2678 p->db = 0;
2679 if( nArg>=2 ){
2680 p->zDbFilename = zNewFilename = sqlite3_mprintf("%s", azArg[1]);
2681 }
2682 open_db(p, 1);
2683 if( p->db!=0 ){
2684 sqlite3_close(savedDb);
2685 sqlite3_free(p->zFreeOnClose);
2686 p->zFreeOnClose = zNewFilename;
2687 }else{
2688 sqlite3_free(zNewFilename);
2689 p->db = savedDb;
2690 p->zDbFilename = zSavedFilename;
2691 }
2692 }else
2693
drh75897232000-05-29 14:26:00 +00002694 if( c=='o' && strncmp(azArg[0], "output", n)==0 && nArg==2 ){
drh42f64e52012-04-04 16:56:23 +00002695 if( p->outfile[0]=='|' ){
2696 pclose(p->out);
2697 }else{
2698 output_file_close(p->out);
drh75897232000-05-29 14:26:00 +00002699 }
drh42f64e52012-04-04 16:56:23 +00002700 p->outfile[0] = 0;
2701 if( azArg[1][0]=='|' ){
drhe1da8fa2012-03-30 00:05:57 +00002702 p->out = popen(&azArg[1][1], "w");
2703 if( p->out==0 ){
2704 fprintf(stderr,"Error: cannot open pipe \"%s\"\n", &azArg[1][1]);
2705 p->out = stdout;
2706 rc = 1;
2707 }else{
2708 sqlite3_snprintf(sizeof(p->outfile), p->outfile, "%s", azArg[1]);
2709 }
drh75897232000-05-29 14:26:00 +00002710 }else{
drh42f64e52012-04-04 16:56:23 +00002711 p->out = output_file_open(azArg[1]);
drh75897232000-05-29 14:26:00 +00002712 if( p->out==0 ){
drh42f64e52012-04-04 16:56:23 +00002713 if( strcmp(azArg[1],"off")!=0 ){
2714 fprintf(stderr,"Error: cannot write to \"%s\"\n", azArg[1]);
2715 }
drh75897232000-05-29 14:26:00 +00002716 p->out = stdout;
shane9bd1b442009-10-23 01:27:39 +00002717 rc = 1;
persicom7e2dfdd2002-04-18 02:46:52 +00002718 } else {
drh42f64e52012-04-04 16:56:23 +00002719 sqlite3_snprintf(sizeof(p->outfile), p->outfile, "%s", azArg[1]);
drh75897232000-05-29 14:26:00 +00002720 }
2721 }
2722 }else
2723
drh078b1fd2012-09-21 13:40:02 +00002724 if( c=='p' && n>=3 && strncmp(azArg[0], "print", n)==0 ){
2725 int i;
2726 for(i=1; i<nArg; i++){
2727 if( i>1 ) fprintf(p->out, " ");
2728 fprintf(p->out, "%s", azArg[i]);
2729 }
2730 fprintf(p->out, "\n");
2731 }else
2732
drhdd45df82002-04-18 12:39:03 +00002733 if( c=='p' && strncmp(azArg[0], "prompt", n)==0 && (nArg==2 || nArg==3)){
persicom7e2dfdd2002-04-18 02:46:52 +00002734 if( nArg >= 2) {
2735 strncpy(mainPrompt,azArg[1],(int)ArraySize(mainPrompt)-1);
2736 }
2737 if( nArg >= 3) {
2738 strncpy(continuePrompt,azArg[2],(int)ArraySize(continuePrompt)-1);
2739 }
2740 }else
2741
shanehe2aa9d72009-11-06 17:20:17 +00002742 if( c=='q' && strncmp(azArg[0], "quit", n)==0 && nArg==1 ){
drh47ad6842006-11-08 12:25:42 +00002743 rc = 2;
persicom7e2dfdd2002-04-18 02:46:52 +00002744 }else
2745
drh9ff849f2009-02-04 20:55:57 +00002746 if( c=='r' && n>=3 && strncmp(azArg[0], "read", n)==0 && nArg==2 ){
drha1f9b5e2004-02-14 16:31:02 +00002747 FILE *alt = fopen(azArg[1], "rb");
drhdaffd0e2001-04-11 14:28:42 +00002748 if( alt==0 ){
shane9bd1b442009-10-23 01:27:39 +00002749 fprintf(stderr,"Error: cannot open \"%s\"\n", azArg[1]);
2750 rc = 1;
drhdaffd0e2001-04-11 14:28:42 +00002751 }else{
shane9bd1b442009-10-23 01:27:39 +00002752 rc = process_input(p, alt);
drhdaffd0e2001-04-11 14:28:42 +00002753 fclose(alt);
2754 }
2755 }else
2756
shanehe2aa9d72009-11-06 17:20:17 +00002757 if( c=='r' && n>=3 && strncmp(azArg[0], "restore", n)==0 && nArg>1 && nArg<4){
drh9ff849f2009-02-04 20:55:57 +00002758 const char *zSrcFile;
2759 const char *zDb;
2760 sqlite3 *pSrc;
2761 sqlite3_backup *pBackup;
drhdc2c4912009-02-04 22:46:47 +00002762 int nTimeout = 0;
2763
drh9ff849f2009-02-04 20:55:57 +00002764 if( nArg==2 ){
2765 zSrcFile = azArg[1];
2766 zDb = "main";
2767 }else{
2768 zSrcFile = azArg[2];
2769 zDb = azArg[1];
2770 }
2771 rc = sqlite3_open(zSrcFile, &pSrc);
2772 if( rc!=SQLITE_OK ){
shane9bd1b442009-10-23 01:27:39 +00002773 fprintf(stderr, "Error: cannot open \"%s\"\n", zSrcFile);
drh9ff849f2009-02-04 20:55:57 +00002774 sqlite3_close(pSrc);
2775 return 1;
2776 }
drh05782482013-10-24 15:20:20 +00002777 open_db(p, 0);
drh9ff849f2009-02-04 20:55:57 +00002778 pBackup = sqlite3_backup_init(p->db, zDb, pSrc, "main");
2779 if( pBackup==0 ){
2780 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(p->db));
2781 sqlite3_close(pSrc);
2782 return 1;
2783 }
drhdc2c4912009-02-04 22:46:47 +00002784 while( (rc = sqlite3_backup_step(pBackup,100))==SQLITE_OK
2785 || rc==SQLITE_BUSY ){
2786 if( rc==SQLITE_BUSY ){
2787 if( nTimeout++ >= 3 ) break;
2788 sqlite3_sleep(100);
drh9ff849f2009-02-04 20:55:57 +00002789 }
2790 }
2791 sqlite3_backup_finish(pBackup);
2792 if( rc==SQLITE_DONE ){
shane9bd1b442009-10-23 01:27:39 +00002793 rc = 0;
drhdc2c4912009-02-04 22:46:47 +00002794 }else if( rc==SQLITE_BUSY || rc==SQLITE_LOCKED ){
shane9bd1b442009-10-23 01:27:39 +00002795 fprintf(stderr, "Error: source database is busy\n");
2796 rc = 1;
drh9ff849f2009-02-04 20:55:57 +00002797 }else{
2798 fprintf(stderr, "Error: %s\n", sqlite3_errmsg(p->db));
shane9bd1b442009-10-23 01:27:39 +00002799 rc = 1;
drh9ff849f2009-02-04 20:55:57 +00002800 }
2801 sqlite3_close(pSrc);
2802 }else
2803
shanehe2aa9d72009-11-06 17:20:17 +00002804 if( c=='s' && strncmp(azArg[0], "schema", n)==0 && nArg<3 ){
drh75897232000-05-29 14:26:00 +00002805 struct callback_data data;
2806 char *zErrMsg = 0;
drh05782482013-10-24 15:20:20 +00002807 open_db(p, 0);
drh75897232000-05-29 14:26:00 +00002808 memcpy(&data, p, sizeof(data));
2809 data.showHeader = 0;
drhe3710332000-09-29 13:30:53 +00002810 data.mode = MODE_Semi;
drh75897232000-05-29 14:26:00 +00002811 if( nArg>1 ){
drhc8d74412004-08-31 23:41:26 +00002812 int i;
drhf0693c82011-10-11 20:41:54 +00002813 for(i=0; azArg[1][i]; i++) azArg[1][i] = ToLower(azArg[1][i]);
drhc8d74412004-08-31 23:41:26 +00002814 if( strcmp(azArg[1],"sqlite_master")==0 ){
drha18c5682000-10-08 22:20:57 +00002815 char *new_argv[2], *new_colv[2];
2816 new_argv[0] = "CREATE TABLE sqlite_master (\n"
2817 " type text,\n"
2818 " name text,\n"
2819 " tbl_name text,\n"
drhadbca9c2001-09-27 15:11:53 +00002820 " rootpage integer,\n"
drha18c5682000-10-08 22:20:57 +00002821 " sql text\n"
2822 ")";
2823 new_argv[1] = 0;
2824 new_colv[0] = "sql";
2825 new_colv[1] = 0;
2826 callback(&data, 1, new_argv, new_colv);
shane9bd1b442009-10-23 01:27:39 +00002827 rc = SQLITE_OK;
drhc8d74412004-08-31 23:41:26 +00002828 }else if( strcmp(azArg[1],"sqlite_temp_master")==0 ){
drhe0bc4042002-06-25 01:09:11 +00002829 char *new_argv[2], *new_colv[2];
2830 new_argv[0] = "CREATE TEMP TABLE sqlite_temp_master (\n"
2831 " type text,\n"
2832 " name text,\n"
2833 " tbl_name text,\n"
2834 " rootpage integer,\n"
2835 " sql text\n"
2836 ")";
2837 new_argv[1] = 0;
2838 new_colv[0] = "sql";
2839 new_colv[1] = 0;
2840 callback(&data, 1, new_argv, new_colv);
shane9bd1b442009-10-23 01:27:39 +00002841 rc = SQLITE_OK;
drha18c5682000-10-08 22:20:57 +00002842 }else{
danielk1977bc6ada42004-06-30 08:20:16 +00002843 zShellStatic = azArg[1];
shane9bd1b442009-10-23 01:27:39 +00002844 rc = sqlite3_exec(p->db,
drhe0bc4042002-06-25 01:09:11 +00002845 "SELECT sql FROM "
drhac43e982012-05-21 03:15:06 +00002846 " (SELECT sql sql, type type, tbl_name tbl_name, name name, rowid x"
drh8f800a72009-01-14 23:17:55 +00002847 " FROM sqlite_master UNION ALL"
drhac43e982012-05-21 03:15:06 +00002848 " SELECT sql, type, tbl_name, name, rowid FROM sqlite_temp_master) "
drh6ac7a582011-11-04 00:35:56 +00002849 "WHERE lower(tbl_name) LIKE shellstatic()"
2850 " AND type!='meta' AND sql NOTNULL "
drh1ba00292013-05-06 21:01:06 +00002851 "ORDER BY rowid",
danielk1977bc6ada42004-06-30 08:20:16 +00002852 callback, &data, &zErrMsg);
2853 zShellStatic = 0;
drha18c5682000-10-08 22:20:57 +00002854 }
drh75897232000-05-29 14:26:00 +00002855 }else{
shane9bd1b442009-10-23 01:27:39 +00002856 rc = sqlite3_exec(p->db,
drhe0bc4042002-06-25 01:09:11 +00002857 "SELECT sql FROM "
drhac43e982012-05-21 03:15:06 +00002858 " (SELECT sql sql, type type, tbl_name tbl_name, name name, rowid x"
drh8f800a72009-01-14 23:17:55 +00002859 " FROM sqlite_master UNION ALL"
drhac43e982012-05-21 03:15:06 +00002860 " SELECT sql, type, tbl_name, name, rowid FROM sqlite_temp_master) "
drh0c356672005-09-10 22:40:53 +00002861 "WHERE type!='meta' AND sql NOTNULL AND name NOT LIKE 'sqlite_%'"
drh1ba00292013-05-06 21:01:06 +00002862 "ORDER BY rowid",
drha18c5682000-10-08 22:20:57 +00002863 callback, &data, &zErrMsg
2864 );
drh75897232000-05-29 14:26:00 +00002865 }
drh75897232000-05-29 14:26:00 +00002866 if( zErrMsg ){
2867 fprintf(stderr,"Error: %s\n", zErrMsg);
drh3f4fedb2004-05-31 19:34:33 +00002868 sqlite3_free(zErrMsg);
shane9bd1b442009-10-23 01:27:39 +00002869 rc = 1;
2870 }else if( rc != SQLITE_OK ){
2871 fprintf(stderr,"Error: querying schema information\n");
2872 rc = 1;
2873 }else{
2874 rc = 0;
drh75897232000-05-29 14:26:00 +00002875 }
2876 }else
2877
drh340f5822013-06-27 13:01:21 +00002878#ifdef SQLITE_DEBUG
drh348d19c2013-06-03 12:47:43 +00002879 /* Undocumented commands for internal testing. Subject to change
2880 ** without notice. */
2881 if( c=='s' && n>=10 && strncmp(azArg[0], "selftest-", 9)==0 ){
2882 if( strncmp(azArg[0]+9, "boolean", n-9)==0 ){
2883 int i, v;
2884 for(i=1; i<nArg; i++){
2885 v = booleanValue(azArg[i]);
2886 fprintf(p->out, "%s: %d 0x%x\n", azArg[i], v, v);
2887 }
2888 }
2889 if( strncmp(azArg[0]+9, "integer", n-9)==0 ){
2890 int i; sqlite3_int64 v;
2891 for(i=1; i<nArg; i++){
drh340f5822013-06-27 13:01:21 +00002892 char zBuf[200];
drh348d19c2013-06-03 12:47:43 +00002893 v = integerValue(azArg[i]);
drh340f5822013-06-27 13:01:21 +00002894 sqlite3_snprintf(sizeof(zBuf), zBuf, "%s: %lld 0x%llx\n", azArg[i], v, v);
2895 fprintf(p->out, "%s", zBuf);
drh348d19c2013-06-03 12:47:43 +00002896 }
2897 }
2898 }else
drh340f5822013-06-27 13:01:21 +00002899#endif
drh348d19c2013-06-03 12:47:43 +00002900
drh75897232000-05-29 14:26:00 +00002901 if( c=='s' && strncmp(azArg[0], "separator", n)==0 && nArg==2 ){
drh5bb3eb92007-05-04 13:15:55 +00002902 sqlite3_snprintf(sizeof(p->separator), p->separator,
2903 "%.*s", (int)sizeof(p->separator)-1, azArg[1]);
drh75897232000-05-29 14:26:00 +00002904 }else
2905
drh62cdde52014-05-28 20:22:28 +00002906 if( c=='s'
2907 && (strncmp(azArg[0], "shell", n)==0 || strncmp(azArg[0],"system",n)==0)
2908 && nArg>=2
2909 ){
2910 char *zCmd;
2911 int i;
drhdcb3e3d2014-05-29 03:17:29 +00002912 zCmd = sqlite3_mprintf(strchr(azArg[1],' ')==0?"%s":"\"%s\"", azArg[1]);
drh62cdde52014-05-28 20:22:28 +00002913 for(i=2; i<nArg; i++){
drhdcb3e3d2014-05-29 03:17:29 +00002914 zCmd = sqlite3_mprintf(strchr(azArg[i],' ')==0?"%z %s":"%z \"%s\"",
2915 zCmd, azArg[i]);
drh62cdde52014-05-28 20:22:28 +00002916 }
2917 system(zCmd);
2918 sqlite3_free(zCmd);
2919 }else
2920
shanehe2aa9d72009-11-06 17:20:17 +00002921 if( c=='s' && strncmp(azArg[0], "show", n)==0 && nArg==1 ){
persicom7e2dfdd2002-04-18 02:46:52 +00002922 int i;
2923 fprintf(p->out,"%9.9s: %s\n","echo", p->echoOn ? "on" : "off");
drhefbf3b12014-02-28 20:47:24 +00002924 fprintf(p->out,"%9.9s: %s\n","eqp", p->autoEQP ? "on" : "off");
drh67505e72002-04-19 12:34:06 +00002925 fprintf(p->out,"%9.9s: %s\n","explain", p->explainPrev.valid ? "on" :"off");
drhdd45df82002-04-18 12:39:03 +00002926 fprintf(p->out,"%9.9s: %s\n","headers", p->showHeader ? "on" : "off");
persicom7e2dfdd2002-04-18 02:46:52 +00002927 fprintf(p->out,"%9.9s: %s\n","mode", modeDescr[p->mode]);
drhfeac5f82004-08-01 00:10:45 +00002928 fprintf(p->out,"%9.9s: ", "nullvalue");
2929 output_c_string(p->out, p->nullvalue);
2930 fprintf(p->out, "\n");
drh67505e72002-04-19 12:34:06 +00002931 fprintf(p->out,"%9.9s: %s\n","output",
drh4f21c4a2008-12-10 22:15:00 +00002932 strlen30(p->outfile) ? p->outfile : "stdout");
drhfeac5f82004-08-01 00:10:45 +00002933 fprintf(p->out,"%9.9s: ", "separator");
2934 output_c_string(p->out, p->separator);
2935 fprintf(p->out, "\n");
shaneh642d8b82010-07-28 16:05:34 +00002936 fprintf(p->out,"%9.9s: %s\n","stats", p->statsOn ? "on" : "off");
persicom7e2dfdd2002-04-18 02:46:52 +00002937 fprintf(p->out,"%9.9s: ","width");
2938 for (i=0;i<(int)ArraySize(p->colWidth) && p->colWidth[i] != 0;i++) {
drhfeac5f82004-08-01 00:10:45 +00002939 fprintf(p->out,"%d ",p->colWidth[i]);
persicom7e2dfdd2002-04-18 02:46:52 +00002940 }
drhfeac5f82004-08-01 00:10:45 +00002941 fprintf(p->out,"\n");
persicom7e2dfdd2002-04-18 02:46:52 +00002942 }else
2943
shaneh642d8b82010-07-28 16:05:34 +00002944 if( c=='s' && strncmp(azArg[0], "stats", n)==0 && nArg>1 && nArg<3 ){
2945 p->statsOn = booleanValue(azArg[1]);
2946 }else
2947
shanehe2aa9d72009-11-06 17:20:17 +00002948 if( c=='t' && n>1 && strncmp(azArg[0], "tables", n)==0 && nArg<3 ){
drh98781232012-04-23 12:38:05 +00002949 sqlite3_stmt *pStmt;
drhe3710332000-09-29 13:30:53 +00002950 char **azResult;
drh98781232012-04-23 12:38:05 +00002951 int nRow, nAlloc;
2952 char *zSql = 0;
2953 int ii;
drh05782482013-10-24 15:20:20 +00002954 open_db(p, 0);
drh98781232012-04-23 12:38:05 +00002955 rc = sqlite3_prepare_v2(p->db, "PRAGMA database_list", -1, &pStmt, 0);
2956 if( rc ) return rc;
2957 zSql = sqlite3_mprintf(
2958 "SELECT name FROM sqlite_master"
2959 " WHERE type IN ('table','view')"
2960 " AND name NOT LIKE 'sqlite_%%'"
2961 " AND name LIKE ?1");
2962 while( sqlite3_step(pStmt)==SQLITE_ROW ){
2963 const char *zDbName = (const char*)sqlite3_column_text(pStmt, 1);
2964 if( zDbName==0 || strcmp(zDbName,"main")==0 ) continue;
2965 if( strcmp(zDbName,"temp")==0 ){
2966 zSql = sqlite3_mprintf(
2967 "%z UNION ALL "
2968 "SELECT 'temp.' || name FROM sqlite_temp_master"
2969 " WHERE type IN ('table','view')"
2970 " AND name NOT LIKE 'sqlite_%%'"
2971 " AND name LIKE ?1", zSql);
2972 }else{
2973 zSql = sqlite3_mprintf(
2974 "%z UNION ALL "
2975 "SELECT '%q.' || name FROM \"%w\".sqlite_master"
2976 " WHERE type IN ('table','view')"
2977 " AND name NOT LIKE 'sqlite_%%'"
2978 " AND name LIKE ?1", zSql, zDbName, zDbName);
2979 }
drha50da102000-08-08 20:19:09 +00002980 }
drh98781232012-04-23 12:38:05 +00002981 sqlite3_finalize(pStmt);
2982 zSql = sqlite3_mprintf("%z ORDER BY 1", zSql);
2983 rc = sqlite3_prepare_v2(p->db, zSql, -1, &pStmt, 0);
2984 sqlite3_free(zSql);
2985 if( rc ) return rc;
2986 nRow = nAlloc = 0;
2987 azResult = 0;
2988 if( nArg>1 ){
2989 sqlite3_bind_text(pStmt, 1, azArg[1], -1, SQLITE_TRANSIENT);
shane9bd1b442009-10-23 01:27:39 +00002990 }else{
drh98781232012-04-23 12:38:05 +00002991 sqlite3_bind_text(pStmt, 1, "%", -1, SQLITE_STATIC);
2992 }
2993 while( sqlite3_step(pStmt)==SQLITE_ROW ){
2994 if( nRow>=nAlloc ){
2995 char **azNew;
2996 int n = nAlloc*2 + 10;
2997 azNew = sqlite3_realloc(azResult, sizeof(azResult[0])*n);
2998 if( azNew==0 ){
2999 fprintf(stderr, "Error: out of memory\n");
3000 break;
3001 }
3002 nAlloc = n;
3003 azResult = azNew;
3004 }
3005 azResult[nRow] = sqlite3_mprintf("%s", sqlite3_column_text(pStmt, 0));
3006 if( azResult[nRow] ) nRow++;
3007 }
3008 sqlite3_finalize(pStmt);
3009 if( nRow>0 ){
drhe3710332000-09-29 13:30:53 +00003010 int len, maxlen = 0;
3011 int i, j;
3012 int nPrintCol, nPrintRow;
drh98781232012-04-23 12:38:05 +00003013 for(i=0; i<nRow; i++){
drh4f21c4a2008-12-10 22:15:00 +00003014 len = strlen30(azResult[i]);
drhe3710332000-09-29 13:30:53 +00003015 if( len>maxlen ) maxlen = len;
3016 }
3017 nPrintCol = 80/(maxlen+2);
3018 if( nPrintCol<1 ) nPrintCol = 1;
3019 nPrintRow = (nRow + nPrintCol - 1)/nPrintCol;
3020 for(i=0; i<nPrintRow; i++){
drh98781232012-04-23 12:38:05 +00003021 for(j=i; j<nRow; j+=nPrintRow){
3022 char *zSp = j<nPrintRow ? "" : " ";
drh151b7d52013-05-06 20:28:54 +00003023 fprintf(p->out, "%s%-*s", zSp, maxlen, azResult[j] ? azResult[j] : "");
drhe3710332000-09-29 13:30:53 +00003024 }
drh151b7d52013-05-06 20:28:54 +00003025 fprintf(p->out, "\n");
drhe3710332000-09-29 13:30:53 +00003026 }
3027 }
drh98781232012-04-23 12:38:05 +00003028 for(ii=0; ii<nRow; ii++) sqlite3_free(azResult[ii]);
3029 sqlite3_free(azResult);
drh75897232000-05-29 14:26:00 +00003030 }else
3031
shaneh96887e12011-02-10 21:08:58 +00003032 if( c=='t' && n>=8 && strncmp(azArg[0], "testctrl", n)==0 && nArg>=2 ){
drhd416fe72011-03-17 16:45:50 +00003033 static const struct {
3034 const char *zCtrlName; /* Name of a test-control option */
3035 int ctrlCode; /* Integer code for that option */
3036 } aCtrl[] = {
3037 { "prng_save", SQLITE_TESTCTRL_PRNG_SAVE },
3038 { "prng_restore", SQLITE_TESTCTRL_PRNG_RESTORE },
3039 { "prng_reset", SQLITE_TESTCTRL_PRNG_RESET },
3040 { "bitvec_test", SQLITE_TESTCTRL_BITVEC_TEST },
3041 { "fault_install", SQLITE_TESTCTRL_FAULT_INSTALL },
3042 { "benign_malloc_hooks", SQLITE_TESTCTRL_BENIGN_MALLOC_HOOKS },
3043 { "pending_byte", SQLITE_TESTCTRL_PENDING_BYTE },
3044 { "assert", SQLITE_TESTCTRL_ASSERT },
3045 { "always", SQLITE_TESTCTRL_ALWAYS },
3046 { "reserve", SQLITE_TESTCTRL_RESERVE },
3047 { "optimizations", SQLITE_TESTCTRL_OPTIMIZATIONS },
3048 { "iskeyword", SQLITE_TESTCTRL_ISKEYWORD },
drhd416fe72011-03-17 16:45:50 +00003049 { "scratchmalloc", SQLITE_TESTCTRL_SCRATCHMALLOC },
drh2cf4acb2014-04-18 00:06:02 +00003050 { "byteorder", SQLITE_TESTCTRL_BYTEORDER },
drhd416fe72011-03-17 16:45:50 +00003051 };
shaneh96887e12011-02-10 21:08:58 +00003052 int testctrl = -1;
3053 int rc = 0;
drhd416fe72011-03-17 16:45:50 +00003054 int i, n;
drh05782482013-10-24 15:20:20 +00003055 open_db(p, 0);
shaneh96887e12011-02-10 21:08:58 +00003056
drhd416fe72011-03-17 16:45:50 +00003057 /* convert testctrl text option to value. allow any unique prefix
3058 ** of the option name, or a numerical value. */
shanehcef83682011-04-07 03:41:01 +00003059 n = strlen30(azArg[1]);
drhfcd71b62011-04-05 22:08:24 +00003060 for(i=0; i<(int)(sizeof(aCtrl)/sizeof(aCtrl[0])); i++){
drhd416fe72011-03-17 16:45:50 +00003061 if( strncmp(azArg[1], aCtrl[i].zCtrlName, n)==0 ){
3062 if( testctrl<0 ){
3063 testctrl = aCtrl[i].ctrlCode;
3064 }else{
drhb07028f2011-10-14 21:49:18 +00003065 fprintf(stderr, "ambiguous option name: \"%s\"\n", azArg[1]);
drhd416fe72011-03-17 16:45:50 +00003066 testctrl = -1;
3067 break;
3068 }
3069 }
3070 }
drh348d19c2013-06-03 12:47:43 +00003071 if( testctrl<0 ) testctrl = (int)integerValue(azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003072 if( (testctrl<SQLITE_TESTCTRL_FIRST) || (testctrl>SQLITE_TESTCTRL_LAST) ){
3073 fprintf(stderr,"Error: invalid testctrl option: %s\n", azArg[1]);
3074 }else{
3075 switch(testctrl){
3076
3077 /* sqlite3_test_control(int, db, int) */
3078 case SQLITE_TESTCTRL_OPTIMIZATIONS:
3079 case SQLITE_TESTCTRL_RESERVE:
3080 if( nArg==3 ){
3081 int opt = (int)strtol(azArg[2], 0, 0);
3082 rc = sqlite3_test_control(testctrl, p->db, opt);
drh151b7d52013-05-06 20:28:54 +00003083 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003084 } else {
drhd416fe72011-03-17 16:45:50 +00003085 fprintf(stderr,"Error: testctrl %s takes a single int option\n",
3086 azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003087 }
3088 break;
3089
3090 /* sqlite3_test_control(int) */
drh2cf4acb2014-04-18 00:06:02 +00003091 case SQLITE_TESTCTRL_PRNG_SAVE:
3092 case SQLITE_TESTCTRL_PRNG_RESTORE:
shaneh96887e12011-02-10 21:08:58 +00003093 case SQLITE_TESTCTRL_PRNG_RESET:
drh2cf4acb2014-04-18 00:06:02 +00003094 case SQLITE_TESTCTRL_BYTEORDER:
shaneh96887e12011-02-10 21:08:58 +00003095 if( nArg==2 ){
3096 rc = sqlite3_test_control(testctrl);
drh151b7d52013-05-06 20:28:54 +00003097 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003098 } else {
3099 fprintf(stderr,"Error: testctrl %s takes no options\n", azArg[1]);
3100 }
3101 break;
3102
3103 /* sqlite3_test_control(int, uint) */
3104 case SQLITE_TESTCTRL_PENDING_BYTE:
3105 if( nArg==3 ){
drhaf664332013-07-18 20:28:29 +00003106 unsigned int opt = (unsigned int)integerValue(azArg[2]);
shaneh96887e12011-02-10 21:08:58 +00003107 rc = sqlite3_test_control(testctrl, opt);
drh151b7d52013-05-06 20:28:54 +00003108 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003109 } else {
drhd416fe72011-03-17 16:45:50 +00003110 fprintf(stderr,"Error: testctrl %s takes a single unsigned"
3111 " int option\n", azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003112 }
3113 break;
3114
3115 /* sqlite3_test_control(int, int) */
3116 case SQLITE_TESTCTRL_ASSERT:
3117 case SQLITE_TESTCTRL_ALWAYS:
3118 if( nArg==3 ){
drh348d19c2013-06-03 12:47:43 +00003119 int opt = booleanValue(azArg[2]);
shaneh96887e12011-02-10 21:08:58 +00003120 rc = sqlite3_test_control(testctrl, opt);
drh151b7d52013-05-06 20:28:54 +00003121 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003122 } else {
drhd416fe72011-03-17 16:45:50 +00003123 fprintf(stderr,"Error: testctrl %s takes a single int option\n",
3124 azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003125 }
3126 break;
3127
3128 /* sqlite3_test_control(int, char *) */
3129#ifdef SQLITE_N_KEYWORD
3130 case SQLITE_TESTCTRL_ISKEYWORD:
3131 if( nArg==3 ){
3132 const char *opt = azArg[2];
3133 rc = sqlite3_test_control(testctrl, opt);
drh151b7d52013-05-06 20:28:54 +00003134 fprintf(p->out, "%d (0x%08x)\n", rc, rc);
shaneh96887e12011-02-10 21:08:58 +00003135 } else {
drhd416fe72011-03-17 16:45:50 +00003136 fprintf(stderr,"Error: testctrl %s takes a single char * option\n",
3137 azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003138 }
3139 break;
3140#endif
3141
3142 case SQLITE_TESTCTRL_BITVEC_TEST:
3143 case SQLITE_TESTCTRL_FAULT_INSTALL:
3144 case SQLITE_TESTCTRL_BENIGN_MALLOC_HOOKS:
3145 case SQLITE_TESTCTRL_SCRATCHMALLOC:
3146 default:
drhd416fe72011-03-17 16:45:50 +00003147 fprintf(stderr,"Error: CLI support for testctrl %s not implemented\n",
3148 azArg[1]);
shaneh96887e12011-02-10 21:08:58 +00003149 break;
3150 }
3151 }
3152 }else
3153
shanehe2aa9d72009-11-06 17:20:17 +00003154 if( c=='t' && n>4 && strncmp(azArg[0], "timeout", n)==0 && nArg==2 ){
drh05782482013-10-24 15:20:20 +00003155 open_db(p, 0);
drh348d19c2013-06-03 12:47:43 +00003156 sqlite3_busy_timeout(p->db, (int)integerValue(azArg[1]));
shanehe2aa9d72009-11-06 17:20:17 +00003157 }else
3158
drhd416fe72011-03-17 16:45:50 +00003159 if( HAS_TIMER && c=='t' && n>=5 && strncmp(azArg[0], "timer", n)==0
3160 && nArg==2
3161 ){
drh3b1a9882007-11-02 12:53:03 +00003162 enableTimer = booleanValue(azArg[1]);
shanehe2aa9d72009-11-06 17:20:17 +00003163 }else
3164
drh42f64e52012-04-04 16:56:23 +00003165 if( c=='t' && strncmp(azArg[0], "trace", n)==0 && nArg>1 ){
drh05782482013-10-24 15:20:20 +00003166 open_db(p, 0);
drh42f64e52012-04-04 16:56:23 +00003167 output_file_close(p->traceOut);
3168 p->traceOut = output_file_open(azArg[1]);
drhbbb0be82012-06-27 16:12:27 +00003169#if !defined(SQLITE_OMIT_TRACE) && !defined(SQLITE_OMIT_FLOATING_POINT)
drh42f64e52012-04-04 16:56:23 +00003170 if( p->traceOut==0 ){
3171 sqlite3_trace(p->db, 0, 0);
3172 }else{
3173 sqlite3_trace(p->db, sql_trace_callback, p->traceOut);
3174 }
3175#endif
3176 }else
3177
drh9fd301b2011-06-03 13:28:22 +00003178 if( c=='v' && strncmp(azArg[0], "version", n)==0 ){
drh151b7d52013-05-06 20:28:54 +00003179 fprintf(p->out, "SQLite %s %s\n" /*extra-version-info*/,
drh9fd301b2011-06-03 13:28:22 +00003180 sqlite3_libversion(), sqlite3_sourceid());
3181 }else
3182
drhde60fc22011-12-14 17:53:36 +00003183 if( c=='v' && strncmp(azArg[0], "vfsname", n)==0 ){
3184 const char *zDbName = nArg==2 ? azArg[1] : "main";
3185 char *zVfsName = 0;
3186 if( p->db ){
3187 sqlite3_file_control(p->db, zDbName, SQLITE_FCNTL_VFSNAME, &zVfsName);
3188 if( zVfsName ){
drh151b7d52013-05-06 20:28:54 +00003189 fprintf(p->out, "%s\n", zVfsName);
drhde60fc22011-12-14 17:53:36 +00003190 sqlite3_free(zVfsName);
3191 }
3192 }
3193 }else
3194
drhcef4fc82012-09-21 22:50:45 +00003195#if defined(SQLITE_DEBUG) && defined(SQLITE_ENABLE_WHERETRACE)
3196 if( c=='w' && strncmp(azArg[0], "wheretrace", n)==0 ){
3197 extern int sqlite3WhereTrace;
drh7d9f3942013-04-03 01:26:54 +00003198 sqlite3WhereTrace = booleanValue(azArg[1]);
drhcef4fc82012-09-21 22:50:45 +00003199 }else
3200#endif
3201
shanehe2aa9d72009-11-06 17:20:17 +00003202 if( c=='w' && strncmp(azArg[0], "width", n)==0 && nArg>1 ){
drh75897232000-05-29 14:26:00 +00003203 int j;
drh43617e92006-03-06 20:55:46 +00003204 assert( nArg<=ArraySize(azArg) );
drh75897232000-05-29 14:26:00 +00003205 for(j=1; j<nArg && j<ArraySize(p->colWidth); j++){
drh348d19c2013-06-03 12:47:43 +00003206 p->colWidth[j-1] = (int)integerValue(azArg[j]);
drh75897232000-05-29 14:26:00 +00003207 }
3208 }else
3209
3210 {
shane9bd1b442009-10-23 01:27:39 +00003211 fprintf(stderr, "Error: unknown command or invalid arguments: "
drh67505e72002-04-19 12:34:06 +00003212 " \"%s\". Enter \".help\" for help\n", azArg[0]);
shane9bd1b442009-10-23 01:27:39 +00003213 rc = 1;
drh75897232000-05-29 14:26:00 +00003214 }
drh67505e72002-04-19 12:34:06 +00003215
3216 return rc;
drh75897232000-05-29 14:26:00 +00003217}
3218
drh67505e72002-04-19 12:34:06 +00003219/*
drh91a66392007-09-07 01:12:32 +00003220** Return TRUE if a semicolon occurs anywhere in the first N characters
3221** of string z[].
drh324ccef2003-02-05 14:06:20 +00003222*/
drh9f099fd2013-08-06 14:01:46 +00003223static int line_contains_semicolon(const char *z, int N){
drh91a66392007-09-07 01:12:32 +00003224 int i;
3225 for(i=0; i<N; i++){ if( z[i]==';' ) return 1; }
3226 return 0;
drh324ccef2003-02-05 14:06:20 +00003227}
3228
3229/*
drh70c7a4b2003-04-26 03:03:06 +00003230** Test to see if a line consists entirely of whitespace.
3231*/
3232static int _all_whitespace(const char *z){
3233 for(; *z; z++){
drhf0693c82011-10-11 20:41:54 +00003234 if( IsSpace(z[0]) ) continue;
drh70c7a4b2003-04-26 03:03:06 +00003235 if( *z=='/' && z[1]=='*' ){
3236 z += 2;
3237 while( *z && (*z!='*' || z[1]!='/') ){ z++; }
3238 if( *z==0 ) return 0;
3239 z++;
3240 continue;
3241 }
3242 if( *z=='-' && z[1]=='-' ){
3243 z += 2;
3244 while( *z && *z!='\n' ){ z++; }
3245 if( *z==0 ) return 1;
3246 continue;
3247 }
3248 return 0;
3249 }
3250 return 1;
3251}
3252
3253/*
drha9b17162003-04-29 18:01:28 +00003254** Return TRUE if the line typed in is an SQL command terminator other
3255** than a semi-colon. The SQL Server style "go" command is understood
3256** as is the Oracle "/".
3257*/
drh9f099fd2013-08-06 14:01:46 +00003258static int line_is_command_terminator(const char *zLine){
drhf0693c82011-10-11 20:41:54 +00003259 while( IsSpace(zLine[0]) ){ zLine++; };
drh233a5312008-12-18 22:25:13 +00003260 if( zLine[0]=='/' && _all_whitespace(&zLine[1]) ){
3261 return 1; /* Oracle */
3262 }
drhf0693c82011-10-11 20:41:54 +00003263 if( ToLower(zLine[0])=='g' && ToLower(zLine[1])=='o'
drhc8d74412004-08-31 23:41:26 +00003264 && _all_whitespace(&zLine[2]) ){
drha9b17162003-04-29 18:01:28 +00003265 return 1; /* SQL Server */
3266 }
3267 return 0;
3268}
3269
3270/*
drh233a5312008-12-18 22:25:13 +00003271** Return true if zSql is a complete SQL statement. Return false if it
3272** ends in the middle of a string literal or C-style comment.
3273*/
drh9f099fd2013-08-06 14:01:46 +00003274static int line_is_complete(char *zSql, int nSql){
drh233a5312008-12-18 22:25:13 +00003275 int rc;
3276 if( zSql==0 ) return 1;
3277 zSql[nSql] = ';';
3278 zSql[nSql+1] = 0;
3279 rc = sqlite3_complete(zSql);
3280 zSql[nSql] = 0;
3281 return rc;
3282}
3283
3284/*
drh67505e72002-04-19 12:34:06 +00003285** Read input from *in and process it. If *in==0 then input
3286** is interactive - the user is typing it it. Otherwise, input
3287** is coming from a file or device. A prompt is issued and history
3288** is saved only if input is interactive. An interrupt signal will
3289** cause this routine to exit immediately, unless input is interactive.
drhc28490c2006-10-26 14:25:58 +00003290**
3291** Return the number of errors.
drh67505e72002-04-19 12:34:06 +00003292*/
drhc28490c2006-10-26 14:25:58 +00003293static int process_input(struct callback_data *p, FILE *in){
drh9f099fd2013-08-06 14:01:46 +00003294 char *zLine = 0; /* A single input line */
3295 char *zSql = 0; /* Accumulated SQL text */
3296 int nLine; /* Length of current line */
3297 int nSql = 0; /* Bytes of zSql[] used */
3298 int nAlloc = 0; /* Allocated zSql[] space */
3299 int nSqlPrior = 0; /* Bytes of zSql[] used by prior line */
3300 char *zErrMsg; /* Error message returned */
3301 int rc; /* Error code */
3302 int errCnt = 0; /* Number of errors seen */
3303 int lineno = 0; /* Current line number */
3304 int startline = 0; /* Line number for start of current input */
drhc49f44e2006-10-26 18:15:42 +00003305
3306 while( errCnt==0 || !bail_on_error || (in==0 && stdin_is_interactive) ){
3307 fflush(p->out);
drh9f099fd2013-08-06 14:01:46 +00003308 zLine = one_input_line(in, zLine, nSql>0);
drhc49f44e2006-10-26 18:15:42 +00003309 if( zLine==0 ){
drh9b8d3572012-04-21 11:33:39 +00003310 /* End of input */
3311 if( stdin_is_interactive ) printf("\n");
3312 break;
drhc49f44e2006-10-26 18:15:42 +00003313 }
drh67505e72002-04-19 12:34:06 +00003314 if( seenInterrupt ){
3315 if( in!=0 ) break;
3316 seenInterrupt = 0;
3317 }
drhc28490c2006-10-26 14:25:58 +00003318 lineno++;
drh849a9d92013-12-21 15:46:06 +00003319 if( nSql==0 && _all_whitespace(zLine) ){
3320 if( p->echoOn ) printf("%s\n", zLine);
3321 continue;
3322 }
drh2af0b2d2002-02-21 02:25:02 +00003323 if( zLine && zLine[0]=='.' && nSql==0 ){
shaneb9fc17d2009-10-22 21:23:35 +00003324 if( p->echoOn ) printf("%s\n", zLine);
drhc49f44e2006-10-26 18:15:42 +00003325 rc = do_meta_command(zLine, p);
shane916f9612009-10-23 00:37:15 +00003326 if( rc==2 ){ /* exit requested */
drh47ad6842006-11-08 12:25:42 +00003327 break;
3328 }else if( rc ){
drhc49f44e2006-10-26 18:15:42 +00003329 errCnt++;
3330 }
drhdaffd0e2001-04-11 14:28:42 +00003331 continue;
3332 }
drh9f099fd2013-08-06 14:01:46 +00003333 if( line_is_command_terminator(zLine) && line_is_complete(zSql, nSql) ){
drh5bb3eb92007-05-04 13:15:55 +00003334 memcpy(zLine,";",2);
drha9b17162003-04-29 18:01:28 +00003335 }
drh9f099fd2013-08-06 14:01:46 +00003336 nLine = strlen30(zLine);
3337 if( nSql+nLine+2>=nAlloc ){
3338 nAlloc = nSql+nLine+100;
3339 zSql = realloc(zSql, nAlloc);
drhdaffd0e2001-04-11 14:28:42 +00003340 if( zSql==0 ){
drh9f099fd2013-08-06 14:01:46 +00003341 fprintf(stderr, "Error: out of memory\n");
drhdaffd0e2001-04-11 14:28:42 +00003342 exit(1);
3343 }
drhdaffd0e2001-04-11 14:28:42 +00003344 }
drh9f099fd2013-08-06 14:01:46 +00003345 nSqlPrior = nSql;
3346 if( nSql==0 ){
3347 int i;
3348 for(i=0; zLine[i] && IsSpace(zLine[i]); i++){}
drh77dfd5b2013-08-19 11:15:48 +00003349 assert( nAlloc>0 && zSql!=0 );
drh9f099fd2013-08-06 14:01:46 +00003350 memcpy(zSql, zLine+i, nLine+1-i);
3351 startline = lineno;
3352 nSql = nLine-i;
3353 }else{
3354 zSql[nSql++] = '\n';
3355 memcpy(zSql+nSql, zLine, nLine+1);
3356 nSql += nLine;
3357 }
3358 if( nSql && line_contains_semicolon(&zSql[nSqlPrior], nSql-nSqlPrior)
drh91a66392007-09-07 01:12:32 +00003359 && sqlite3_complete(zSql) ){
drhdaffd0e2001-04-11 14:28:42 +00003360 p->cnt = 0;
drh05782482013-10-24 15:20:20 +00003361 open_db(p, 0);
drh3b1a9882007-11-02 12:53:03 +00003362 BEGIN_TIMER;
shane626a6e42009-10-22 17:30:15 +00003363 rc = shell_exec(p->db, zSql, shell_callback, p, &zErrMsg);
drh3b1a9882007-11-02 12:53:03 +00003364 END_TIMER;
drh7f953e22002-07-13 17:33:45 +00003365 if( rc || zErrMsg ){
drhc28490c2006-10-26 14:25:58 +00003366 char zPrefix[100];
3367 if( in!=0 || !stdin_is_interactive ){
drh5bb3eb92007-05-04 13:15:55 +00003368 sqlite3_snprintf(sizeof(zPrefix), zPrefix,
shane9bd1b442009-10-23 01:27:39 +00003369 "Error: near line %d:", startline);
drhc28490c2006-10-26 14:25:58 +00003370 }else{
shane9bd1b442009-10-23 01:27:39 +00003371 sqlite3_snprintf(sizeof(zPrefix), zPrefix, "Error:");
drhc28490c2006-10-26 14:25:58 +00003372 }
drh7f953e22002-07-13 17:33:45 +00003373 if( zErrMsg!=0 ){
shaned2bed1c2009-10-21 03:56:54 +00003374 fprintf(stderr, "%s %s\n", zPrefix, zErrMsg);
drh3f4fedb2004-05-31 19:34:33 +00003375 sqlite3_free(zErrMsg);
drh7f953e22002-07-13 17:33:45 +00003376 zErrMsg = 0;
3377 }else{
shaned2bed1c2009-10-21 03:56:54 +00003378 fprintf(stderr, "%s %s\n", zPrefix, sqlite3_errmsg(p->db));
drh7f953e22002-07-13 17:33:45 +00003379 }
drhc49f44e2006-10-26 18:15:42 +00003380 errCnt++;
drhdaffd0e2001-04-11 14:28:42 +00003381 }
drhdaffd0e2001-04-11 14:28:42 +00003382 nSql = 0;
drh9f099fd2013-08-06 14:01:46 +00003383 }else if( nSql && _all_whitespace(zSql) ){
drh849a9d92013-12-21 15:46:06 +00003384 if( p->echoOn ) printf("%s\n", zSql);
drh7a411f42013-04-17 17:33:17 +00003385 nSql = 0;
drhdaffd0e2001-04-11 14:28:42 +00003386 }
3387 }
drh9f099fd2013-08-06 14:01:46 +00003388 if( nSql ){
drhd416fe72011-03-17 16:45:50 +00003389 if( !_all_whitespace(zSql) ){
3390 fprintf(stderr, "Error: incomplete SQL: %s\n", zSql);
3391 }
drhdaffd0e2001-04-11 14:28:42 +00003392 free(zSql);
3393 }
danielk19772ac27622007-07-03 05:31:16 +00003394 free(zLine);
drh4d15a0d2012-12-01 20:21:22 +00003395 return errCnt>0;
drhdaffd0e2001-04-11 14:28:42 +00003396}
3397
drh67505e72002-04-19 12:34:06 +00003398/*
3399** Return a pathname which is the user's home directory. A
drh85e72432012-04-11 11:38:53 +00003400** 0 return indicates an error of some kind.
drh67505e72002-04-19 12:34:06 +00003401*/
3402static char *find_home_dir(void){
drh85e72432012-04-11 11:38:53 +00003403 static char *home_dir = NULL;
3404 if( home_dir ) return home_dir;
persicom7e2dfdd2002-04-18 02:46:52 +00003405
drh83905c92012-06-21 13:00:37 +00003406#if !defined(_WIN32) && !defined(WIN32) && !defined(_WIN32_WCE) && !defined(__RTP__) && !defined(_WRS_KERNEL)
mistachkinc8bde372012-06-18 08:00:56 +00003407 {
3408 struct passwd *pwent;
3409 uid_t uid = getuid();
3410 if( (pwent=getpwuid(uid)) != NULL) {
3411 home_dir = pwent->pw_dir;
3412 }
drh67505e72002-04-19 12:34:06 +00003413 }
3414#endif
3415
chw65d3c132007-11-12 21:09:10 +00003416#if defined(_WIN32_WCE)
3417 /* Windows CE (arm-wince-mingw32ce-gcc) does not provide getenv()
3418 */
drh85e72432012-04-11 11:38:53 +00003419 home_dir = "/";
chw65d3c132007-11-12 21:09:10 +00003420#else
3421
drh83905c92012-06-21 13:00:37 +00003422#if defined(_WIN32) || defined(WIN32)
drh164a1b62006-08-19 11:15:20 +00003423 if (!home_dir) {
3424 home_dir = getenv("USERPROFILE");
3425 }
3426#endif
3427
drh67505e72002-04-19 12:34:06 +00003428 if (!home_dir) {
3429 home_dir = getenv("HOME");
drh67505e72002-04-19 12:34:06 +00003430 }
3431
drh83905c92012-06-21 13:00:37 +00003432#if defined(_WIN32) || defined(WIN32)
drhe98d4fa2002-04-21 19:06:22 +00003433 if (!home_dir) {
drh164a1b62006-08-19 11:15:20 +00003434 char *zDrive, *zPath;
3435 int n;
3436 zDrive = getenv("HOMEDRIVE");
3437 zPath = getenv("HOMEPATH");
3438 if( zDrive && zPath ){
drh4f21c4a2008-12-10 22:15:00 +00003439 n = strlen30(zDrive) + strlen30(zPath) + 1;
drh164a1b62006-08-19 11:15:20 +00003440 home_dir = malloc( n );
3441 if( home_dir==0 ) return 0;
3442 sqlite3_snprintf(n, home_dir, "%s%s", zDrive, zPath);
3443 return home_dir;
3444 }
3445 home_dir = "c:\\";
drhe98d4fa2002-04-21 19:06:22 +00003446 }
3447#endif
3448
chw65d3c132007-11-12 21:09:10 +00003449#endif /* !_WIN32_WCE */
3450
drh67505e72002-04-19 12:34:06 +00003451 if( home_dir ){
drh4f21c4a2008-12-10 22:15:00 +00003452 int n = strlen30(home_dir) + 1;
drh5bb3eb92007-05-04 13:15:55 +00003453 char *z = malloc( n );
3454 if( z ) memcpy(z, home_dir, n);
drh67505e72002-04-19 12:34:06 +00003455 home_dir = z;
3456 }
drhe98d4fa2002-04-21 19:06:22 +00003457
drh67505e72002-04-19 12:34:06 +00003458 return home_dir;
3459}
3460
3461/*
3462** Read input from the file given by sqliterc_override. Or if that
3463** parameter is NULL, take input from ~/.sqliterc
shane9bd1b442009-10-23 01:27:39 +00003464**
3465** Returns the number of errors.
drh67505e72002-04-19 12:34:06 +00003466*/
shane9bd1b442009-10-23 01:27:39 +00003467static int process_sqliterc(
drh22fbcb82004-02-01 01:22:50 +00003468 struct callback_data *p, /* Configuration data */
3469 const char *sqliterc_override /* Name of config file. NULL to use default */
3470){
persicom7e2dfdd2002-04-18 02:46:52 +00003471 char *home_dir = NULL;
drh22fbcb82004-02-01 01:22:50 +00003472 const char *sqliterc = sqliterc_override;
drh43617e92006-03-06 20:55:46 +00003473 char *zBuf = 0;
persicom7e2dfdd2002-04-18 02:46:52 +00003474 FILE *in = NULL;
shane9bd1b442009-10-23 01:27:39 +00003475 int rc = 0;
persicom7e2dfdd2002-04-18 02:46:52 +00003476
3477 if (sqliterc == NULL) {
drh67505e72002-04-19 12:34:06 +00003478 home_dir = find_home_dir();
drhe98d4fa2002-04-21 19:06:22 +00003479 if( home_dir==0 ){
chw97185482008-11-17 08:05:31 +00003480#if !defined(__RTP__) && !defined(_WRS_KERNEL)
shane86f5bdb2009-10-24 02:00:07 +00003481 fprintf(stderr,"%s: Error: cannot locate your home directory\n", Argv0);
chw97185482008-11-17 08:05:31 +00003482#endif
shane9bd1b442009-10-23 01:27:39 +00003483 return 1;
drhe98d4fa2002-04-21 19:06:22 +00003484 }
drh2f3de322012-06-27 16:41:31 +00003485 sqlite3_initialize();
drh85e72432012-04-11 11:38:53 +00003486 zBuf = sqlite3_mprintf("%s/.sqliterc",home_dir);
3487 sqliterc = zBuf;
persicom7e2dfdd2002-04-18 02:46:52 +00003488 }
drha1f9b5e2004-02-14 16:31:02 +00003489 in = fopen(sqliterc,"rb");
drh22fbcb82004-02-01 01:22:50 +00003490 if( in ){
drhc28490c2006-10-26 14:25:58 +00003491 if( stdin_is_interactive ){
shane86f5bdb2009-10-24 02:00:07 +00003492 fprintf(stderr,"-- Loading resources from %s\n",sqliterc);
drh22fbcb82004-02-01 01:22:50 +00003493 }
shane9bd1b442009-10-23 01:27:39 +00003494 rc = process_input(p,in);
drhdd45df82002-04-18 12:39:03 +00003495 fclose(in);
persicom7e2dfdd2002-04-18 02:46:52 +00003496 }
drh85e72432012-04-11 11:38:53 +00003497 sqlite3_free(zBuf);
shane9bd1b442009-10-23 01:27:39 +00003498 return rc;
persicom7e2dfdd2002-04-18 02:46:52 +00003499}
3500
drh67505e72002-04-19 12:34:06 +00003501/*
drhe1e38c42003-05-04 18:30:59 +00003502** Show available command line options
3503*/
3504static const char zOptions[] =
drhc49f44e2006-10-26 18:15:42 +00003505 " -bail stop after hitting an error\n"
drhc49f44e2006-10-26 18:15:42 +00003506 " -batch force batch I/O\n"
drhe1e38c42003-05-04 18:30:59 +00003507 " -column set output mode to 'column'\n"
mistachkin6d81d752012-10-25 15:43:28 +00003508 " -cmd COMMAND run \"COMMAND\" before reading stdin\n"
drhc49f44e2006-10-26 18:15:42 +00003509 " -csv set output mode to 'csv'\n"
drhcc3b4f82012-02-07 14:13:50 +00003510 " -echo print commands before execution\n"
mistachkin6d81d752012-10-25 15:43:28 +00003511 " -init FILENAME read/process named file\n"
drhcc3b4f82012-02-07 14:13:50 +00003512 " -[no]header turn headers on or off\n"
drh98d312f2012-10-25 15:23:14 +00003513#if defined(SQLITE_ENABLE_MEMSYS3) || defined(SQLITE_ENABLE_MEMSYS5)
3514 " -heap SIZE Size of heap for memsys3 or memsys5\n"
3515#endif
drhcc3b4f82012-02-07 14:13:50 +00003516 " -help show this message\n"
drhe1e38c42003-05-04 18:30:59 +00003517 " -html set output mode to HTML\n"
drhcc3b4f82012-02-07 14:13:50 +00003518 " -interactive force interactive I/O\n"
drhe1e38c42003-05-04 18:30:59 +00003519 " -line set output mode to 'line'\n"
3520 " -list set output mode to 'list'\n"
drh7d9f3942013-04-03 01:26:54 +00003521 " -mmap N default mmap size set to N\n"
drhcc3b4f82012-02-07 14:13:50 +00003522#ifdef SQLITE_ENABLE_MULTIPLEX
3523 " -multiplex enable the multiplexor VFS\n"
3524#endif
drh98d312f2012-10-25 15:23:14 +00003525 " -nullvalue TEXT set text string for NULL values. Default ''\n"
3526 " -separator SEP set output field separator. Default: '|'\n"
shaneh642d8b82010-07-28 16:05:34 +00003527 " -stats print memory stats before each finalize\n"
drhe1e38c42003-05-04 18:30:59 +00003528 " -version show SQLite version\n"
drha7e61d82011-03-12 17:02:57 +00003529 " -vfs NAME use NAME as the default VFS\n"
drh2b625e22011-03-16 17:05:28 +00003530#ifdef SQLITE_ENABLE_VFSTRACE
3531 " -vfstrace enable tracing of all VFS calls\n"
3532#endif
drhe1e38c42003-05-04 18:30:59 +00003533;
3534static void usage(int showDetail){
drh80e8be92006-08-29 12:04:19 +00003535 fprintf(stderr,
3536 "Usage: %s [OPTIONS] FILENAME [SQL]\n"
3537 "FILENAME is the name of an SQLite database. A new database is created\n"
3538 "if the file does not previously exist.\n", Argv0);
drhe1e38c42003-05-04 18:30:59 +00003539 if( showDetail ){
drh80e8be92006-08-29 12:04:19 +00003540 fprintf(stderr, "OPTIONS include:\n%s", zOptions);
drhe1e38c42003-05-04 18:30:59 +00003541 }else{
3542 fprintf(stderr, "Use the -help option for additional information\n");
3543 }
3544 exit(1);
3545}
3546
3547/*
drh67505e72002-04-19 12:34:06 +00003548** Initialize the state information in data
3549*/
drh0850b532006-01-31 19:31:43 +00003550static void main_init(struct callback_data *data) {
persicom7e2dfdd2002-04-18 02:46:52 +00003551 memset(data, 0, sizeof(*data));
3552 data->mode = MODE_List;
drh5bb3eb92007-05-04 13:15:55 +00003553 memcpy(data->separator,"|", 2);
persicom7e2dfdd2002-04-18 02:46:52 +00003554 data->showHeader = 0;
drh52784bd2011-05-18 17:15:06 +00003555 sqlite3_config(SQLITE_CONFIG_URI, 1);
drh127f9d72010-02-23 01:47:00 +00003556 sqlite3_config(SQLITE_CONFIG_LOG, shellLog, data);
drh5bb3eb92007-05-04 13:15:55 +00003557 sqlite3_snprintf(sizeof(mainPrompt), mainPrompt,"sqlite> ");
3558 sqlite3_snprintf(sizeof(continuePrompt), continuePrompt," ...> ");
dan0f831772010-03-03 07:23:12 +00003559 sqlite3_config(SQLITE_CONFIG_SINGLETHREAD);
persicom7e2dfdd2002-04-18 02:46:52 +00003560}
3561
drh98d312f2012-10-25 15:23:14 +00003562/*
drh5c7976f2014-02-10 19:59:27 +00003563** Output text to the console in a font that attracts extra attention.
drh1247aa42014-02-10 19:27:05 +00003564*/
3565#ifdef _WIN32
drh5c7976f2014-02-10 19:59:27 +00003566static void printBold(const char *zText){
3567 HANDLE out = GetStdHandle(STD_OUTPUT_HANDLE);
3568 CONSOLE_SCREEN_BUFFER_INFO defaultScreenInfo;
3569 GetConsoleScreenBufferInfo(out, &defaultScreenInfo);
3570 SetConsoleTextAttribute(out,
3571 FOREGROUND_RED|FOREGROUND_INTENSITY
3572 );
3573 printf("%s", zText);
3574 SetConsoleTextAttribute(out, defaultScreenInfo.wAttributes);
drh1247aa42014-02-10 19:27:05 +00003575}
3576#else
drh5c7976f2014-02-10 19:59:27 +00003577static void printBold(const char *zText){
3578 printf("\033[1m%s\033[0m", zText);
drh1247aa42014-02-10 19:27:05 +00003579}
3580#endif
3581
3582/*
drh98d312f2012-10-25 15:23:14 +00003583** Get the argument to an --option. Throw an error and die if no argument
3584** is available.
3585*/
3586static char *cmdline_option_value(int argc, char **argv, int i){
3587 if( i==argc ){
3588 fprintf(stderr, "%s: Error: missing argument to %s\n",
3589 argv[0], argv[argc-1]);
3590 exit(1);
3591 }
3592 return argv[i];
3593}
3594
drh75897232000-05-29 14:26:00 +00003595int main(int argc, char **argv){
drh75897232000-05-29 14:26:00 +00003596 char *zErrMsg = 0;
3597 struct callback_data data;
drh22fbcb82004-02-01 01:22:50 +00003598 const char *zInitFile = 0;
3599 char *zFirstCmd = 0;
drh44c2eb12003-04-30 11:38:26 +00003600 int i;
drhc28490c2006-10-26 14:25:58 +00003601 int rc = 0;
drhb3735912014-02-10 16:13:42 +00003602 int warnInmemoryDb = 0;
drh75897232000-05-29 14:26:00 +00003603
drh69b30ab2014-02-27 15:11:52 +00003604#if USE_SYSTEM_SQLITE+0!=1
drh52784bd2011-05-18 17:15:06 +00003605 if( strcmp(sqlite3_sourceid(),SQLITE_SOURCE_ID)!=0 ){
3606 fprintf(stderr, "SQLite header and source version mismatch\n%s\n%s\n",
3607 sqlite3_sourceid(), SQLITE_SOURCE_ID);
3608 exit(1);
3609 }
drhc7181902014-02-27 15:04:13 +00003610#endif
drhdaffd0e2001-04-11 14:28:42 +00003611 Argv0 = argv[0];
persicom7e2dfdd2002-04-18 02:46:52 +00003612 main_init(&data);
drhc28490c2006-10-26 14:25:58 +00003613 stdin_is_interactive = isatty(0);
persicom7e2dfdd2002-04-18 02:46:52 +00003614
drh44c2eb12003-04-30 11:38:26 +00003615 /* Make sure we have a valid signal handler early, before anything
3616 ** else is done.
3617 */
drh4c504392000-10-16 22:06:40 +00003618#ifdef SIGINT
3619 signal(SIGINT, interrupt_handler);
3620#endif
drh44c2eb12003-04-30 11:38:26 +00003621
drh22fbcb82004-02-01 01:22:50 +00003622 /* Do an initial pass through the command-line argument to locate
3623 ** the name of the database file, the name of the initialization file,
drh9c88d682010-12-17 14:03:01 +00003624 ** the size of the alternative malloc heap,
drh22fbcb82004-02-01 01:22:50 +00003625 ** and the first command to execute.
drh44c2eb12003-04-30 11:38:26 +00003626 */
drh98d312f2012-10-25 15:23:14 +00003627 for(i=1; i<argc; i++){
drhc28490c2006-10-26 14:25:58 +00003628 char *z;
drhc28490c2006-10-26 14:25:58 +00003629 z = argv[i];
drh98d312f2012-10-25 15:23:14 +00003630 if( z[0]!='-' ){
3631 if( data.zDbFilename==0 ){
3632 data.zDbFilename = z;
3633 continue;
3634 }
3635 if( zFirstCmd==0 ){
3636 zFirstCmd = z;
3637 continue;
3638 }
3639 fprintf(stderr,"%s: Error: too many options: \"%s\"\n", Argv0, argv[i]);
3640 fprintf(stderr,"Use -help for a list of options.\n");
3641 return 1;
3642 }
drhcc3b4f82012-02-07 14:13:50 +00003643 if( z[1]=='-' ) z++;
3644 if( strcmp(z,"-separator")==0
3645 || strcmp(z,"-nullvalue")==0
3646 || strcmp(z,"-cmd")==0
3647 ){
drh98d312f2012-10-25 15:23:14 +00003648 (void)cmdline_option_value(argc, argv, ++i);
drhcc3b4f82012-02-07 14:13:50 +00003649 }else if( strcmp(z,"-init")==0 ){
drh98d312f2012-10-25 15:23:14 +00003650 zInitFile = cmdline_option_value(argc, argv, ++i);
drhcc3b4f82012-02-07 14:13:50 +00003651 }else if( strcmp(z,"-batch")==0 ){
drh98d312f2012-10-25 15:23:14 +00003652 /* Need to check for batch mode here to so we can avoid printing
3653 ** informational messages (like from process_sqliterc) before
3654 ** we do the actual processing of arguments later in a second pass.
3655 */
shanef69573d2009-10-24 02:06:14 +00003656 stdin_is_interactive = 0;
drhcc3b4f82012-02-07 14:13:50 +00003657 }else if( strcmp(z,"-heap")==0 ){
drhb07028f2011-10-14 21:49:18 +00003658#if defined(SQLITE_ENABLE_MEMSYS3) || defined(SQLITE_ENABLE_MEMSYS5)
drh9c88d682010-12-17 14:03:01 +00003659 const char *zSize;
3660 sqlite3_int64 szHeap;
3661
drh98d312f2012-10-25 15:23:14 +00003662 zSize = cmdline_option_value(argc, argv, ++i);
drh7d9f3942013-04-03 01:26:54 +00003663 szHeap = integerValue(zSize);
drh9c88d682010-12-17 14:03:01 +00003664 if( szHeap>0x7fff0000 ) szHeap = 0x7fff0000;
drh9c88d682010-12-17 14:03:01 +00003665 sqlite3_config(SQLITE_CONFIG_HEAP, malloc((int)szHeap), (int)szHeap, 64);
3666#endif
drh97ae8ff2011-03-16 16:56:29 +00003667#ifdef SQLITE_ENABLE_VFSTRACE
drhcc3b4f82012-02-07 14:13:50 +00003668 }else if( strcmp(z,"-vfstrace")==0 ){
drh97ae8ff2011-03-16 16:56:29 +00003669 extern int vfstrace_register(
3670 const char *zTraceName,
3671 const char *zOldVfsName,
3672 int (*xOut)(const char*,void*),
3673 void *pOutArg,
3674 int makeDefault
3675 );
drh2b625e22011-03-16 17:05:28 +00003676 vfstrace_register("trace",0,(int(*)(const char*,void*))fputs,stderr,1);
drh97ae8ff2011-03-16 16:56:29 +00003677#endif
drh6f25e892011-07-08 17:02:57 +00003678#ifdef SQLITE_ENABLE_MULTIPLEX
drhcc3b4f82012-02-07 14:13:50 +00003679 }else if( strcmp(z,"-multiplex")==0 ){
drh6f25e892011-07-08 17:02:57 +00003680 extern int sqlite3_multiple_initialize(const char*,int);
3681 sqlite3_multiplex_initialize(0, 1);
3682#endif
drh7d9f3942013-04-03 01:26:54 +00003683 }else if( strcmp(z,"-mmap")==0 ){
drh9b4c59f2013-04-15 17:03:42 +00003684 sqlite3_int64 sz = integerValue(cmdline_option_value(argc,argv,++i));
3685 sqlite3_config(SQLITE_CONFIG_MMAP_SIZE, sz, sz);
drhcc3b4f82012-02-07 14:13:50 +00003686 }else if( strcmp(z,"-vfs")==0 ){
drh98d312f2012-10-25 15:23:14 +00003687 sqlite3_vfs *pVfs = sqlite3_vfs_find(cmdline_option_value(argc,argv,++i));
drha7e61d82011-03-12 17:02:57 +00003688 if( pVfs ){
3689 sqlite3_vfs_register(pVfs, 1);
3690 }else{
3691 fprintf(stderr, "no such VFS: \"%s\"\n", argv[i]);
3692 exit(1);
3693 }
drh44c2eb12003-04-30 11:38:26 +00003694 }
3695 }
drh98d312f2012-10-25 15:23:14 +00003696 if( data.zDbFilename==0 ){
danielk197703aded42004-11-22 05:26:27 +00003697#ifndef SQLITE_OMIT_MEMORYDB
drh22fbcb82004-02-01 01:22:50 +00003698 data.zDbFilename = ":memory:";
drh1247aa42014-02-10 19:27:05 +00003699 warnInmemoryDb = argc==1;
danielk197703aded42004-11-22 05:26:27 +00003700#else
shane86f5bdb2009-10-24 02:00:07 +00003701 fprintf(stderr,"%s: Error: no database filename specified\n", Argv0);
3702 return 1;
drh01b41712005-08-29 23:06:23 +00003703#endif
drhc7181902014-02-27 15:04:13 +00003704#ifdef SQLITE_SHELL_DBNAME_PROC
3705 { extern void SQLITE_SHELL_DBNAME_PROC(const char**);
3706 SQLITE_SHELL_DBNAME_PROC(&data.zDbFilename);
3707 warnInmemoryDb = 0; }
3708#endif
drh98d312f2012-10-25 15:23:14 +00003709 }
3710 data.out = stdout;
drh01b41712005-08-29 23:06:23 +00003711
drh44c2eb12003-04-30 11:38:26 +00003712 /* Go ahead and open the database file if it already exists. If the
3713 ** file does not exist, delay opening it. This prevents empty database
3714 ** files from being created if a user mistypes the database name argument
3715 ** to the sqlite command-line tool.
3716 */
drhc8d74412004-08-31 23:41:26 +00003717 if( access(data.zDbFilename, 0)==0 ){
drh05782482013-10-24 15:20:20 +00003718 open_db(&data, 0);
drh44c2eb12003-04-30 11:38:26 +00003719 }
3720
drh22fbcb82004-02-01 01:22:50 +00003721 /* Process the initialization file if there is one. If no -init option
3722 ** is given on the command line, look for a file named ~/.sqliterc and
3723 ** try to process it.
drh44c2eb12003-04-30 11:38:26 +00003724 */
shane86f5bdb2009-10-24 02:00:07 +00003725 rc = process_sqliterc(&data,zInitFile);
3726 if( rc>0 ){
3727 return rc;
3728 }
drh44c2eb12003-04-30 11:38:26 +00003729
drh22fbcb82004-02-01 01:22:50 +00003730 /* Make a second pass through the command-line argument and set
3731 ** options. This second pass is delayed until after the initialization
3732 ** file is processed so that the command-line arguments will override
3733 ** settings in the initialization file.
drh44c2eb12003-04-30 11:38:26 +00003734 */
drh98d312f2012-10-25 15:23:14 +00003735 for(i=1; i<argc; i++){
drh22fbcb82004-02-01 01:22:50 +00003736 char *z = argv[i];
drh98d312f2012-10-25 15:23:14 +00003737 if( z[0]!='-' ) continue;
drhc28490c2006-10-26 14:25:58 +00003738 if( z[1]=='-' ){ z++; }
drh2e584cd2006-09-25 13:09:22 +00003739 if( strcmp(z,"-init")==0 ){
drh22fbcb82004-02-01 01:22:50 +00003740 i++;
3741 }else if( strcmp(z,"-html")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00003742 data.mode = MODE_Html;
drh22fbcb82004-02-01 01:22:50 +00003743 }else if( strcmp(z,"-list")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00003744 data.mode = MODE_List;
drh22fbcb82004-02-01 01:22:50 +00003745 }else if( strcmp(z,"-line")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00003746 data.mode = MODE_Line;
drh22fbcb82004-02-01 01:22:50 +00003747 }else if( strcmp(z,"-column")==0 ){
drh8b32e172002-04-08 02:42:57 +00003748 data.mode = MODE_Column;
drhc49f44e2006-10-26 18:15:42 +00003749 }else if( strcmp(z,"-csv")==0 ){
3750 data.mode = MODE_Csv;
drh5bb3eb92007-05-04 13:15:55 +00003751 memcpy(data.separator,",",2);
drh22fbcb82004-02-01 01:22:50 +00003752 }else if( strcmp(z,"-separator")==0 ){
drh5bb3eb92007-05-04 13:15:55 +00003753 sqlite3_snprintf(sizeof(data.separator), data.separator,
drh98d312f2012-10-25 15:23:14 +00003754 "%s",cmdline_option_value(argc,argv,++i));
drh22fbcb82004-02-01 01:22:50 +00003755 }else if( strcmp(z,"-nullvalue")==0 ){
drh5bb3eb92007-05-04 13:15:55 +00003756 sqlite3_snprintf(sizeof(data.nullvalue), data.nullvalue,
drh98d312f2012-10-25 15:23:14 +00003757 "%s",cmdline_option_value(argc,argv,++i));
drh22fbcb82004-02-01 01:22:50 +00003758 }else if( strcmp(z,"-header")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00003759 data.showHeader = 1;
drh22fbcb82004-02-01 01:22:50 +00003760 }else if( strcmp(z,"-noheader")==0 ){
drh1e5d0e92000-05-31 23:33:17 +00003761 data.showHeader = 0;
drh22fbcb82004-02-01 01:22:50 +00003762 }else if( strcmp(z,"-echo")==0 ){
drhdaffd0e2001-04-11 14:28:42 +00003763 data.echoOn = 1;
drhefbf3b12014-02-28 20:47:24 +00003764 }else if( strcmp(z,"-eqp")==0 ){
3765 data.autoEQP = 1;
shaneh642d8b82010-07-28 16:05:34 +00003766 }else if( strcmp(z,"-stats")==0 ){
3767 data.statsOn = 1;
drhc49f44e2006-10-26 18:15:42 +00003768 }else if( strcmp(z,"-bail")==0 ){
3769 bail_on_error = 1;
drh22fbcb82004-02-01 01:22:50 +00003770 }else if( strcmp(z,"-version")==0 ){
drh9fd301b2011-06-03 13:28:22 +00003771 printf("%s %s\n", sqlite3_libversion(), sqlite3_sourceid());
drh151e3e12006-06-06 12:32:21 +00003772 return 0;
drhc28490c2006-10-26 14:25:58 +00003773 }else if( strcmp(z,"-interactive")==0 ){
3774 stdin_is_interactive = 1;
3775 }else if( strcmp(z,"-batch")==0 ){
3776 stdin_is_interactive = 0;
drh9c88d682010-12-17 14:03:01 +00003777 }else if( strcmp(z,"-heap")==0 ){
3778 i++;
drh7d9f3942013-04-03 01:26:54 +00003779 }else if( strcmp(z,"-mmap")==0 ){
3780 i++;
drha7e61d82011-03-12 17:02:57 +00003781 }else if( strcmp(z,"-vfs")==0 ){
3782 i++;
drh6f25e892011-07-08 17:02:57 +00003783#ifdef SQLITE_ENABLE_VFSTRACE
drh97ae8ff2011-03-16 16:56:29 +00003784 }else if( strcmp(z,"-vfstrace")==0 ){
3785 i++;
drh6f25e892011-07-08 17:02:57 +00003786#endif
3787#ifdef SQLITE_ENABLE_MULTIPLEX
3788 }else if( strcmp(z,"-multiplex")==0 ){
3789 i++;
3790#endif
drhcc3b4f82012-02-07 14:13:50 +00003791 }else if( strcmp(z,"-help")==0 ){
drhe1e38c42003-05-04 18:30:59 +00003792 usage(1);
drhcc3b4f82012-02-07 14:13:50 +00003793 }else if( strcmp(z,"-cmd")==0 ){
3794 if( i==argc-1 ) break;
drh98d312f2012-10-25 15:23:14 +00003795 z = cmdline_option_value(argc,argv,++i);
drhcc3b4f82012-02-07 14:13:50 +00003796 if( z[0]=='.' ){
3797 rc = do_meta_command(z, &data);
drh99b39082013-04-17 12:19:48 +00003798 if( rc && bail_on_error ) return rc==2 ? 0 : rc;
drhcc3b4f82012-02-07 14:13:50 +00003799 }else{
drh05782482013-10-24 15:20:20 +00003800 open_db(&data, 0);
drhcc3b4f82012-02-07 14:13:50 +00003801 rc = shell_exec(data.db, z, shell_callback, &data, &zErrMsg);
3802 if( zErrMsg!=0 ){
3803 fprintf(stderr,"Error: %s\n", zErrMsg);
3804 if( bail_on_error ) return rc!=0 ? rc : 1;
3805 }else if( rc!=0 ){
3806 fprintf(stderr,"Error: unable to process SQL \"%s\"\n", z);
3807 if( bail_on_error ) return rc;
3808 }
3809 }
drh1e5d0e92000-05-31 23:33:17 +00003810 }else{
shane86f5bdb2009-10-24 02:00:07 +00003811 fprintf(stderr,"%s: Error: unknown option: %s\n", Argv0, z);
drhe1e38c42003-05-04 18:30:59 +00003812 fprintf(stderr,"Use -help for a list of options.\n");
drh1e5d0e92000-05-31 23:33:17 +00003813 return 1;
3814 }
3815 }
drh44c2eb12003-04-30 11:38:26 +00003816
drh22fbcb82004-02-01 01:22:50 +00003817 if( zFirstCmd ){
drh44c2eb12003-04-30 11:38:26 +00003818 /* Run just the command that follows the database name
3819 */
drh22fbcb82004-02-01 01:22:50 +00003820 if( zFirstCmd[0]=='.' ){
shane916f9612009-10-23 00:37:15 +00003821 rc = do_meta_command(zFirstCmd, &data);
drh99b39082013-04-17 12:19:48 +00003822 if( rc==2 ) rc = 0;
drh6ff13852001-11-25 13:18:23 +00003823 }else{
drh05782482013-10-24 15:20:20 +00003824 open_db(&data, 0);
shane626a6e42009-10-22 17:30:15 +00003825 rc = shell_exec(data.db, zFirstCmd, shell_callback, &data, &zErrMsg);
shane86f5bdb2009-10-24 02:00:07 +00003826 if( zErrMsg!=0 ){
3827 fprintf(stderr,"Error: %s\n", zErrMsg);
3828 return rc!=0 ? rc : 1;
3829 }else if( rc!=0 ){
3830 fprintf(stderr,"Error: unable to process SQL \"%s\"\n", zFirstCmd);
3831 return rc;
drh6ff13852001-11-25 13:18:23 +00003832 }
drh75897232000-05-29 14:26:00 +00003833 }
3834 }else{
drh44c2eb12003-04-30 11:38:26 +00003835 /* Run commands received from standard input
3836 */
drhc28490c2006-10-26 14:25:58 +00003837 if( stdin_is_interactive ){
drh67505e72002-04-19 12:34:06 +00003838 char *zHome;
3839 char *zHistory = 0;
drh5bb3eb92007-05-04 13:15:55 +00003840 int nHistory;
drh75897232000-05-29 14:26:00 +00003841 printf(
drh743e0032011-12-12 16:51:50 +00003842 "SQLite version %s %.19s\n" /*extra-version-info*/
drh1247aa42014-02-10 19:27:05 +00003843 "Enter \".help\" for usage hints.\n",
drh9fd301b2011-06-03 13:28:22 +00003844 sqlite3_libversion(), sqlite3_sourceid()
drh75897232000-05-29 14:26:00 +00003845 );
drhb3735912014-02-10 16:13:42 +00003846 if( warnInmemoryDb ){
drh1247aa42014-02-10 19:27:05 +00003847 printf("Connected to a ");
mistachkin378d01a2014-03-06 02:15:42 +00003848 printBold("transient in-memory database");
3849 printf(".\nUse \".open FILENAME\" to reopen on a "
drh1247aa42014-02-10 19:27:05 +00003850 "persistent database.\n");
drhb3735912014-02-10 16:13:42 +00003851 }
drh67505e72002-04-19 12:34:06 +00003852 zHome = find_home_dir();
drhea678832008-12-10 19:26:22 +00003853 if( zHome ){
drh4f21c4a2008-12-10 22:15:00 +00003854 nHistory = strlen30(zHome) + 20;
drhea678832008-12-10 19:26:22 +00003855 if( (zHistory = malloc(nHistory))!=0 ){
3856 sqlite3_snprintf(nHistory, zHistory,"%s/.sqlite_history", zHome);
3857 }
drh67505e72002-04-19 12:34:06 +00003858 }
drhaaa21b42014-02-11 14:37:51 +00003859#if defined(HAVE_READLINE)
drh67505e72002-04-19 12:34:06 +00003860 if( zHistory ) read_history(zHistory);
danielk19774af00c62005-01-23 23:43:21 +00003861#endif
drhc28490c2006-10-26 14:25:58 +00003862 rc = process_input(&data, 0);
drh67505e72002-04-19 12:34:06 +00003863 if( zHistory ){
3864 stifle_history(100);
3865 write_history(zHistory);
adamd0a3daa32006-07-28 20:16:14 +00003866 free(zHistory);
drh67505e72002-04-19 12:34:06 +00003867 }
drhdaffd0e2001-04-11 14:28:42 +00003868 }else{
drhc28490c2006-10-26 14:25:58 +00003869 rc = process_input(&data, stdin);
drh75897232000-05-29 14:26:00 +00003870 }
3871 }
drh33048c02001-10-01 14:29:22 +00003872 set_table_name(&data, 0);
drh72af0772010-05-06 20:19:55 +00003873 if( data.db ){
drhe14cd932010-12-08 03:28:17 +00003874 sqlite3_close(data.db);
adamd0a3daa32006-07-28 20:16:14 +00003875 }
drh05782482013-10-24 15:20:20 +00003876 sqlite3_free(data.zFreeOnClose);
drhc28490c2006-10-26 14:25:58 +00003877 return rc;
drh75897232000-05-29 14:26:00 +00003878}