~drizzle-trunk/drizzle/development

206.3.1 by Patrick Galbraith
Most everything working with client rename
1
/* Copyright (C) 2008 Drizzle Open Source Development Project
1 by brian
clean slate
2
3
   This program is free software; you can redistribute it and/or modify
4
   it under the terms of the GNU General Public License as published by
5
   the Free Software Foundation; version 2 of the License.
6
7
   This program is distributed in the hope that it will be useful,
8
   but WITHOUT ANY WARRANTY; without even the implied warranty of
9
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10
   GNU General Public License for more details.
11
12
   You should have received a copy of the GNU General Public License
13
   along with this program; if not, write to the Free Software
14
   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
15
279.2.4 by Monty Taylor
Moved import, check and dump to C++... fixed errors.
16
/* drizzledump.cc  - Dump a tables contents and format to an ASCII file
1 by brian
clean slate
17
**
18
** The author's original notes follow :-
19
**
20
** AUTHOR: Igor Romanenko (igor@frog.kiev.ua)
21
** DATE:   December 3, 1994
22
** WARRANTY: None, expressed, impressed, implied
23
**          or other
24
** STATUS: Public domain
25
*/
26
27
#define DUMP_VERSION "10.13"
28
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
29
#include <string>
212.5.39 by Monty Taylor
Phew. Moved my_base and my_global.
30
#include "client_priv.h"
31
212.5.13 by Monty Taylor
Moved my_sys/my_pthread/my_nosys and mysys_err to mysys.
32
#include <mysys/my_sys.h>
212.5.18 by Monty Taylor
Moved m_ctype, m_string and my_bitmap. Removed t_ctype.
33
#include <mystrings/m_string.h>
34
#include <mystrings/m_ctype.h>
212.5.17 by Monty Taylor
Moved queues and hash.
35
#include <mysys/hash.h>
1 by brian
clean slate
36
#include <stdarg.h>
37
212.5.42 by Monty Taylor
Ding dong include is dead.
38
#include <drizzled/error.h>
1 by brian
clean slate
39
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
40
using namespace std;
1 by brian
clean slate
41
/* Exit codes */
42
43
#define EX_USAGE 1
206.3.1 by Patrick Galbraith
Most everything working with client rename
44
#define EX_DRIZZLEERR 2
1 by brian
clean slate
45
#define EX_CONSCHECK 3
46
#define EX_EOM 4
47
#define EX_EOF 5 /* ferror for output file was got */
48
#define EX_ILLEGAL_TABLE 6
49
50
/* index into 'show fields from table' */
51
52
#define SHOW_FIELDNAME  0
53
#define SHOW_TYPE  1
54
#define SHOW_NULL  2
55
#define SHOW_DEFAULT  4
56
#define SHOW_EXTRA  5
57
58
/* Size of buffer for dump's select query */
59
#define QUERY_LENGTH 1536
60
61
/* ignore table flags */
62
#define IGNORE_NONE 0x00 /* no ignore */
63
#define IGNORE_DATA 0x01 /* don't dump data for this table */
64
#define IGNORE_INSERT_DELAYED 0x02 /* table doesn't support INSERT DELAYED */
65
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
66
static void add_load_option(string &str, const char *option,
67
                            const char *option_value);
288 by Brian Aker
ulong cleanp in client apps
68
static uint32_t find_set(TYPELIB *lib, const char *x, uint length,
1 by brian
clean slate
69
                      char **err_pos, uint *err_len);
70
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
71
static void field_escape(string &in, const char *from);
143 by Brian Aker
Bool cleanup.
72
static bool  verbose= 0, opt_no_create_info= 0, opt_no_data= 0,
1 by brian
clean slate
73
                quick= 1, extended_insert= 1,
74
                lock_tables=1,ignore_errors=0,flush_logs=0,flush_privileges=0,
75
                opt_drop=1,opt_keywords=0,opt_lock=1,opt_compress=0,
76
                opt_delayed=0,create_options=1,opt_quoted=0,opt_databases=0,
77
                opt_alldbs=0,opt_create_db=0,opt_lock_all_tables=0,
78
                opt_set_charset=0, opt_dump_date=1,
79
                opt_autocommit=0,opt_disable_keys=1,opt_xml=0,
80
                opt_delete_master_logs=0, tty_password=0,
81
                opt_single_transaction=0, opt_comments= 0, opt_compact= 0,
82
                opt_hex_blob=0, opt_order_by_primary=0, opt_ignore=0,
83
                opt_complete_insert= 0, opt_drop_database= 0,
84
                opt_replace_into= 0,
85
                opt_routines=0, opt_tz_utc=1,
86
                opt_slave_apply= 0, 
87
                opt_include_master_host_port= 0,
88
                opt_events= 0,
89
                opt_alltspcs=0, opt_notspcs= 0;
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
90
static bool debug_info_flag= 0, debug_check_flag= 0;
288 by Brian Aker
ulong cleanp in client apps
91
static uint32_t opt_max_allowed_packet, opt_net_buffer_length;
206.3.1 by Patrick Galbraith
Most everything working with client rename
92
static DRIZZLE drizzle_connection,*drizzle=0;
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
93
static string insert_pat;
1 by brian
clean slate
94
static char  *opt_password=0,*current_user=0,
95
             *current_host=0,*path=0,*fields_terminated=0,
96
             *lines_terminated=0, *enclosed=0, *opt_enclosed=0, *escaped=0,
97
             *where=0, *order_by=0,
98
             *opt_compatible_mode_str= 0,
99
             *err_ptr= 0,
100
             *log_error_file= NULL;
101
static char **defaults_argv= 0;
102
static char compatible_mode_normal_str[255];
103
/* Server supports character_set_results session variable? */
163 by Brian Aker
Merge Monty's code.
104
static bool server_supports_switching_charsets= true;
288 by Brian Aker
ulong cleanp in client apps
105
static uint32_t opt_compatible_mode= 0;
206.3.1 by Patrick Galbraith
Most everything working with client rename
106
#define DRIZZLE_OPT_MASTER_DATA_EFFECTIVE_SQL 1
107
#define DRIZZLE_OPT_MASTER_DATA_COMMENTED_SQL 2
108
#define DRIZZLE_OPT_SLAVE_DATA_EFFECTIVE_SQL 1
109
#define DRIZZLE_OPT_SLAVE_DATA_COMMENTED_SQL 2
110
static uint opt_drizzle_port= 0, opt_master_data;
1 by brian
clean slate
111
static uint opt_slave_data;
112
static uint my_end_arg;
113
static int   first_error=0;
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
114
static string extended_row;
1 by brian
clean slate
115
FILE *md_result_file= 0;
116
FILE *stderror_file=0;
117
206.3.1 by Patrick Galbraith
Most everything working with client rename
118
static uint opt_protocol= DRIZZLE_PROTOCOL_TCP;
1 by brian
clean slate
119
120
/*
121
  Constant for detection of default value of default_charset.
206.3.1 by Patrick Galbraith
Most everything working with client rename
122
  If default_charset is equal to drizzle_universal_client_charset, then
1 by brian
clean slate
123
  it is the default value which assigned at the very beginning of main().
124
*/
206.3.1 by Patrick Galbraith
Most everything working with client rename
125
static const char *drizzle_universal_client_charset=
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
126
  DRIZZLE_UNIVERSAL_CLIENT_CHARSET;
1 by brian
clean slate
127
static char *default_charset;
383.1.12 by Brian Aker
Much closer toward UTF8 being around all the time...
128
static const CHARSET_INFO *charset_info= &my_charset_utf8_general_ci;
206.3.1 by Patrick Galbraith
Most everything working with client rename
129
const char *default_dbug_option="d:t:o,/tmp/drizzledump.trace";
1 by brian
clean slate
130
/* have we seen any VIEWs during table scanning? */
143 by Brian Aker
Bool cleanup.
131
bool seen_views= 0;
1 by brian
clean slate
132
const char *compatible_mode_names[]=
133
{
134
  "MYSQL323", "MYSQL40", "POSTGRESQL", "ORACLE", "MSSQL", "DB2",
135
  "MAXDB", "NO_KEY_OPTIONS", "NO_TABLE_OPTIONS", "NO_FIELD_OPTIONS",
136
  "ANSI",
137
  NullS
138
};
139
#define MASK_ANSI_QUOTES \
140
(\
141
 (1<<2)  | /* POSTGRESQL */\
142
 (1<<3)  | /* ORACLE     */\
143
 (1<<4)  | /* MSSQL      */\
144
 (1<<5)  | /* DB2        */\
145
 (1<<6)  | /* MAXDB      */\
146
 (1<<10)   /* ANSI       */\
147
)
148
TYPELIB compatible_mode_typelib= {array_elements(compatible_mode_names) - 1,
149
                                  "", compatible_mode_names, NULL};
150
151
HASH ignore_table;
152
153
static struct my_option my_long_options[] =
154
{
155
  {"all", 'a', "Deprecated. Use --create-options instead.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
156
   (char**) &create_options, (char**) &create_options, 0, GET_BOOL, NO_ARG, 1,
1 by brian
clean slate
157
   0, 0, 0, 0, 0},
158
  {"all-databases", 'A',
159
   "Dump all the databases. This will be same as --databases with all databases selected.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
160
   (char**) &opt_alldbs, (char**) &opt_alldbs, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0,
1 by brian
clean slate
161
   0, 0},
162
  {"all-tablespaces", 'Y',
163
   "Dump all the tablespaces.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
164
   (char**) &opt_alltspcs, (char**) &opt_alltspcs, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0,
1 by brian
clean slate
165
   0, 0},
166
  {"no-tablespaces", 'y',
167
   "Do not dump any tablespace information.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
168
   (char**) &opt_notspcs, (char**) &opt_notspcs, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0,
1 by brian
clean slate
169
   0, 0},
170
  {"add-drop-database", OPT_DROP_DATABASE, "Add a 'DROP DATABASE' before each create.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
171
   (char**) &opt_drop_database, (char**) &opt_drop_database, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0,
1 by brian
clean slate
172
   0},
173
  {"add-drop-table", OPT_DROP, "Add a 'drop table' before each create.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
174
   (char**) &opt_drop, (char**) &opt_drop, 0, GET_BOOL, NO_ARG, 1, 0, 0, 0, 0,
1 by brian
clean slate
175
   0},
176
  {"add-locks", OPT_LOCKS, "Add locks around insert statements.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
177
   (char**) &opt_lock, (char**) &opt_lock, 0, GET_BOOL, NO_ARG, 1, 0, 0, 0, 0,
1 by brian
clean slate
178
   0},
179
  {"allow-keywords", OPT_KEYWORDS,
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
180
   "Allow creation of column names that are keywords.", (char**) &opt_keywords,
181
   (char**) &opt_keywords, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
206.3.1 by Patrick Galbraith
Most everything working with client rename
182
  {"apply-slave-statements", OPT_DRIZZLEDUMP_SLAVE_APPLY,
1 by brian
clean slate
183
   "Adds 'STOP SLAVE' prior to 'CHANGE MASTER' and 'START SLAVE' to bottom of dump.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
184
   (char**) &opt_slave_apply, (char**) &opt_slave_apply, 0, GET_BOOL, NO_ARG,
1 by brian
clean slate
185
   0, 0, 0, 0, 0, 0},
186
  {"character-sets-dir", OPT_CHARSETS_DIR,
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
187
   "Directory where character sets are.", (char**) &charsets_dir,
188
   (char**) &charsets_dir, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
1 by brian
clean slate
189
  {"comments", 'i', "Write additional information.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
190
   (char**) &opt_comments, (char**) &opt_comments, 0, GET_BOOL, NO_ARG,
1 by brian
clean slate
191
   1, 0, 0, 0, 0, 0},
192
  {"compatible", OPT_COMPATIBLE,
206.3.1 by Patrick Galbraith
Most everything working with client rename
193
   "Change the dump to be compatible with a given mode. By default tables are dumped in a format optimized for MySQL. Legal modes are: ansi, mysql323, mysql40, postgresql, oracle, mssql, db2, maxdb, no_key_options, no_table_options, no_field_options. One can use several modes separated by commas. Note: Requires DRIZZLE server version 4.1.0 or higher. This option is ignored with earlier server versions.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
194
   (char**) &opt_compatible_mode_str, (char**) &opt_compatible_mode_str, 0,
1 by brian
clean slate
195
   GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
196
  {"compact", OPT_COMPACT,
197
   "Give less verbose output (useful for debugging). Disables structure comments and header/footer constructs.  Enables options --skip-add-drop-table --no-set-names --skip-disable-keys --skip-add-locks",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
198
   (char**) &opt_compact, (char**) &opt_compact, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0,
1 by brian
clean slate
199
   0, 0},
200
  {"complete-insert", 'c', "Use complete insert statements.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
201
   (char**) &opt_complete_insert, (char**) &opt_complete_insert, 0, GET_BOOL,
1 by brian
clean slate
202
   NO_ARG, 0, 0, 0, 0, 0, 0},
203
  {"compress", 'C', "Use compression in server/client protocol.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
204
   (char**) &opt_compress, (char**) &opt_compress, 0, GET_BOOL, NO_ARG, 0, 0, 0,
1 by brian
clean slate
205
   0, 0, 0},
206
  {"create-options", OPT_CREATE_OPTIONS,
206.3.1 by Patrick Galbraith
Most everything working with client rename
207
   "Include all DRIZZLE specific create options.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
208
   (char**) &create_options, (char**) &create_options, 0, GET_BOOL, NO_ARG, 1,
1 by brian
clean slate
209
   0, 0, 0, 0, 0},
210
  {"databases", 'B',
211
   "To dump several databases. Note the difference in usage; In this case no tables are given. All name arguments are regarded as databasenames. 'USE db_name;' will be included in the output.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
212
   (char**) &opt_databases, (char**) &opt_databases, 0, GET_BOOL, NO_ARG, 0, 0,
1 by brian
clean slate
213
   0, 0, 0, 0},
214
  {"debug-check", OPT_DEBUG_CHECK, "Check memory and open file usage at exit.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
215
   (char**) &debug_check_flag, (char**) &debug_check_flag, 0,
1 by brian
clean slate
216
   GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
217
  {"debug-info", OPT_DEBUG_INFO, "Print some debug info at exit.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
218
   (char**) &debug_info_flag, (char**) &debug_info_flag,
1 by brian
clean slate
219
   0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
220
  {"default-character-set", OPT_DEFAULT_CHARSET,
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
221
   "Set the default character set.", (char**) &default_charset,
222
   (char**) &default_charset, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
1 by brian
clean slate
223
  {"delayed-insert", OPT_DELAYED, "Insert rows with INSERT DELAYED; ",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
224
   (char**) &opt_delayed, (char**) &opt_delayed, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0,
1 by brian
clean slate
225
   0, 0},
226
  {"delete-master-logs", OPT_DELETE_MASTER_LOGS,
227
   "Delete logs on master after backup. This automatically enables --master-data.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
228
   (char**) &opt_delete_master_logs, (char**) &opt_delete_master_logs, 0,
1 by brian
clean slate
229
   GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
230
  {"disable-keys", 'K',
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
231
   "'/*!40000 ALTER TABLE tb_name DISABLE KEYS */; and '/*!40000 ALTER TABLE tb_name ENABLE KEYS */; will be put in the output.", (char**) &opt_disable_keys,
232
   (char**) &opt_disable_keys, 0, GET_BOOL, NO_ARG, 1, 0, 0, 0, 0, 0},
206.3.1 by Patrick Galbraith
Most everything working with client rename
233
  {"dump-slave", OPT_DRIZZLEDUMP_SLAVE_DATA,
1 by brian
clean slate
234
   "This causes the binary log position and filename of the master to be "
235
   "appended to the dumped data output. Setting the value to 1, will print"
236
   "it as a CHANGE MASTER command in the dumped data output; if equal"
237
   " to 2, that command will be prefixed with a comment symbol. "
238
   "This option will turn --lock-all-tables on, unless "
239
   "--single-transaction is specified too (in which case a "
240
   "global read lock is only taken a short time at the beginning of the dump "
241
   "- don't forget to read about --single-transaction below). In all cases "
242
   "any action on logs will happen at the exact moment of the dump."
243
   "Option automatically turns --lock-tables off.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
244
   (char**) &opt_slave_data, (char**) &opt_slave_data, 0,
206.3.1 by Patrick Galbraith
Most everything working with client rename
245
   GET_UINT, OPT_ARG, 0, 0, DRIZZLE_OPT_SLAVE_DATA_COMMENTED_SQL, 0, 0, 0},
1 by brian
clean slate
246
  {"events", 'E', "Dump events.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
247
     (char**) &opt_events, (char**) &opt_events, 0, GET_BOOL,
1 by brian
clean slate
248
     NO_ARG, 0, 0, 0, 0, 0, 0},
249
  {"extended-insert", 'e',
250
   "Allows utilization of the new, much faster INSERT syntax.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
251
   (char**) &extended_insert, (char**) &extended_insert, 0, GET_BOOL, NO_ARG,
1 by brian
clean slate
252
   1, 0, 0, 0, 0, 0},
253
  {"fields-terminated-by", OPT_FTB,
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
254
   "Fields in the textfile are terminated by ...", (char**) &fields_terminated,
255
   (char**) &fields_terminated, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
1 by brian
clean slate
256
  {"fields-enclosed-by", OPT_ENC,
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
257
   "Fields in the importfile are enclosed by ...", (char**) &enclosed,
258
   (char**) &enclosed, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0 ,0, 0},
1 by brian
clean slate
259
  {"fields-optionally-enclosed-by", OPT_O_ENC,
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
260
   "Fields in the i.file are opt. enclosed by ...", (char**) &opt_enclosed,
261
   (char**) &opt_enclosed, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0 ,0, 0},
1 by brian
clean slate
262
  {"fields-escaped-by", OPT_ESC, "Fields in the i.file are escaped by ...",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
263
   (char**) &escaped, (char**) &escaped, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
1 by brian
clean slate
264
  {"first-slave", 'x', "Deprecated, renamed to --lock-all-tables.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
265
   (char**) &opt_lock_all_tables, (char**) &opt_lock_all_tables, 0, GET_BOOL, NO_ARG,
1 by brian
clean slate
266
   0, 0, 0, 0, 0, 0},
267
  {"flush-logs", 'F', "Flush logs file in server before starting dump. "
268
   "Note that if you dump many databases at once (using the option "
269
   "--databases= or --all-databases), the logs will be flushed for "
270
   "each database dumped. The exception is when using --lock-all-tables "
271
   "or --master-data: "
272
   "in this case the logs will be flushed only once, corresponding "
273
   "to the moment all tables are locked. So if you want your dump and "
274
   "the log flush to happen at the same exact moment you should use "
275
   "--lock-all-tables or --master-data with --flush-logs",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
276
   (char**) &flush_logs, (char**) &flush_logs, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0,
1 by brian
clean slate
277
   0, 0},
278
  {"flush-privileges", OPT_ESC, "Emit a FLUSH PRIVILEGES statement "
206.3.1 by Patrick Galbraith
Most everything working with client rename
279
   "after dumping the DRIZZLE database.  This option should be used any "
280
   "time the dump contains the DRIZZLE database and any other database "
281
   "that depends on the data in the DRIZZLE database for proper restore. ",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
282
   (char**) &flush_privileges, (char**) &flush_privileges, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0,
1 by brian
clean slate
283
   0, 0},
284
  {"force", 'f', "Continue even if we get an sql-error.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
285
   (char**) &ignore_errors, (char**) &ignore_errors, 0, GET_BOOL, NO_ARG,
1 by brian
clean slate
286
   0, 0, 0, 0, 0, 0},
287
  {"help", '?', "Display this help message and exit.", 0, 0, 0, GET_NO_ARG,
288
   NO_ARG, 0, 0, 0, 0, 0, 0},
289
  {"hex-blob", OPT_HEXBLOB, "Dump binary strings (BINARY, "
290
    "VARBINARY, BLOB) in hexadecimal format.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
291
   (char**) &opt_hex_blob, (char**) &opt_hex_blob, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
292
  {"host", 'h', "Connect to host.", (char**) &current_host,
293
   (char**) &current_host, 0, GET_STR_ALLOC, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
1 by brian
clean slate
294
  {"ignore-table", OPT_IGNORE_TABLE,
295
   "Do not dump the specified table. To specify more than one table to ignore, "
296
   "use the directive multiple times, once for each table.  Each table must "
297
   "be specified with both database and table names, e.g. --ignore-table=database.table",
298
   0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
206.3.1 by Patrick Galbraith
Most everything working with client rename
299
  {"include-master-host-port", OPT_DRIZZLEDUMP_INCLUDE_MASTER_HOST_PORT,
1 by brian
clean slate
300
   "Adds 'MASTER_HOST=<host>, MASTER_PORT=<port>' to 'CHANGE MASTER TO..' in dump produced with --dump-slave.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
301
   (char**) &opt_include_master_host_port, 
302
   (char**) &opt_include_master_host_port, 
1 by brian
clean slate
303
   0, GET_BOOL, NO_ARG,
304
   0, 0, 0, 0, 0, 0},
305
  {"insert-ignore", OPT_INSERT_IGNORE, "Insert rows with INSERT IGNORE.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
306
   (char**) &opt_ignore, (char**) &opt_ignore, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0,
1 by brian
clean slate
307
   0, 0},
308
  {"lines-terminated-by", OPT_LTB, "Lines in the i.file are terminated by ...",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
309
   (char**) &lines_terminated, (char**) &lines_terminated, 0, GET_STR,
1 by brian
clean slate
310
   REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
311
  {"lock-all-tables", 'x', "Locks all tables across all databases. This "
312
   "is achieved by taking a global read lock for the duration of the whole "
313
   "dump. Automatically turns --single-transaction and --lock-tables off.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
314
   (char**) &opt_lock_all_tables, (char**) &opt_lock_all_tables, 0, GET_BOOL, NO_ARG,
1 by brian
clean slate
315
   0, 0, 0, 0, 0, 0},
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
316
  {"lock-tables", 'l', "Lock all tables for read.", (char**) &lock_tables,
317
   (char**) &lock_tables, 0, GET_BOOL, NO_ARG, 1, 0, 0, 0, 0, 0},
1 by brian
clean slate
318
  {"log-error", OPT_ERROR_LOG_FILE, "Append warnings and errors to given file.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
319
   (char**) &log_error_file, (char**) &log_error_file, 0, GET_STR,
1 by brian
clean slate
320
   REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
321
  {"master-data", OPT_MASTER_DATA,
322
   "This causes the binary log position and filename to be appended to the "
323
   "output. If equal to 1, will print it as a CHANGE MASTER command; if equal"
324
   " to 2, that command will be prefixed with a comment symbol. "
325
   "This option will turn --lock-all-tables on, unless "
326
   "--single-transaction is specified too (in which case a "
327
   "global read lock is only taken a short time at the beginning of the dump "
328
   "- don't forget to read about --single-transaction below). In all cases "
329
   "any action on logs will happen at the exact moment of the dump."
330
   "Option automatically turns --lock-tables off.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
331
   (char**) &opt_master_data, (char**) &opt_master_data, 0,
206.3.1 by Patrick Galbraith
Most everything working with client rename
332
   GET_UINT, OPT_ARG, 0, 0, DRIZZLE_OPT_MASTER_DATA_COMMENTED_SQL, 0, 0, 0},
1 by brian
clean slate
333
  {"max_allowed_packet", OPT_MAX_ALLOWED_PACKET, "",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
334
    (char**) &opt_max_allowed_packet, (char**) &opt_max_allowed_packet, 0,
1 by brian
clean slate
335
    GET_ULONG, REQUIRED_ARG, 24*1024*1024, 4096,
152 by Brian Aker
longlong replacement
336
   (int64_t) 2L*1024L*1024L*1024L, MALLOC_OVERHEAD, 1024, 0},
1 by brian
clean slate
337
  {"net_buffer_length", OPT_NET_BUFFER_LENGTH, "",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
338
    (char**) &opt_net_buffer_length, (char**) &opt_net_buffer_length, 0,
1 by brian
clean slate
339
    GET_ULONG, REQUIRED_ARG, 1024*1024L-1025, 4096, 16*1024L*1024L,
340
   MALLOC_OVERHEAD-1024, 1024, 0},
341
  {"no-autocommit", OPT_AUTOCOMMIT,
342
   "Wrap tables with autocommit/commit statements.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
343
   (char**) &opt_autocommit, (char**) &opt_autocommit, 0, GET_BOOL, NO_ARG,
1 by brian
clean slate
344
   0, 0, 0, 0, 0, 0},
345
  {"no-create-db", 'n',
346
   "'CREATE DATABASE /*!32312 IF NOT EXISTS*/ db_name;' will not be put in the output. The above line will be added otherwise, if --databases or --all-databases option was given.}.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
347
   (char**) &opt_create_db, (char**) &opt_create_db, 0, GET_BOOL, NO_ARG, 0, 0,
1 by brian
clean slate
348
   0, 0, 0, 0},
349
  {"no-create-info", 't', "Don't write table creation info.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
350
   (char**) &opt_no_create_info, (char**) &opt_no_create_info, 0, GET_BOOL,
1 by brian
clean slate
351
   NO_ARG, 0, 0, 0, 0, 0, 0},
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
352
  {"no-data", 'd', "No row information.", (char**) &opt_no_data,
353
   (char**) &opt_no_data, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
1 by brian
clean slate
354
  {"no-set-names", 'N',
355
   "Deprecated. Use --skip-set-charset instead.",
356
   0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0},
357
  {"opt", OPT_OPTIMIZE,
358
   "Same as --add-drop-table, --add-locks, --create-options, --quick, --extended-insert, --lock-tables, --set-charset, and --disable-keys. Enabled by default, disable with --skip-opt.",
359
   0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0},
360
  {"order-by-primary", OPT_ORDER_BY_PRIMARY,
361
   "Sorts each table's rows by primary key, or first unique key, if such a key exists.  Useful when dumping a MyISAM table to be loaded into an InnoDB table, but will make the dump itself take considerably longer.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
362
   (char**) &opt_order_by_primary, (char**) &opt_order_by_primary, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
1 by brian
clean slate
363
  {"password", 'p',
364
   "Password to use when connecting to server. If password is not given it's solicited on the tty.",
365
   0, 0, 0, GET_STR, OPT_ARG, 0, 0, 0, 0, 0, 0},
206.3.1 by Patrick Galbraith
Most everything working with client rename
366
  {"port", 'P', "Port number to use for connection.", (char**) &opt_drizzle_port,
367
   (char**) &opt_drizzle_port, 0, GET_UINT, REQUIRED_ARG, 0, 0, 0, 0, 0,
1 by brian
clean slate
368
   0},
369
  {"quick", 'q', "Don't buffer query, dump directly to stdout.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
370
   (char**) &quick, (char**) &quick, 0, GET_BOOL, NO_ARG, 1, 0, 0, 0, 0, 0},
1 by brian
clean slate
371
  {"quote-names",'Q', "Quote table and column names with backticks (`).",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
372
   (char**) &opt_quoted, (char**) &opt_quoted, 0, GET_BOOL, NO_ARG, 1, 0, 0, 0,
1 by brian
clean slate
373
   0, 0},
206.3.1 by Patrick Galbraith
Most everything working with client rename
374
  {"replace", OPT_DRIZZLE_REPLACE_INTO, "Use REPLACE INTO instead of INSERT INTO.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
375
   (char**) &opt_replace_into, (char**) &opt_replace_into, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0,
1 by brian
clean slate
376
   0, 0},
377
  {"result-file", 'r',
378
   "Direct output to a given file. This option should be used in MSDOS, because it prevents new line '\\n' from being converted to '\\r\\n' (carriage return + line feed).",
379
   0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
380
  {"routines", 'R', "Dump stored routines (functions and procedures).",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
381
     (char**) &opt_routines, (char**) &opt_routines, 0, GET_BOOL,
1 by brian
clean slate
382
     NO_ARG, 0, 0, 0, 0, 0, 0},
383
  {"set-charset", OPT_SET_CHARSET,
384
   "Add 'SET NAMES default_character_set' to the output.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
385
   (char**) &opt_set_charset, (char**) &opt_set_charset, 0, GET_BOOL, NO_ARG, 1,
1 by brian
clean slate
386
   0, 0, 0, 0, 0},
387
  {"set-variable", 'O',
388
   "Change the value of a variable. Please note that this option is deprecated; you can set variables directly with --variable-name=value.",
389
   0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
390
  /*
391
    Note that the combination --single-transaction --master-data
392
    will give bullet-proof binlog position only if server >=4.1.3. That's the
393
    old "FLUSH TABLES WITH READ LOCK does not block commit" fixed bug.
394
  */
395
  {"single-transaction", OPT_TRANSACTION,
396
   "Creates a consistent snapshot by dumping all tables in a single "
397
   "transaction. Works ONLY for tables stored in storage engines which "
398
   "support multiversioning (currently only InnoDB does); the dump is NOT "
399
   "guaranteed to be consistent for other storage engines. "
400
   "While a --single-transaction dump is in process, to ensure a valid "
401
   "dump file (correct table contents and binary log position), no other "
402
   "connection should use the following statements: ALTER TABLE, DROP "
403
   "TABLE, RENAME TABLE, TRUNCATE TABLE, as consistent snapshot is not "
404
   "isolated from them. Option automatically turns off --lock-tables.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
405
   (char**) &opt_single_transaction, (char**) &opt_single_transaction, 0,
1 by brian
clean slate
406
   GET_BOOL, NO_ARG,  0, 0, 0, 0, 0, 0},
407
  {"dump-date", OPT_DUMP_DATE, "Put a dump date to the end of the output.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
408
   (char**) &opt_dump_date, (char**) &opt_dump_date, 0,
1 by brian
clean slate
409
   GET_BOOL, NO_ARG, 1, 0, 0, 0, 0, 0},
410
  {"skip-opt", OPT_SKIP_OPTIMIZATION,
411
   "Disable --opt. Disables --add-drop-table, --add-locks, --create-options, --quick, --extended-insert, --lock-tables, --set-charset, and --disable-keys.",
412
   0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0},
413
  {"tab",'T',
414
   "Creates tab separated textfile for each table to given path. (creates .sql and .txt files). NOTE: This only works if mysqldump is run on the same machine as the mysqld daemon.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
415
   (char**) &path, (char**) &path, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
1 by brian
clean slate
416
  {"tables", OPT_TABLES, "Overrides option --databases (-B).",
417
   0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0},
418
  {"tz-utc", OPT_TZ_UTC,
419
    "SET TIME_ZONE='+00:00' at top of dump to allow dumping of TIMESTAMP data when a server has data in different time zones or data is being moved between servers with different time zones.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
420
    (char**) &opt_tz_utc, (char**) &opt_tz_utc, 0, GET_BOOL, NO_ARG, 1, 0, 0, 0, 0, 0},
1 by brian
clean slate
421
#ifndef DONT_ALLOW_USER_CHANGE
422
  {"user", 'u', "User for login if not current user.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
423
   (char**) &current_user, (char**) &current_user, 0, GET_STR, REQUIRED_ARG,
1 by brian
clean slate
424
   0, 0, 0, 0, 0, 0},
425
#endif
426
  {"verbose", 'v', "Print info about the various stages.",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
427
   (char**) &verbose, (char**) &verbose, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
1 by brian
clean slate
428
  {"version",'V', "Output version information and exit.", 0, 0, 0,
429
   GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0},
430
  {"where", 'w', "Dump only selected records; QUOTES mandatory!",
77.1.77 by Monty Taylor
A crapton more warning cleanups (I turned on more warnings)
431
   (char**) &where, (char**) &where, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
1 by brian
clean slate
432
  {"xml", 'X', "Dump a database as well formed XML.", 0, 0, 0, GET_NO_ARG,
433
   NO_ARG, 0, 0, 0, 0, 0, 0},
434
  {0, 0, 0, 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0}
435
};
436
206.3.1 by Patrick Galbraith
Most everything working with client rename
437
static const char *load_default_groups[]= { "drizzledump","client",0 };
1 by brian
clean slate
438
439
static void maybe_exit(int error);
440
static void die(int error, const char* reason, ...);
441
static void maybe_die(int error, const char* reason, ...);
442
static void write_header(FILE *sql_file, char *db_name);
206.3.1 by Patrick Galbraith
Most everything working with client rename
443
static void print_value(FILE *file, DRIZZLE_RES  *result, DRIZZLE_ROW row,
1 by brian
clean slate
444
                        const char *prefix,const char *name,
445
                        int string_value);
446
static int dump_selected_tables(char *db, char **table_names, int tables);
447
static int dump_all_tables_in_db(char *db);
448
static int init_dumping_tables(char *);
449
static int init_dumping(char *, int init_func(char*));
450
static int dump_databases(char **);
53.2.4 by Monty Taylor
Changes so that client/ builds cleanly with no warnings.
451
static int dump_all_databases(void);
143 by Brian Aker
Bool cleanup.
452
static char *quote_name(const char *name, char *buff, bool force);
1 by brian
clean slate
453
char check_if_ignore_table(const char *table_name, char *table_type);
454
static char *primary_key_fields(const char *table_name);
455
456
/*
457
  Print the supplied message if in verbose mode
458
459
  SYNOPSIS
460
    verbose_msg()
461
    fmt   format specifier
462
    ...   variable number of parameters
463
*/
464
static void verbose_msg(const char *fmt, ...)
465
{
466
  va_list args;
142.1.2 by Patrick
All DBUG_x removed from client/
467
1 by brian
clean slate
468
469
  if (!verbose)
142.1.2 by Patrick
All DBUG_x removed from client/
470
    return;
1 by brian
clean slate
471
472
  va_start(args, fmt);
473
  vfprintf(stderr, fmt, args);
474
  va_end(args);
475
142.1.2 by Patrick
All DBUG_x removed from client/
476
  return;
1 by brian
clean slate
477
}
478
479
/*
480
  exit with message if ferror(file)
481
482
  SYNOPSIS
483
    check_io()
484
    file        - checked file
485
*/
486
53.2.4 by Monty Taylor
Changes so that client/ builds cleanly with no warnings.
487
static void check_io(FILE *file)
1 by brian
clean slate
488
{
489
  if (ferror(file))
490
    die(EX_EOF, "Got errno %d on write", errno);
491
}
492
493
static void print_version(void)
494
{
495
  printf("%s  Ver %s Distrib %s, for %s (%s)\n",my_progname,DUMP_VERSION,
264.1.10 by Monty Taylor
Removed client insistence on version.h stuff.
496
         drizzle_get_client_info(),SYSTEM_TYPE,MACHINE_TYPE);
1 by brian
clean slate
497
} /* print_version */
498
499
500
static void short_usage_sub(void)
501
{
502
  printf("Usage: %s [OPTIONS] database [tables]\n", my_progname);
503
  printf("OR     %s [OPTIONS] --databases [OPTIONS] DB1 [DB2 DB3...]\n",
504
         my_progname);
505
  printf("OR     %s [OPTIONS] --all-databases [OPTIONS]\n", my_progname);
506
}
507
508
509
static void usage(void)
510
{
511
  print_version();
512
  puts("By Igor Romanenko, Monty, Jani & Sinisa");
513
  puts("This software comes with ABSOLUTELY NO WARRANTY. This is free software,\nand you are welcome to modify and redistribute it under the GPL license\n");
206.3.1 by Patrick Galbraith
Most everything working with client rename
514
  puts("Dumping definition and data DRIZZLE database or table");
1 by brian
clean slate
515
  short_usage_sub();
516
  print_defaults("my",load_default_groups);
517
  my_print_help(my_long_options);
518
  my_print_variables(my_long_options);
519
} /* usage */
520
521
522
static void short_usage(void)
523
{
524
  short_usage_sub();
525
  printf("For more options, use %s --help\n", my_progname);
526
}
527
528
static void write_header(FILE *sql_file, char *db_name)
529
{
530
  if (opt_xml)
531
  {
532
    fputs("<?xml version=\"1.0\"?>\n", sql_file);
533
    /*
534
      Schema reference.  Allows use of xsi:nil for NULL values and 
535
      xsi:type to define an element's data type.
536
    */
206.3.1 by Patrick Galbraith
Most everything working with client rename
537
    fputs("<drizzledump ", sql_file);
1 by brian
clean slate
538
    fputs("xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\"",
539
          sql_file);
540
    fputs(">\n", sql_file);
541
    check_io(sql_file);
542
  }
543
  else if (!opt_compact)
544
  {
545
    if (opt_comments)
546
    {
547
      fprintf(sql_file,
206.3.1 by Patrick Galbraith
Most everything working with client rename
548
              "-- DRIZZLE dump %s  Distrib %s, for %s (%s)\n--\n",
264.1.10 by Monty Taylor
Removed client insistence on version.h stuff.
549
              DUMP_VERSION, drizzle_get_client_info(),
550
              SYSTEM_TYPE, MACHINE_TYPE);
1 by brian
clean slate
551
      fprintf(sql_file, "-- Host: %s    Database: %s\n",
552
              current_host ? current_host : "localhost", db_name ? db_name :
553
              "");
554
      fputs("-- ------------------------------------------------------\n",
555
            sql_file);
556
      fprintf(sql_file, "-- Server version\t%s\n",
206.3.1 by Patrick Galbraith
Most everything working with client rename
557
              drizzle_get_server_info(&drizzle_connection));
1 by brian
clean slate
558
    }
559
    if (opt_set_charset)
560
      fprintf(sql_file,
561
"\n/*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;"
562
"\n/*!40101 SET NAMES %s */;\n",default_charset);
563
564
    if (opt_tz_utc)
565
    {
566
      fprintf(sql_file, "/*!40103 SET @OLD_TIME_ZONE=@@TIME_ZONE */;\n");
567
      fprintf(sql_file, "/*!40103 SET TIME_ZONE='+00:00' */;\n");
568
    }
569
570
    if (!path)
571
    {
572
      fprintf(md_result_file,"\
573
/*!40014 SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0 */;\n\
574
/*!40014 SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0 */;\n\
575
");
576
    }
577
    check_io(sql_file);
578
  }
579
} /* write_header */
580
581
582
static void write_footer(FILE *sql_file)
583
{
584
  if (opt_xml)
585
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
586
    fputs("</drizzledump>\n", sql_file);
1 by brian
clean slate
587
    check_io(sql_file);
588
  }
589
  else if (!opt_compact)
590
  {
591
    if (opt_tz_utc)
592
      fprintf(sql_file,"/*!40103 SET TIME_ZONE=@OLD_TIME_ZONE */;\n");
593
594
    if (!path)
595
    {
596
      fprintf(md_result_file,"\
597
/*!40014 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS */;\n\
598
/*!40014 SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS */;\n");
599
    }
600
    if (opt_set_charset)
601
      fprintf(sql_file,
602
"/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */;\n");
603
    fprintf(sql_file,
604
            "/*!40111 SET SQL_NOTES=@OLD_SQL_NOTES */;\n");
605
    fputs("\n", sql_file);
606
    if (opt_comments)
607
    {
608
      if (opt_dump_date)
609
      {
610
        char time_str[20];
611
        get_date(time_str, GETDATE_DATE_TIME, 0);
612
        fprintf(sql_file, "-- Dump completed on %s\n",
613
                time_str);
614
      }
615
      else
616
        fprintf(sql_file, "-- Dump completed\n");
617
    }
618
    check_io(sql_file);
619
  }
620
} /* write_footer */
621
622
623
static void free_table_ent(char *key)
624
{
625
  my_free(key, MYF(0));
626
}
627
628
53.2.4 by Monty Taylor
Changes so that client/ builds cleanly with no warnings.
629
static uchar* get_table_key(const char *entry, size_t *length,
143 by Brian Aker
Bool cleanup.
630
                            bool not_used __attribute__((unused)))
1 by brian
clean slate
631
{
632
  *length= strlen(entry);
633
  return (uchar*) entry;
634
}
635
636
143 by Brian Aker
Bool cleanup.
637
static bool
1 by brian
clean slate
638
get_one_option(int optid, const struct my_option *opt __attribute__((unused)),
639
               char *argument)
640
{
641
  switch (optid) {
642
  case 'p':
643
    if (argument)
644
    {
645
      char *start=argument;
646
      my_free(opt_password,MYF(MY_ALLOW_ZERO_PTR));
647
      opt_password=my_strdup(argument,MYF(MY_FAE));
648
      while (*argument) *argument++= 'x';               /* Destroy argument */
649
      if (*start)
650
        start[1]=0;                             /* Cut length of argument */
651
      tty_password= 0;
652
    }
653
    else
654
      tty_password=1;
655
    break;
656
  case 'r':
657
    if (!(md_result_file= my_fopen(argument, O_WRONLY | FILE_BINARY,
658
                                    MYF(MY_WME))))
659
      exit(1);
660
    break;
661
  case 'N':
662
    opt_set_charset= 0;
663
    break;
664
  case 'T':
665
    opt_disable_keys=0;
666
667
    if (strlen(argument) >= FN_REFLEN)
668
    {
669
      /*
670
        This check is made because the some the file functions below
671
        have FN_REFLEN sized stack allocated buffers and will cause
672
        a crash even if the input destination buffer is large enough
673
        to hold the output.
674
      */
675
      die(EX_USAGE, "Input filename too long: %s", argument);
676
    }
677
678
    break;
679
  case 'V': print_version(); exit(0);
680
  case 'X':
681
    opt_xml= 1;
682
    extended_insert= opt_drop= opt_lock=
683
      opt_disable_keys= opt_autocommit= opt_create_db= 0;
684
    break;
685
  case 'I':
686
  case '?':
687
    usage();
688
    exit(0);
689
  case (int) OPT_MASTER_DATA:
690
    if (!argument) /* work like in old versions */
206.3.1 by Patrick Galbraith
Most everything working with client rename
691
      opt_master_data= DRIZZLE_OPT_MASTER_DATA_EFFECTIVE_SQL;
1 by brian
clean slate
692
    break;
206.3.1 by Patrick Galbraith
Most everything working with client rename
693
  case (int) OPT_DRIZZLEDUMP_SLAVE_DATA:
1 by brian
clean slate
694
    if (!argument) /* work like in old versions */
206.3.1 by Patrick Galbraith
Most everything working with client rename
695
      opt_slave_data= DRIZZLE_OPT_SLAVE_DATA_EFFECTIVE_SQL;
1 by brian
clean slate
696
    break;
697
  case (int) OPT_OPTIMIZE:
698
    extended_insert= opt_drop= opt_lock= quick= create_options=
699
      opt_disable_keys= lock_tables= opt_set_charset= 1;
700
    break;
701
  case (int) OPT_SKIP_OPTIMIZATION:
702
    extended_insert= opt_drop= opt_lock= quick= create_options=
703
      opt_disable_keys= lock_tables= opt_set_charset= 0;
704
    break;
705
  case (int) OPT_COMPACT:
706
  if (opt_compact)
707
  {
708
    opt_comments= opt_drop= opt_disable_keys= opt_lock= 0;
709
    opt_set_charset= 0;
710
  }
711
  case (int) OPT_TABLES:
712
    opt_databases=0;
713
    break;
714
  case (int) OPT_IGNORE_TABLE:
715
  {
716
    if (!strchr(argument, '.'))
717
    {
718
      fprintf(stderr, "Illegal use of option --ignore-table=<database>.<table>\n");
719
      exit(1);
720
    }
721
    if (my_hash_insert(&ignore_table, (uchar*)my_strdup(argument, MYF(0))))
722
      exit(EX_EOM);
723
    break;
724
  }
725
  case (int) OPT_COMPATIBLE:
726
    {
727
      char buff[255];
728
      char *end= compatible_mode_normal_str;
297 by Brian Aker
Final ulong cleanup in clients
729
      uint32_t i;
288 by Brian Aker
ulong cleanp in client apps
730
      uint32_t mode;
297 by Brian Aker
Final ulong cleanup in clients
731
      uint32_t error_len;
1 by brian
clean slate
732
733
      opt_quoted= 1;
734
      opt_set_charset= 0;
735
      opt_compatible_mode_str= argument;
736
      opt_compatible_mode= find_set(&compatible_mode_typelib,
737
                                    argument, strlen(argument),
297 by Brian Aker
Final ulong cleanup in clients
738
                                    &err_ptr, &error_len);
739
      if (error_len)
1 by brian
clean slate
740
      {
297 by Brian Aker
Final ulong cleanup in clients
741
        strmake(buff, err_ptr, min(sizeof(buff), error_len));
1 by brian
clean slate
742
        fprintf(stderr, "Invalid mode to --compatible: %s\n", buff);
743
        exit(1);
744
      }
745
      mode= opt_compatible_mode;
746
      for (i= 0, mode= opt_compatible_mode; mode; mode>>= 1, i++)
747
      {
748
        if (mode & 1)
749
        {
266.1.21 by Monty Taylor
Removed references to strmov and strnmov
750
          end= stpcpy(end, compatible_mode_names[i]);
751
          end= stpcpy(end, ",");
1 by brian
clean slate
752
        }
753
      }
754
      if (end!=compatible_mode_normal_str)
755
        end[-1]= 0;
756
      /*
757
        Set charset to the default compiled value if it hasn't
758
        been reset yet by --default-character-set=xxx.
759
      */
206.3.1 by Patrick Galbraith
Most everything working with client rename
760
      if (default_charset == drizzle_universal_client_charset)
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
761
        default_charset= (char*) DRIZZLE_DEFAULT_CHARSET_NAME;
1 by brian
clean slate
762
      break;
763
    }
764
  }
765
  return 0;
766
}
767
768
static int get_options(int *argc, char ***argv)
769
{
770
  int ho_error;
236.3.5 by Andrey Hristov
Constify libdrizzle functions
771
  const DRIZZLE_PARAMETERS *drizzle_params= drizzle_get_parameters();
1 by brian
clean slate
772
206.3.1 by Patrick Galbraith
Most everything working with client rename
773
  opt_max_allowed_packet= *drizzle_params->p_max_allowed_packet;
774
  opt_net_buffer_length= *drizzle_params->p_net_buffer_length;
1 by brian
clean slate
775
776
  md_result_file= stdout;
777
  load_defaults("my",load_default_groups,argc,argv);
778
  defaults_argv= *argv;
779
780
  if (hash_init(&ignore_table, charset_info, 16, 0, 0,
781
                (hash_get_key) get_table_key,
782
                (hash_free_key) free_table_ent, 0))
783
    return(EX_EOM);
784
  /* Don't copy internal log tables */
785
  if (my_hash_insert(&ignore_table,
786
                     (uchar*) my_strdup("mysql.apply_status", MYF(MY_WME))) ||
787
      my_hash_insert(&ignore_table,
788
                     (uchar*) my_strdup("mysql.schema", MYF(MY_WME))) ||
789
      my_hash_insert(&ignore_table,
790
                     (uchar*) my_strdup("mysql.general_log", MYF(MY_WME))) ||
791
      my_hash_insert(&ignore_table,
792
                     (uchar*) my_strdup("mysql.slow_log", MYF(MY_WME))) ||
793
      my_hash_insert(&ignore_table,
794
                     (uchar*) my_strdup("mysql.online_backup", MYF(MY_WME))) ||
795
      my_hash_insert(&ignore_table,
796
                     (uchar*) my_strdup("mysql.online_backup_progress", MYF(MY_WME))))
797
    return(EX_EOM);
798
799
  if ((ho_error= handle_options(argc, argv, my_long_options, get_one_option)))
800
    return(ho_error);
801
206.3.1 by Patrick Galbraith
Most everything working with client rename
802
  *drizzle_params->p_max_allowed_packet= opt_max_allowed_packet;
803
  *drizzle_params->p_net_buffer_length= opt_net_buffer_length;
1 by brian
clean slate
804
  if (debug_info_flag)
805
    my_end_arg= MY_CHECK_ERROR | MY_GIVE_INFO;
806
  if (debug_check_flag)
807
    my_end_arg= MY_CHECK_ERROR;
808
809
  if (opt_delayed)
810
    opt_lock=0;                         /* Can't have lock with delayed */
811
  if (!path && (enclosed || opt_enclosed || escaped || lines_terminated ||
812
                fields_terminated))
813
  {
814
    fprintf(stderr,
815
            "%s: You must use option --tab with --fields-...\n", my_progname);
816
    return(EX_USAGE);
817
  }
818
819
  /* We don't delete master logs if slave data option */
820
  if (opt_slave_data)
821
  {
822
    opt_lock_all_tables= !opt_single_transaction;
823
    opt_master_data= 0;
824
    opt_delete_master_logs= 0;
825
  }
826
827
  /* Ensure consistency of the set of binlog & locking options */
828
  if (opt_delete_master_logs && !opt_master_data)
206.3.1 by Patrick Galbraith
Most everything working with client rename
829
    opt_master_data= DRIZZLE_OPT_MASTER_DATA_COMMENTED_SQL;
1 by brian
clean slate
830
  if (opt_single_transaction && opt_lock_all_tables)
831
  {
832
    fprintf(stderr, "%s: You can't use --single-transaction and "
833
            "--lock-all-tables at the same time.\n", my_progname);
834
    return(EX_USAGE);
835
  }
836
  if (opt_master_data)
837
  {
838
    opt_lock_all_tables= !opt_single_transaction;
839
    opt_slave_data= 0;
840
  }
841
  if (opt_single_transaction || opt_lock_all_tables)
842
    lock_tables= 0;
843
  if (enclosed && opt_enclosed)
844
  {
845
    fprintf(stderr, "%s: You can't use ..enclosed.. and ..optionally-enclosed.. at the same time.\n", my_progname);
846
    return(EX_USAGE);
847
  }
848
  if ((opt_databases || opt_alldbs) && path)
849
  {
850
    fprintf(stderr,
851
            "%s: --databases or --all-databases can't be used with --tab.\n",
852
            my_progname);
853
    return(EX_USAGE);
854
  }
855
  if (strcmp(default_charset, charset_info->csname) &&
856
      !(charset_info= get_charset_by_csname(default_charset,
857
                                            MY_CS_PRIMARY, MYF(MY_WME))))
858
    exit(1);
859
  if ((*argc < 1 && !opt_alldbs) || (*argc > 0 && opt_alldbs))
860
  {
861
    short_usage();
862
    return EX_USAGE;
863
  }
864
  if (tty_password)
865
    opt_password=get_tty_password(NullS);
866
  return(0);
867
} /* get_options */
868
869
870
/*
206.3.1 by Patrick Galbraith
Most everything working with client rename
871
** DB_error -- prints DRIZZLE error message and exits the program.
1 by brian
clean slate
872
*/
206.3.1 by Patrick Galbraith
Most everything working with client rename
873
static void DB_error(DRIZZLE *drizzle_arg, const char *when)
1 by brian
clean slate
874
{
142.1.2 by Patrick
All DBUG_x removed from client/
875
206.3.1 by Patrick Galbraith
Most everything working with client rename
876
  maybe_die(EX_DRIZZLEERR, "Got error: %d: %s %s",
877
          drizzle_errno(drizzle_arg), drizzle_error(drizzle_arg), when);
142.1.2 by Patrick
All DBUG_x removed from client/
878
  return;
1 by brian
clean slate
879
}
880
881
882
883
/*
884
  Prints out an error message and kills the process.
885
886
  SYNOPSIS
887
    die()
888
    error_num   - process return value
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
889
    fmt_reason  - a format string for use by vsnprintf.
1 by brian
clean slate
890
    ...         - variable arguments for above fmt_reason string
891
  
892
  DESCRIPTION
893
    This call prints out the formatted error message to stderr and then
894
    terminates the process.
895
*/
896
static void die(int error_num, const char* fmt_reason, ...)
897
{
898
  char buffer[1000];
899
  va_list args;
900
  va_start(args,fmt_reason);
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
901
  vsnprintf(buffer, sizeof(buffer), fmt_reason, args);
1 by brian
clean slate
902
  va_end(args);
903
904
  fprintf(stderr, "%s: %s\n", my_progname, buffer);
905
  fflush(stderr);
906
907
  ignore_errors= 0; /* force the exit */
908
  maybe_exit(error_num);
909
}
910
911
912
/*
913
  Prints out an error message and maybe kills the process.
914
915
  SYNOPSIS
916
    maybe_die()
917
    error_num   - process return value
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
918
    fmt_reason  - a format string for use by vsnprintf.
1 by brian
clean slate
919
    ...         - variable arguments for above fmt_reason string
920
  
921
  DESCRIPTION
922
    This call prints out the formatted error message to stderr and then
923
    terminates the process, unless the --force command line option is used.
924
    
925
    This call should be used for non-fatal errors (such as database
926
    errors) that the code may still be able to continue to the next unit
927
    of work.
928
    
929
*/
930
static void maybe_die(int error_num, const char* fmt_reason, ...)
931
{
932
  char buffer[1000];
933
  va_list args;
934
  va_start(args,fmt_reason);
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
935
  vsnprintf(buffer, sizeof(buffer), fmt_reason, args);
1 by brian
clean slate
936
  va_end(args);
937
938
  fprintf(stderr, "%s: %s\n", my_progname, buffer);
939
  fflush(stderr);
940
941
  maybe_exit(error_num);
942
}
943
944
945
946
/*
947
  Sends a query to server, optionally reads result, prints error message if
948
  some.
949
950
  SYNOPSIS
206.3.1 by Patrick Galbraith
Most everything working with client rename
951
    drizzle_query_with_error_report()
952
    drizzle_con       connection to use
1 by brian
clean slate
953
    res             if non zero, result will be put there with
206.3.1 by Patrick Galbraith
Most everything working with client rename
954
                    drizzle_store_result()
1 by brian
clean slate
955
    query           query to send to server
956
957
  RETURN VALUES
958
    0               query sending and (if res!=0) result reading went ok
959
    1               error
960
*/
961
206.3.1 by Patrick Galbraith
Most everything working with client rename
962
static int drizzle_query_with_error_report(DRIZZLE *drizzle_con, DRIZZLE_RES **res,
1 by brian
clean slate
963
                                         const char *query)
964
{
206.3.1 by Patrick Galbraith
Most everything working with client rename
965
  if (drizzle_query(drizzle_con, query) ||
966
      (res && !((*res)= drizzle_store_result(drizzle_con))))
1 by brian
clean slate
967
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
968
    maybe_die(EX_DRIZZLEERR, "Couldn't execute '%s': %s (%d)",
969
            query, drizzle_error(drizzle_con), drizzle_errno(drizzle_con));
1 by brian
clean slate
970
    return 1;
971
  }
972
  return 0;
973
}
974
975
976
/**
977
  Switch charset for results to some specified charset.  If the server does not
978
  support character_set_results variable, nothing can be done here.  As for
979
  whether something should be done here, future new callers of this function
980
  should be aware that the server lacking the facility of switching charsets is
981
  treated as success.
982
983
  @note  If the server lacks support, then nothing is changed and no error
984
         condition is returned.
985
986
  @returns  whether there was an error or not
987
*/
206.3.1 by Patrick Galbraith
Most everything working with client rename
988
static int switch_character_set_results(DRIZZLE *drizzle, const char *cs_name)
1 by brian
clean slate
989
{
990
  char query_buffer[QUERY_LENGTH];
991
  size_t query_length;
992
993
  /* Server lacks facility.  This is not an error, by arbitrary decision . */
994
  if (!server_supports_switching_charsets)
163 by Brian Aker
Merge Monty's code.
995
    return false;
1 by brian
clean slate
996
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
997
  query_length= snprintf(query_buffer,
998
                         sizeof (query_buffer),
999
                         "SET SESSION character_set_results = '%s'",
1000
                         (const char *) cs_name);
1 by brian
clean slate
1001
206.3.1 by Patrick Galbraith
Most everything working with client rename
1002
  return drizzle_real_query(drizzle, query_buffer, query_length);
1 by brian
clean slate
1003
}
1004
1005
/*
1006
  Open a new .sql file to dump the table or view into
1007
1008
  SYNOPSIS
1009
    open_sql_file_for_table
1010
    name      name of the table or view
1011
1012
  RETURN VALUES
1013
    0        Failed to open file
1014
    > 0      Handle of the open file
1015
*/
1016
static FILE* open_sql_file_for_table(const char* table)
1017
{
1018
  FILE* res;
1019
  char filename[FN_REFLEN], tmp_path[FN_REFLEN];
1020
  convert_dirname(tmp_path,path,NullS);
1021
  res= my_fopen(fn_format(filename, table, tmp_path, ".sql", 4),
1022
                O_WRONLY, MYF(MY_WME));
1023
  return res;
1024
}
1025
1026
53.2.4 by Monty Taylor
Changes so that client/ builds cleanly with no warnings.
1027
static void free_resources(void)
1 by brian
clean slate
1028
{
1029
  if (md_result_file && md_result_file != stdout)
1030
    my_fclose(md_result_file, MYF(0));
1031
  my_free(opt_password, MYF(MY_ALLOW_ZERO_PTR));
1032
  if (hash_inited(&ignore_table))
1033
    hash_free(&ignore_table);
1034
  if (defaults_argv)
1035
    free_defaults(defaults_argv);
1036
  my_end(my_end_arg);
1037
}
1038
1039
1040
static void maybe_exit(int error)
1041
{
1042
  if (!first_error)
1043
    first_error= error;
1044
  if (ignore_errors)
1045
    return;
206.3.1 by Patrick Galbraith
Most everything working with client rename
1046
  if (drizzle)
1047
    drizzle_close(drizzle);
1 by brian
clean slate
1048
  free_resources();
1049
  exit(error);
1050
}
1051
1052
1053
/*
1054
  db_connect -- connects to the host and selects DB.
1055
*/
1056
1057
static int connect_to_db(char *host, char *user,char *passwd)
1058
{
1059
  char buff[20+FN_REFLEN];
142.1.2 by Patrick
All DBUG_x removed from client/
1060
1 by brian
clean slate
1061
1062
  verbose_msg("-- Connecting to %s...\n", host ? host : "localhost");
202.2.4 by Monty Taylor
Merged from Patrick.
1063
  drizzle_create(&drizzle_connection);
1 by brian
clean slate
1064
  if (opt_compress)
206.3.1 by Patrick Galbraith
Most everything working with client rename
1065
    drizzle_options(&drizzle_connection,DRIZZLE_OPT_COMPRESS,NullS);
1 by brian
clean slate
1066
  if (opt_protocol)
206.3.1 by Patrick Galbraith
Most everything working with client rename
1067
    drizzle_options(&drizzle_connection,DRIZZLE_OPT_PROTOCOL,(char*)&opt_protocol);
1068
  if (!(drizzle= drizzle_connect(&drizzle_connection,host,user,passwd,
1069
                                  NULL,opt_drizzle_port, NULL,
1 by brian
clean slate
1070
                                  0)))
1071
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
1072
    DB_error(&drizzle_connection, "when trying to connect");
142.1.2 by Patrick
All DBUG_x removed from client/
1073
    return(1);
1 by brian
clean slate
1074
  }
206.3.1 by Patrick Galbraith
Most everything working with client rename
1075
  if (drizzle_get_server_version(&drizzle_connection) < 40100)
1 by brian
clean slate
1076
  {
1077
    /* Don't dump SET NAMES with a pre-4.1 server (bug#7997).  */
1078
    opt_set_charset= 0;
1079
1080
    /* Don't switch charsets for 4.1 and earlier.  (bug#34192). */
163 by Brian Aker
Merge Monty's code.
1081
    server_supports_switching_charsets= false;
1 by brian
clean slate
1082
  } 
1083
  /*
1084
    set time_zone to UTC to allow dumping date types between servers with
1085
    different time zone settings
1086
  */
1087
  if (opt_tz_utc)
1088
  {
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
1089
    snprintf(buff, sizeof(buff), "/*!40103 SET TIME_ZONE='+00:00' */");
206.3.1 by Patrick Galbraith
Most everything working with client rename
1090
    if (drizzle_query_with_error_report(drizzle, 0, buff))
142.1.2 by Patrick
All DBUG_x removed from client/
1091
      return(1);
1 by brian
clean slate
1092
  }
142.1.2 by Patrick
All DBUG_x removed from client/
1093
  return(0);
1 by brian
clean slate
1094
} /* connect_to_db */
1095
1096
1097
/*
1098
** dbDisconnect -- disconnects from the host.
1099
*/
1100
static void dbDisconnect(char *host)
1101
{
1102
  verbose_msg("-- Disconnecting from %s...\n", host ? host : "localhost");
206.3.1 by Patrick Galbraith
Most everything working with client rename
1103
  drizzle_close(drizzle);
1 by brian
clean slate
1104
} /* dbDisconnect */
1105
1106
1107
static void unescape(FILE *file,char *pos,uint length)
1108
{
1109
  char *tmp;
142.1.2 by Patrick
All DBUG_x removed from client/
1110
1 by brian
clean slate
1111
  if (!(tmp=(char*) my_malloc(length*2+1, MYF(MY_WME))))
206.3.1 by Patrick Galbraith
Most everything working with client rename
1112
    die(EX_DRIZZLEERR, "Couldn't allocate memory");
1 by brian
clean slate
1113
383.1.38 by Monty Taylor
Reworked drizzle_escape_string.
1114
  drizzle_escape_string(tmp, pos, length);
1 by brian
clean slate
1115
  fputc('\'', file);
1116
  fputs(tmp, file);
1117
  fputc('\'', file);
1118
  check_io(file);
1119
  my_free(tmp, MYF(MY_WME));
142.1.2 by Patrick
All DBUG_x removed from client/
1120
  return;
1 by brian
clean slate
1121
} /* unescape */
1122
1123
143 by Brian Aker
Bool cleanup.
1124
static bool test_if_special_chars(const char *str)
1 by brian
clean slate
1125
{
1126
  for ( ; *str ; str++)
1127
    if (!my_isvar(charset_info,*str) && *str != '$')
1128
      return 1;
1129
  return 0;
1130
} /* test_if_special_chars */
1131
1132
1133
1134
/*
1135
  quote_name(name, buff, force)
1136
1137
  Quotes char string, taking into account compatible mode
1138
1139
  Args
1140
1141
  name                 Unquoted string containing that which will be quoted
1142
  buff                 The buffer that contains the quoted value, also returned
1143
  force                Flag to make it ignore 'test_if_special_chars'
1144
1145
  Returns
1146
1147
  buff                 quoted string
1148
1149
*/
143 by Brian Aker
Bool cleanup.
1150
static char *quote_name(const char *name, char *buff, bool force)
1 by brian
clean slate
1151
{
1152
  char *to= buff;
1153
  char qtype= (opt_compatible_mode & MASK_ANSI_QUOTES) ? '\"' : '`';
1154
1155
  if (!force && !opt_quoted && !test_if_special_chars(name))
1156
    return (char*) name;
1157
  *to++= qtype;
1158
  while (*name)
1159
  {
1160
    if (*name == qtype)
1161
      *to++= qtype;
1162
    *to++= *name++;
1163
  }
1164
  to[0]= qtype;
1165
  to[1]= 0;
1166
  return buff;
1167
} /* quote_name */
1168
1169
1170
/*
1171
  Quote a table name so it can be used in "SHOW TABLES LIKE <tabname>"
1172
1173
  SYNOPSIS
1174
    quote_for_like()
1175
    name     name of the table
1176
    buff     quoted name of the table
1177
1178
  DESCRIPTION
1179
    Quote \, _, ' and % characters
1180
206.3.1 by Patrick Galbraith
Most everything working with client rename
1181
    Note: Because DRIZZLE uses the C escape syntax in strings
1 by brian
clean slate
1182
    (for example, '\n' to represent newline), you must double
1183
    any '\' that you use in your LIKE  strings. For example, to
1184
    search for '\n', specify it as '\\n'. To search for '\', specify
1185
    it as '\\\\' (the backslashes are stripped once by the parser
1186
    and another time when the pattern match is done, leaving a
1187
    single backslash to be matched).
1188
1189
    Example: "t\1" => "t\\\\1"
1190
1191
*/
1192
static char *quote_for_like(const char *name, char *buff)
1193
{
1194
  char *to= buff;
1195
  *to++= '\'';
1196
  while (*name)
1197
  {
1198
    if (*name == '\\')
1199
    {
1200
      *to++='\\';
1201
      *to++='\\';
1202
      *to++='\\';
1203
    }
1204
    else if (*name == '\'' || *name == '_'  || *name == '%')
1205
      *to++= '\\';
1206
    *to++= *name++;
1207
  }
1208
  to[0]= '\'';
1209
  to[1]= 0;
1210
  return buff;
1211
}
1212
1213
1214
/*
1215
  Quote and print a string.
1216
1217
  SYNOPSIS
1218
    print_quoted_xml()
1219
    xml_file    - output file
1220
    str         - string to print
1221
    len         - its length
1222
1223
  DESCRIPTION
1224
    Quote '<' '>' '&' '\"' chars and print a string to the xml_file.
1225
*/
1226
288 by Brian Aker
ulong cleanp in client apps
1227
static void print_quoted_xml(FILE *xml_file, const char *str, uint32_t len)
1 by brian
clean slate
1228
{
1229
  const char *end;
1230
1231
  for (end= str + len; str != end; str++)
1232
  {
1233
    switch (*str) {
1234
    case '<':
1235
      fputs("&lt;", xml_file);
1236
      break;
1237
    case '>':
1238
      fputs("&gt;", xml_file);
1239
      break;
1240
    case '&':
1241
      fputs("&amp;", xml_file);
1242
      break;
1243
    case '\"':
1244
      fputs("&quot;", xml_file);
1245
      break;
1246
    default:
1247
      fputc(*str, xml_file);
1248
      break;
1249
    }
1250
  }
1251
  check_io(xml_file);
1252
}
1253
1254
1255
/*
1256
  Print xml tag. Optionally add attribute(s).
1257
1258
  SYNOPSIS
1259
    print_xml_tag(xml_file, sbeg, send, tag_name, first_attribute_name, 
1260
                    ..., attribute_name_n, attribute_value_n, NullS)
1261
    xml_file              - output file
1262
    sbeg                  - line beginning
1263
    line_end              - line ending
1264
    tag_name              - XML tag name.
1265
    first_attribute_name  - tag and first attribute
1266
    first_attribute_value - (Implied) value of first attribute
1267
    attribute_name_n      - attribute n
1268
    attribute_value_n     - value of attribute n
1269
1270
  DESCRIPTION
1271
    Print XML tag with any number of attribute="value" pairs to the xml_file.
1272
1273
    Format is:
1274
      sbeg<tag_name first_attribute_name="first_attribute_value" ... 
1275
      attribute_name_n="attribute_value_n">send
1276
  NOTE
1277
    Additional arguments must be present in attribute/value pairs.
1278
    The last argument should be the null character pointer.
1279
    All attribute_value arguments MUST be NULL terminated strings.
1280
    All attribute_value arguments will be quoted before output.
1281
*/
1282
1283
static void print_xml_tag(FILE * xml_file, const char* sbeg,
1284
                          const char* line_end, 
1285
                          const char* tag_name, 
1286
                          const char* first_attribute_name, ...)
1287
{
1288
  va_list arg_list;
1289
  const char *attribute_name, *attribute_value;
1290
1291
  fputs(sbeg, xml_file);
1292
  fputc('<', xml_file);
1293
  fputs(tag_name, xml_file);  
1294
1295
  va_start(arg_list, first_attribute_name);
1296
  attribute_name= first_attribute_name;
1297
  while (attribute_name != NullS)
1298
  {
1299
    attribute_value= va_arg(arg_list, char *);
142.1.2 by Patrick
All DBUG_x removed from client/
1300
    assert(attribute_value != NullS);
1 by brian
clean slate
1301
1302
    fputc(' ', xml_file);
1303
    fputs(attribute_name, xml_file);    
1304
    fputc('\"', xml_file);
1305
    
1306
    print_quoted_xml(xml_file, attribute_value, strlen(attribute_value));
1307
    fputc('\"', xml_file);
1308
1309
    attribute_name= va_arg(arg_list, char *);
1310
  }
1311
  va_end(arg_list);
1312
1313
  fputc('>', xml_file);
1314
  fputs(line_end, xml_file);
1315
  check_io(xml_file);
1316
}
1317
1318
1319
/*
1320
  Print xml tag with for a field that is null
1321
1322
  SYNOPSIS
1323
    print_xml_null_tag()
1324
    xml_file    - output file
1325
    sbeg        - line beginning
1326
    stag_atr    - tag and attribute
1327
    sval        - value of attribute
1328
    line_end        - line ending
1329
1330
  DESCRIPTION
1331
    Print tag with one attribute to the xml_file. Format is:
1332
      <stag_atr="sval" xsi:nil="true"/>
1333
  NOTE
1334
    sval MUST be a NULL terminated string.
1335
    sval string will be qouted before output.
1336
*/
1337
1338
static void print_xml_null_tag(FILE * xml_file, const char* sbeg,
1339
                               const char* stag_atr, const char* sval,
1340
                               const char* line_end)
1341
{
1342
  fputs(sbeg, xml_file);
1343
  fputs("<", xml_file);
1344
  fputs(stag_atr, xml_file);
1345
  fputs("\"", xml_file);
1346
  print_quoted_xml(xml_file, sval, strlen(sval));
1347
  fputs("\" xsi:nil=\"true\" />", xml_file);
1348
  fputs(line_end, xml_file);
1349
  check_io(xml_file);
1350
}
1351
1352
1353
/*
1354
  Print xml tag with many attributes.
1355
1356
  SYNOPSIS
1357
    print_xml_row()
1358
    xml_file    - output file
1359
    row_name    - xml tag name
1360
    tableRes    - query result
1361
    row         - result row
1362
1363
  DESCRIPTION
1364
    Print tag with many attribute to the xml_file. Format is:
1365
      \t\t<row_name Atr1="Val1" Atr2="Val2"... />
1366
  NOTE
1367
    All atributes and values will be quoted before output.
1368
*/
1369
1370
static void print_xml_row(FILE *xml_file, const char *row_name,
206.3.1 by Patrick Galbraith
Most everything working with client rename
1371
                          DRIZZLE_RES *tableRes, DRIZZLE_ROW *row)
1 by brian
clean slate
1372
{
1373
  uint i;
206.3.1 by Patrick Galbraith
Most everything working with client rename
1374
  DRIZZLE_FIELD *field;
1375
  uint32_t *lengths= drizzle_fetch_lengths(tableRes);
1 by brian
clean slate
1376
1377
  fprintf(xml_file, "\t\t<%s", row_name);
1378
  check_io(xml_file);
206.3.1 by Patrick Galbraith
Most everything working with client rename
1379
  drizzle_field_seek(tableRes, 0);
1380
  for (i= 0; (field= drizzle_fetch_field(tableRes)); i++)
1 by brian
clean slate
1381
  {
1382
    if ((*row)[i])
1383
    {
1384
      fputc(' ', xml_file);
1385
      print_quoted_xml(xml_file, field->name, field->name_length);
1386
      fputs("=\"", xml_file);
1387
      print_quoted_xml(xml_file, (*row)[i], lengths[i]);
1388
      fputc('"', xml_file);
1389
      check_io(xml_file);
1390
    }
1391
  }
1392
  fputs(" />\n", xml_file);
1393
  check_io(xml_file);
1394
}
1395
1396
1397
/*
1398
  Print hex value for blob data.
1399
1400
  SYNOPSIS
1401
    print_blob_as_hex()
1402
    output_file         - output file
1403
    str                 - string to print
1404
    len                 - its length
1405
1406
  DESCRIPTION
1407
    Print hex value for blob data.
1408
*/
1409
288 by Brian Aker
ulong cleanp in client apps
1410
static void print_blob_as_hex(FILE *output_file, const char *str, uint32_t len)
1 by brian
clean slate
1411
{
1412
    /* sakaik got the idea to to provide blob's in hex notation. */
1413
    const char *ptr= str, *end= ptr + len;
1414
    for (; ptr < end ; ptr++)
1415
      fprintf(output_file, "%02X", *((uchar *)ptr));
1416
    check_io(output_file);
1417
}
1418
1419
/*
1420
  get_table_structure -- retrievs database structure, prints out corresponding
1421
  CREATE statement and fills out insert_pat if the table is the type we will
1422
  be dumping.
1423
1424
  ARGS
1425
    table       - table name
1426
    db          - db name
1427
    table_type  - table type, e.g. "MyISAM" or "InnoDB", but also "VIEW"
1428
    ignore_flag - what we must particularly ignore - see IGNORE_ defines above
1429
1430
  RETURN
1431
    number of fields in table, 0 if error
1432
*/
1433
1434
static uint get_table_structure(char *table, char *db, char *table_type,
1435
                                char *ignore_flag)
1436
{
143 by Brian Aker
Bool cleanup.
1437
  bool    init=0, delayed, write_data, complete_insert;
157 by Brian Aker
Second pass cleanup on removal of my_uint types
1438
  uint64_t num_fields;
1 by brian
clean slate
1439
  char       *result_table, *opt_quoted_table;
1440
  const char *insert_option;
1441
  char	     name_buff[NAME_LEN+3],table_buff[NAME_LEN*2+3];
1442
  char       table_buff2[NAME_LEN*2+3], query_buff[QUERY_LENGTH];
1443
  FILE       *sql_file= md_result_file;
1444
  int        len;
206.3.1 by Patrick Galbraith
Most everything working with client rename
1445
  DRIZZLE_RES  *result;
1446
  DRIZZLE_ROW  row;
1 by brian
clean slate
1447
1448
  *ignore_flag= check_if_ignore_table(table, table_type);
1449
1450
  delayed= opt_delayed;
1451
  if (delayed && (*ignore_flag & IGNORE_INSERT_DELAYED))
1452
  {
1453
    delayed= 0;
1454
    verbose_msg("-- Warning: Unable to use delayed inserts for table '%s' "
1455
                "because it's of type %s\n", table, table_type);
1456
  }
1457
1458
  complete_insert= 0;
1459
  if ((write_data= !(*ignore_flag & IGNORE_DATA)))
1460
  {
1461
    complete_insert= opt_complete_insert;
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1462
    insert_pat= "";
1 by brian
clean slate
1463
  }
1464
1465
  insert_option= ((delayed && opt_ignore) ? " DELAYED IGNORE " :
1466
                  delayed ? " DELAYED " : opt_ignore ? " IGNORE " : "");
1467
1468
  verbose_msg("-- Retrieving table structure for table %s...\n", table);
1469
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
1470
  len= snprintf(query_buff, sizeof(query_buff),
1471
                "SET OPTION SQL_QUOTE_SHOW_CREATE=%d",
1472
                (opt_quoted || opt_keywords));
1 by brian
clean slate
1473
1474
  result_table=     quote_name(table, table_buff, 1);
1475
  opt_quoted_table= quote_name(table, table_buff2, 0);
1476
1477
  if (opt_order_by_primary)
1478
  {
1479
    my_free(order_by, MYF(MY_ALLOW_ZERO_PTR));
1480
    order_by= primary_key_fields(result_table);
1481
  }
1482
206.3.1 by Patrick Galbraith
Most everything working with client rename
1483
  if (!opt_xml && !drizzle_query_with_error_report(drizzle, 0, query_buff))
1 by brian
clean slate
1484
  {
1485
    /* using SHOW CREATE statement */
1486
    if (!opt_no_create_info)
1487
    {
1488
      /* Make an sql-file, if path was given iow. option -T was given */
1489
      char buff[20+FN_REFLEN];
236.3.5 by Andrey Hristov
Constify libdrizzle functions
1490
      const DRIZZLE_FIELD *field;
1 by brian
clean slate
1491
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
1492
      snprintf(buff, sizeof(buff), "show create table %s", result_table);
1 by brian
clean slate
1493
206.3.1 by Patrick Galbraith
Most everything working with client rename
1494
      if (switch_character_set_results(drizzle, "binary") ||
1495
          drizzle_query_with_error_report(drizzle, &result, buff) ||
1496
          switch_character_set_results(drizzle, default_charset))
142.1.2 by Patrick
All DBUG_x removed from client/
1497
        return(0);
1 by brian
clean slate
1498
1499
      if (path)
1500
      {
1501
        if (!(sql_file= open_sql_file_for_table(table)))
142.1.2 by Patrick
All DBUG_x removed from client/
1502
          return(0);
1 by brian
clean slate
1503
1504
        write_header(sql_file, db);
1505
      }
1506
      if (!opt_xml && opt_comments)
1507
      {
1508
      if (strcmp (table_type, "VIEW") == 0)         /* view */
1509
        fprintf(sql_file, "\n--\n-- Temporary table structure for view %s\n--\n\n",
1510
                result_table);
1511
      else
1512
        fprintf(sql_file, "\n--\n-- Table structure for table %s\n--\n\n",
1513
                result_table);
1514
        check_io(sql_file);
1515
      }
1516
      if (opt_drop)
1517
      {
1518
      /*
1519
        Even if the "table" is a view, we do a DROP TABLE here.  The
1520
        view-specific code below fills in the DROP VIEW.
1521
       */
1522
        fprintf(sql_file, "DROP TABLE IF EXISTS %s;\n",
1523
                opt_quoted_table);
1524
        check_io(sql_file);
1525
      }
1526
206.3.1 by Patrick Galbraith
Most everything working with client rename
1527
      field= drizzle_fetch_field_direct(result, 0);
1 by brian
clean slate
1528
      if (strcmp(field->name, "View") == 0)
1529
      {
1530
        char *scv_buff= NULL;
1531
1532
        verbose_msg("-- It's a view, create dummy table for view\n");
1533
1534
        /* save "show create" statement for later */
206.3.1 by Patrick Galbraith
Most everything working with client rename
1535
        if ((row= drizzle_fetch_row(result)) && (scv_buff=row[1]))
1 by brian
clean slate
1536
          scv_buff= my_strdup(scv_buff, MYF(0));
1537
206.3.1 by Patrick Galbraith
Most everything working with client rename
1538
        drizzle_free_result(result);
1 by brian
clean slate
1539
1540
        /*
1541
          Create a table with the same name as the view and with columns of
1542
          the same name in order to satisfy views that depend on this view.
1543
          The table will be removed when the actual view is created.
1544
1545
          The properties of each column, aside from the data type, are not
1546
          preserved in this temporary table, because they are not necessary.
1547
1548
          This will not be necessary once we can determine dependencies
1549
          between views and can simply dump them in the appropriate order.
1550
        */
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
1551
        snprintf(query_buff, sizeof(query_buff),
1552
                 "SHOW FIELDS FROM %s", result_table);
206.3.1 by Patrick Galbraith
Most everything working with client rename
1553
        if (switch_character_set_results(drizzle, "binary") ||
1554
            drizzle_query_with_error_report(drizzle, &result, query_buff) ||
1555
            switch_character_set_results(drizzle, default_charset))
1 by brian
clean slate
1556
        {
1557
          /*
1558
            View references invalid or privileged table/col/fun (err 1356),
1559
            so we cannot create a stand-in table.  Be defensive and dump
1560
            a comment with the view's 'show create' statement. (Bug #17371)
1561
          */
1562
206.3.1 by Patrick Galbraith
Most everything working with client rename
1563
          if (drizzle_errno(drizzle) == ER_VIEW_INVALID)
1 by brian
clean slate
1564
            fprintf(sql_file, "\n-- failed on view %s: %s\n\n", result_table, scv_buff ? scv_buff : "");
1565
1566
          my_free(scv_buff, MYF(MY_ALLOW_ZERO_PTR));
1567
142.1.2 by Patrick
All DBUG_x removed from client/
1568
          return(0);
1 by brian
clean slate
1569
        }
1570
        else
1571
          my_free(scv_buff, MYF(MY_ALLOW_ZERO_PTR));
1572
206.3.1 by Patrick Galbraith
Most everything working with client rename
1573
        if (drizzle_num_rows(result))
1 by brian
clean slate
1574
        {
1575
          if (opt_drop)
1576
          {
1577
            /*
1578
              We have already dropped any table of the same name above, so
1579
              here we just drop the view.
1580
            */
1581
1582
            fprintf(sql_file, "/*!50001 DROP VIEW IF EXISTS %s*/;\n",
1583
                    opt_quoted_table);
1584
            check_io(sql_file);
1585
          }
1586
1587
          fprintf(sql_file,
1588
                  "/*!50001 CREATE TABLE %s (\n",
1589
                  result_table);
1590
1591
          /*
1592
            Get first row, following loop will prepend comma - keeps from
1593
            having to know if the row being printed is last to determine if
1594
            there should be a _trailing_ comma.
1595
          */
1596
206.3.1 by Patrick Galbraith
Most everything working with client rename
1597
          row= drizzle_fetch_row(result);
1 by brian
clean slate
1598
1599
          fprintf(sql_file, "  %s %s", quote_name(row[0], name_buff, 0),
1600
                  row[1]);
1601
206.3.1 by Patrick Galbraith
Most everything working with client rename
1602
          while((row= drizzle_fetch_row(result)))
1 by brian
clean slate
1603
          {
1604
            /* col name, col type */
1605
            fprintf(sql_file, ",\n  %s %s",
1606
                    quote_name(row[0], name_buff, 0), row[1]);
1607
          }
377.1.4 by Brian Aker
Big, fat, UTF-8 patch. This fixes some of the oddities around only one
1608
          fprintf(sql_file, "\n) */;\n"); 
1 by brian
clean slate
1609
          check_io(sql_file);
1610
        }
1611
206.3.1 by Patrick Galbraith
Most everything working with client rename
1612
        drizzle_free_result(result);
1 by brian
clean slate
1613
1614
        if (path)
1615
          my_fclose(sql_file, MYF(MY_WME));
1616
1617
        seen_views= 1;
142.1.2 by Patrick
All DBUG_x removed from client/
1618
        return(0);
1 by brian
clean slate
1619
      }
1620
206.3.1 by Patrick Galbraith
Most everything working with client rename
1621
      row= drizzle_fetch_row(result);
1 by brian
clean slate
1622
377.1.4 by Brian Aker
Big, fat, UTF-8 patch. This fixes some of the oddities around only one
1623
      fprintf(sql_file, "%s;\n", row[1]);
1 by brian
clean slate
1624
1625
      check_io(sql_file);
206.3.1 by Patrick Galbraith
Most everything working with client rename
1626
      drizzle_free_result(result);
1 by brian
clean slate
1627
    }
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
1628
    snprintf(query_buff, sizeof(query_buff), "show fields from %s",
1629
             result_table);
206.3.1 by Patrick Galbraith
Most everything working with client rename
1630
    if (drizzle_query_with_error_report(drizzle, &result, query_buff))
1 by brian
clean slate
1631
    {
1632
      if (path)
1633
        my_fclose(sql_file, MYF(MY_WME));
142.1.2 by Patrick
All DBUG_x removed from client/
1634
      return(0);
1 by brian
clean slate
1635
    }
1636
1637
    /*
1638
      If write_data is true, then we build up insert statements for
1639
      the table's data. Note: in subsequent lines of code, this test
1640
      will have to be performed each time we are appending to
1641
      insert_pat.
1642
    */
1643
    if (write_data)
1644
    {
1645
      if (opt_replace_into)
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1646
        insert_pat.append("REPLACE ");
1 by brian
clean slate
1647
      else
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1648
        insert_pat.append("INSERT ");
1649
      insert_pat.append(insert_option);
1650
      insert_pat.append("INTO ");
1651
      insert_pat.append(opt_quoted_table);
1 by brian
clean slate
1652
      if (complete_insert)
1653
      {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1654
        insert_pat.append(" (");
1 by brian
clean slate
1655
      }
1656
      else
1657
      {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1658
        insert_pat.append(" VALUES ");
1 by brian
clean slate
1659
        if (!extended_insert)
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1660
          insert_pat.append("(");
1 by brian
clean slate
1661
      }
1662
    }
1663
206.3.1 by Patrick Galbraith
Most everything working with client rename
1664
    while ((row= drizzle_fetch_row(result)))
1 by brian
clean slate
1665
    {
1666
      if (complete_insert)
1667
      {
1668
        if (init)
1669
        {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1670
          insert_pat.append(", ");
1 by brian
clean slate
1671
        }
1672
        init=1;
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1673
        insert_pat.append(quote_name(row[SHOW_FIELDNAME], name_buff, 0));
1 by brian
clean slate
1674
      }
1675
    }
206.3.1 by Patrick Galbraith
Most everything working with client rename
1676
    num_fields= drizzle_num_rows(result);
1677
    drizzle_free_result(result);
1 by brian
clean slate
1678
  }
1679
  else
1680
  {
1681
    verbose_msg("%s: Warning: Can't set SQL_QUOTE_SHOW_CREATE option (%s)\n",
206.3.1 by Patrick Galbraith
Most everything working with client rename
1682
                my_progname, drizzle_error(drizzle));
1 by brian
clean slate
1683
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
1684
    snprintf(query_buff, sizeof(query_buff), "show fields from %s",
1685
             result_table);
206.3.1 by Patrick Galbraith
Most everything working with client rename
1686
    if (drizzle_query_with_error_report(drizzle, &result, query_buff))
142.1.2 by Patrick
All DBUG_x removed from client/
1687
      return(0);
1 by brian
clean slate
1688
1689
    /* Make an sql-file, if path was given iow. option -T was given */
1690
    if (!opt_no_create_info)
1691
    {
1692
      if (path)
1693
      {
1694
        if (!(sql_file= open_sql_file_for_table(table)))
142.1.2 by Patrick
All DBUG_x removed from client/
1695
          return(0);
1 by brian
clean slate
1696
        write_header(sql_file, db);
1697
      }
1698
      if (!opt_xml && opt_comments)
1699
        fprintf(sql_file, "\n--\n-- Table structure for table %s\n--\n\n",
1700
                result_table);
1701
      if (opt_drop)
1702
        fprintf(sql_file, "DROP TABLE IF EXISTS %s;\n", result_table);
1703
      if (!opt_xml)
1704
        fprintf(sql_file, "CREATE TABLE %s (\n", result_table);
1705
      else
1706
        print_xml_tag(sql_file, "\t", "\n", "table_structure", "name=", table, 
1707
                NullS);
1708
      check_io(sql_file);
1709
    }
1710
1711
    if (write_data)
1712
    {
1713
      if (opt_replace_into)
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1714
        insert_pat.append("REPLACE ");
1 by brian
clean slate
1715
      else
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1716
        insert_pat.append("INSERT ");
1717
      insert_pat.append(insert_option);
1718
      insert_pat.append("INTO ");
1719
      insert_pat.append(result_table);
1 by brian
clean slate
1720
      if (complete_insert)
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1721
        insert_pat.append(" (");
1 by brian
clean slate
1722
      else
1723
      {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1724
        insert_pat.append(" VALUES ");
1 by brian
clean slate
1725
        if (!extended_insert)
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1726
          insert_pat.append("(");
1 by brian
clean slate
1727
      }
1728
    }
1729
206.3.1 by Patrick Galbraith
Most everything working with client rename
1730
    while ((row= drizzle_fetch_row(result)))
1 by brian
clean slate
1731
    {
206.3.1 by Patrick Galbraith
Most everything working with client rename
1732
      uint32_t *lengths= drizzle_fetch_lengths(result);
1 by brian
clean slate
1733
      if (init)
1734
      {
1735
        if (!opt_xml && !opt_no_create_info)
1736
        {
1737
          fputs(",\n",sql_file);
1738
          check_io(sql_file);
1739
        }
1740
        if (complete_insert)
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1741
          insert_pat.append(", ");
1 by brian
clean slate
1742
      }
1743
      init=1;
1744
      if (complete_insert)
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1745
        insert_pat.append(quote_name(row[SHOW_FIELDNAME], name_buff, 0));
1 by brian
clean slate
1746
      if (!opt_no_create_info)
1747
      {
1748
        if (opt_xml)
1749
        {
1750
          print_xml_row(sql_file, "field", result, &row);
1751
          continue;
1752
        }
1753
1754
        if (opt_keywords)
1755
          fprintf(sql_file, "  %s.%s %s", result_table,
1756
                  quote_name(row[SHOW_FIELDNAME],name_buff, 0),
1757
                  row[SHOW_TYPE]);
1758
        else
1759
          fprintf(sql_file, "  %s %s", quote_name(row[SHOW_FIELDNAME],
1760
                                                  name_buff, 0),
1761
                  row[SHOW_TYPE]);
1762
        if (row[SHOW_DEFAULT])
1763
        {
1764
          fputs(" DEFAULT ", sql_file);
1765
          unescape(sql_file, row[SHOW_DEFAULT], lengths[SHOW_DEFAULT]);
1766
        }
1767
        if (!row[SHOW_NULL][0])
1768
          fputs(" NOT NULL", sql_file);
1769
        if (row[SHOW_EXTRA][0])
1770
          fprintf(sql_file, " %s",row[SHOW_EXTRA]);
1771
        check_io(sql_file);
1772
      }
1773
    }
206.3.1 by Patrick Galbraith
Most everything working with client rename
1774
    num_fields= drizzle_num_rows(result);
1775
    drizzle_free_result(result);
1 by brian
clean slate
1776
    if (!opt_no_create_info)
1777
    {
1778
      /* Make an sql-file, if path was given iow. option -T was given */
1779
      char buff[20+FN_REFLEN];
1780
      uint keynr,primary_key;
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
1781
      snprintf(buff, sizeof(buff), "show keys from %s", result_table);
206.3.1 by Patrick Galbraith
Most everything working with client rename
1782
      if (drizzle_query_with_error_report(drizzle, &result, buff))
1 by brian
clean slate
1783
      {
206.3.1 by Patrick Galbraith
Most everything working with client rename
1784
        if (drizzle_errno(drizzle) == ER_WRONG_OBJECT)
1 by brian
clean slate
1785
        {
1786
          /* it is VIEW */
1787
          fputs("\t\t<options Comment=\"view\" />\n", sql_file);
1788
          goto continue_xml;
1789
        }
1790
        fprintf(stderr, "%s: Can't get keys for table %s (%s)\n",
206.3.1 by Patrick Galbraith
Most everything working with client rename
1791
                my_progname, result_table, drizzle_error(drizzle));
1 by brian
clean slate
1792
        if (path)
1793
          my_fclose(sql_file, MYF(MY_WME));
142.1.2 by Patrick
All DBUG_x removed from client/
1794
        return(0);
1 by brian
clean slate
1795
      }
1796
1797
      /* Find first which key is primary key */
1798
      keynr=0;
1799
      primary_key=INT_MAX;
206.3.1 by Patrick Galbraith
Most everything working with client rename
1800
      while ((row= drizzle_fetch_row(result)))
1 by brian
clean slate
1801
      {
1802
        if (atoi(row[3]) == 1)
1803
        {
1804
          keynr++;
1805
#ifdef FORCE_PRIMARY_KEY
1806
          if (atoi(row[1]) == 0 && primary_key == INT_MAX)
1807
            primary_key=keynr;
1808
#endif
1809
          if (!strcmp(row[2],"PRIMARY"))
1810
          {
1811
            primary_key=keynr;
1812
            break;
1813
          }
1814
        }
1815
      }
206.3.1 by Patrick Galbraith
Most everything working with client rename
1816
      drizzle_data_seek(result,0);
1 by brian
clean slate
1817
      keynr=0;
206.3.1 by Patrick Galbraith
Most everything working with client rename
1818
      while ((row= drizzle_fetch_row(result)))
1 by brian
clean slate
1819
      {
1820
        if (opt_xml)
1821
        {
1822
          print_xml_row(sql_file, "key", result, &row);
1823
          continue;
1824
        }
1825
1826
        if (atoi(row[3]) == 1)
1827
        {
1828
          if (keynr++)
1829
            putc(')', sql_file);
1830
          if (atoi(row[1]))       /* Test if duplicate key */
1831
            /* Duplicate allowed */
1832
            fprintf(sql_file, ",\n  KEY %s (",quote_name(row[2],name_buff,0));
1833
          else if (keynr == primary_key)
1834
            fputs(",\n  PRIMARY KEY (",sql_file); /* First UNIQUE is primary */
1835
          else
1836
            fprintf(sql_file, ",\n  UNIQUE %s (",quote_name(row[2],name_buff,
1837
                                                            0));
1838
        }
1839
        else
1840
          putc(',', sql_file);
1841
        fputs(quote_name(row[4], name_buff, 0), sql_file);
1842
        if (row[7])
1843
          fprintf(sql_file, " (%s)",row[7]);      /* Sub key */
1844
        check_io(sql_file);
1845
      }
206.3.1 by Patrick Galbraith
Most everything working with client rename
1846
      drizzle_free_result(result);
1 by brian
clean slate
1847
      if (!opt_xml)
1848
      {
1849
        if (keynr)
1850
          putc(')', sql_file);
1851
        fputs("\n)",sql_file);
1852
        check_io(sql_file);
1853
      }
1854
206.3.1 by Patrick Galbraith
Most everything working with client rename
1855
      /* Get DRIZZLE specific create options */
1 by brian
clean slate
1856
      if (create_options)
1857
      {
1858
        char show_name_buff[NAME_LEN*2+2+24];
1859
1860
        /* Check memory for quote_for_like() */
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
1861
        snprintf(buff, sizeof(buff), "show table status like %s",
1862
                 quote_for_like(table, show_name_buff));
1 by brian
clean slate
1863
206.3.1 by Patrick Galbraith
Most everything working with client rename
1864
        if (drizzle_query_with_error_report(drizzle, &result, buff))
1 by brian
clean slate
1865
        {
206.3.1 by Patrick Galbraith
Most everything working with client rename
1866
          if (drizzle_errno(drizzle) != ER_PARSE_ERROR)
1867
          {                                     /* If old DRIZZLE version */
1 by brian
clean slate
1868
            verbose_msg("-- Warning: Couldn't get status information for " \
206.3.1 by Patrick Galbraith
Most everything working with client rename
1869
                        "table %s (%s)\n", result_table,drizzle_error(drizzle));
1 by brian
clean slate
1870
          }
1871
        }
206.3.1 by Patrick Galbraith
Most everything working with client rename
1872
        else if (!(row= drizzle_fetch_row(result)))
1 by brian
clean slate
1873
        {
1874
          fprintf(stderr,
1875
                  "Error: Couldn't read status information for table %s (%s)\n",
206.3.1 by Patrick Galbraith
Most everything working with client rename
1876
                  result_table,drizzle_error(drizzle));
1 by brian
clean slate
1877
        }
1878
        else
1879
        {
1880
          if (opt_xml)
1881
            print_xml_row(sql_file, "options", result, &row);
1882
          else
1883
          {
1884
            fputs("/*!",sql_file);
1885
            print_value(sql_file,result,row,"engine=","Engine",0);
1886
            print_value(sql_file,result,row,"","Create_options",0);
1887
            print_value(sql_file,result,row,"comment=","Comment",1);
1888
            fputs(" */",sql_file);
1889
            check_io(sql_file);
1890
          }
1891
        }
206.3.1 by Patrick Galbraith
Most everything working with client rename
1892
        drizzle_free_result(result);              /* Is always safe to free */
1 by brian
clean slate
1893
      }
1894
continue_xml:
1895
      if (!opt_xml)
1896
        fputs(";\n", sql_file);
1897
      else
1898
        fputs("\t</table_structure>\n", sql_file);
1899
      check_io(sql_file);
1900
    }
1901
  }
1902
  if (complete_insert)
1903
  {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1904
    insert_pat.append(") VALUES ");
1 by brian
clean slate
1905
    if (!extended_insert)
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1906
      insert_pat.append("(");
1 by brian
clean slate
1907
  }
1908
  if (sql_file != md_result_file)
1909
  {
1910
    fputs("\n", sql_file);
1911
    write_footer(sql_file);
1912
    my_fclose(sql_file, MYF(MY_WME));
1913
  }
142.1.2 by Patrick
All DBUG_x removed from client/
1914
  return((uint) num_fields);
1 by brian
clean slate
1915
} /* get_table_structure */
1916
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1917
static void add_load_option(string &str, const char *option,
1918
                            const char *option_value)
1 by brian
clean slate
1919
{
1920
  if (!option_value)
1921
  {
1922
    /* Null value means we don't add this option. */
1923
    return;
1924
  }
1925
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1926
  str.append(option);
1 by brian
clean slate
1927
  
1928
  if (strncmp(option_value, "0x", sizeof("0x")-1) == 0)
1929
  {
1930
    /* It's a hex constant, don't escape */
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1931
    str.append(option_value);
1 by brian
clean slate
1932
  }
1933
  else
1934
  {
1935
    /* char constant; escape */
1936
    field_escape(str, option_value);
1937
  }
1938
}
1939
1940
1941
/*
1942
  Allow the user to specify field terminator strings like:
1943
  "'", "\", "\\" (escaped backslash), "\t" (tab), "\n" (newline)
1944
  This is done by doubling ' and add a end -\ if needed to avoid
1945
  syntax errors from the SQL parser.
1946
*/
1947
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1948
static void field_escape(string &in, const char *from)
1 by brian
clean slate
1949
{
1950
  uint end_backslashes= 0; 
1951
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1952
  in.append("'");
1 by brian
clean slate
1953
1954
  while (*from)
1955
  {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1956
    in.append(from, 1);
1 by brian
clean slate
1957
1958
    if (*from == '\\')
1959
      end_backslashes^=1;    /* find odd number of backslashes */
1960
    else
1961
    {
1962
      if (*from == '\'' && !end_backslashes)
1963
      {
206.3.1 by Patrick Galbraith
Most everything working with client rename
1964
        /* We want a duplicate of "'" for DRIZZLE */
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1965
        in.append("\'");
1 by brian
clean slate
1966
      }
1967
      end_backslashes=0;
1968
    }
1969
    from++;
1970
  }
1971
  /* Add missing backslashes if user has specified odd number of backs.*/
1972
  if (end_backslashes)
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
1973
    in.append("\\");
1974
1975
  in.append("'");
1 by brian
clean slate
1976
}
1977
1978
1979
1980
/*
1981
1982
 SYNOPSIS
1983
  dump_table()
1984
1985
  dump_table saves database contents as a series of INSERT statements.
1986
1987
  ARGS
1988
   table - table name
1989
   db    - db name
1990
1991
   RETURNS
1992
    void
1993
*/
1994
1995
1996
static void dump_table(char *table, char *db)
1997
{
1998
  char ignore_flag;
1999
  char buf[200], table_buff[NAME_LEN+3];
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2000
  string query_string;
1 by brian
clean slate
2001
  char table_type[NAME_LEN];
2002
  char *result_table, table_buff2[NAME_LEN*2+3], *opt_quoted_table;
2003
  int error= 0;
288 by Brian Aker
ulong cleanp in client apps
2004
  uint32_t         rownr, row_break, total_length, init_length;
1 by brian
clean slate
2005
  uint num_fields;
206.3.1 by Patrick Galbraith
Most everything working with client rename
2006
  DRIZZLE_RES     *res;
2007
  DRIZZLE_FIELD   *field;
2008
  DRIZZLE_ROW     row;
142.1.2 by Patrick
All DBUG_x removed from client/
2009
1 by brian
clean slate
2010
2011
  /*
2012
    Make sure you get the create table info before the following check for
2013
    --no-data flag below. Otherwise, the create table info won't be printed.
2014
  */
2015
  num_fields= get_table_structure(table, db, table_type, &ignore_flag);
2016
2017
  /*
2018
    The "table" could be a view.  If so, we don't do anything here.
2019
  */
2020
  if (strcmp(table_type, "VIEW") == 0)
142.1.2 by Patrick
All DBUG_x removed from client/
2021
    return;
1 by brian
clean slate
2022
2023
  /* Check --no-data flag */
2024
  if (opt_no_data)
2025
  {
2026
    verbose_msg("-- Skipping dump data for table '%s', --no-data was used\n",
2027
                table);
142.1.2 by Patrick
All DBUG_x removed from client/
2028
    return;
1 by brian
clean slate
2029
  }
2030
2031
  /*
2032
    If the table type is a merge table or any type that has to be
2033
     _completely_ ignored and no data dumped
2034
  */
2035
  if (ignore_flag & IGNORE_DATA)
2036
  {
2037
    verbose_msg("-- Warning: Skipping data for table '%s' because " \
2038
                "it's of type %s\n", table, table_type);
142.1.2 by Patrick
All DBUG_x removed from client/
2039
    return;
1 by brian
clean slate
2040
  }
2041
  /* Check that there are any fields in the table */
2042
  if (num_fields == 0)
2043
  {
2044
    verbose_msg("-- Skipping dump data for table '%s', it has no fields\n",
2045
                table);
142.1.2 by Patrick
All DBUG_x removed from client/
2046
    return;
1 by brian
clean slate
2047
  }
2048
2049
  /*
2050
     Check --skip-events flag: it is not enough to skip creation of events
2051
     discarding SHOW CREATE EVENT statements generation. The myslq.event
2052
     table data should be skipped too.
2053
  */
383.1.12 by Brian Aker
Much closer toward UTF8 being around all the time...
2054
  if (!opt_events && !my_strcasecmp(&my_charset_utf8_general_ci, db, "mysql") &&
2055
      !my_strcasecmp(&my_charset_utf8_general_ci, table, "event"))
1 by brian
clean slate
2056
  {
2057
    verbose_msg("-- Skipping data table mysql.event, --skip-events was used\n");
142.1.2 by Patrick
All DBUG_x removed from client/
2058
    return;
1 by brian
clean slate
2059
  }
2060
2061
  result_table= quote_name(table,table_buff, 1);
2062
  opt_quoted_table= quote_name(table, table_buff2, 0);
2063
2064
  verbose_msg("-- Sending SELECT query...\n");
2065
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2066
  query_string.clear();
2067
  query_string.reserve(1024);
1 by brian
clean slate
2068
2069
  if (path)
2070
  {
2071
    char filename[FN_REFLEN], tmp_path[FN_REFLEN];
2072
2073
    /*
2074
      Convert the path to native os format
2075
      and resolve to the full filepath.
2076
    */
2077
    convert_dirname(tmp_path,path,NullS);    
2078
    my_load_path(tmp_path, tmp_path, NULL);
2079
    fn_format(filename, table, tmp_path, ".txt", MYF(MY_UNPACK_FILENAME));
2080
2081
    /* Must delete the file that 'INTO OUTFILE' will write to */
2082
    my_delete(filename, MYF(0));
2083
2084
    /* convert to a unix path name to stick into the query */
2085
    to_unix_path(filename);
2086
2087
    /* now build the query string */
2088
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2089
    query_string.append( "SELECT * INTO OUTFILE '");
2090
    query_string.append( filename);
2091
    query_string.append( "'");
1 by brian
clean slate
2092
2093
    if (fields_terminated || enclosed || opt_enclosed || escaped)
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2094
      query_string.append( " FIELDS");
1 by brian
clean slate
2095
    
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2096
    add_load_option(query_string, " TERMINATED BY ", fields_terminated);
2097
    add_load_option(query_string, " ENCLOSED BY ", enclosed);
2098
    add_load_option(query_string, " OPTIONALLY ENCLOSED BY ", opt_enclosed);
2099
    add_load_option(query_string, " ESCAPED BY ", escaped);
2100
    add_load_option(query_string, " LINES TERMINATED BY ", lines_terminated);
1 by brian
clean slate
2101
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2102
    query_string.append( " FROM ");
2103
    query_string.append( result_table);
1 by brian
clean slate
2104
2105
    if (where)
2106
    {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2107
      query_string.append( " WHERE ");
2108
      query_string.append( where);
1 by brian
clean slate
2109
    }
2110
2111
    if (order_by)
2112
    {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2113
      query_string.append( " ORDER BY ");
2114
      query_string.append( order_by);
1 by brian
clean slate
2115
    }
2116
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2117
    if (drizzle_real_query(drizzle, query_string.c_str(), query_string.length()))
1 by brian
clean slate
2118
    {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2119
      DB_error(drizzle, "when executing 'SELECT INTO OUTFILE'");
142.1.2 by Patrick
All DBUG_x removed from client/
2120
      return;
1 by brian
clean slate
2121
    }
2122
  }
2123
  else
2124
  {
2125
    if (!opt_xml && opt_comments)
2126
    {
2127
      fprintf(md_result_file,"\n--\n-- Dumping data for table %s\n--\n",
2128
              result_table);
2129
      check_io(md_result_file);
2130
    }
2131
    
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2132
    query_string.append( "SELECT * FROM ");
2133
    query_string.append( result_table);
1 by brian
clean slate
2134
2135
    if (where)
2136
    {
2137
      if (!opt_xml && opt_comments)
2138
      {
2139
        fprintf(md_result_file, "-- WHERE:  %s\n", where);
2140
        check_io(md_result_file);
2141
      }
2142
      
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2143
      query_string.append( " WHERE ");
2144
      query_string.append( where);
1 by brian
clean slate
2145
    }
2146
    if (order_by)
2147
    {
2148
      if (!opt_xml && opt_comments)
2149
      {
2150
        fprintf(md_result_file, "-- ORDER BY:  %s\n", order_by);
2151
        check_io(md_result_file);
2152
      }
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2153
      query_string.append( " ORDER BY ");
2154
      query_string.append( order_by);
1 by brian
clean slate
2155
    }
2156
2157
    if (!opt_xml && !opt_compact)
2158
    {
2159
      fputs("\n", md_result_file);
2160
      check_io(md_result_file);
2161
    }
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2162
    if (drizzle_query_with_error_report(drizzle, 0, query_string.c_str()))
1 by brian
clean slate
2163
    {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2164
      DB_error(drizzle, "when retrieving data from server");
1 by brian
clean slate
2165
      goto err;
2166
    }
2167
    if (quick)
206.3.1 by Patrick Galbraith
Most everything working with client rename
2168
      res=drizzle_use_result(drizzle);
1 by brian
clean slate
2169
    else
206.3.1 by Patrick Galbraith
Most everything working with client rename
2170
      res=drizzle_store_result(drizzle);
1 by brian
clean slate
2171
    if (!res)
2172
    {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2173
      DB_error(drizzle, "when retrieving data from server");
1 by brian
clean slate
2174
      goto err;
2175
    }
2176
2177
    verbose_msg("-- Retrieving rows...\n");
206.3.1 by Patrick Galbraith
Most everything working with client rename
2178
    if (drizzle_num_fields(res) != num_fields)
1 by brian
clean slate
2179
    {
2180
      fprintf(stderr,"%s: Error in field count for table: %s !  Aborting.\n",
2181
              my_progname, result_table);
2182
      error= EX_CONSCHECK;
2183
      goto err;
2184
    }
2185
2186
    if (opt_lock)
2187
    {
2188
      fprintf(md_result_file,"LOCK TABLES %s WRITE;\n", opt_quoted_table);
2189
      check_io(md_result_file);
2190
    }
2191
    /* Moved disable keys to after lock per bug 15977 */
2192
    if (opt_disable_keys)
2193
    {
2194
      fprintf(md_result_file, "/*!40000 ALTER TABLE %s DISABLE KEYS */;\n",
2195
	      opt_quoted_table);
2196
      check_io(md_result_file);
2197
    }
2198
2199
    total_length= opt_net_buffer_length;                /* Force row break */
2200
    row_break=0;
2201
    rownr=0;
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2202
    init_length=(uint) insert_pat.length()+4;
1 by brian
clean slate
2203
    if (opt_xml)
2204
      print_xml_tag(md_result_file, "\t", "\n", "table_data", "name=", table,
2205
              NullS);
2206
    if (opt_autocommit)
2207
    {
2208
      fprintf(md_result_file, "set autocommit=0;\n");
2209
      check_io(md_result_file);
2210
    }
2211
206.3.1 by Patrick Galbraith
Most everything working with client rename
2212
    while ((row= drizzle_fetch_row(res)))
1 by brian
clean slate
2213
    {
2214
      uint i;
206.3.1 by Patrick Galbraith
Most everything working with client rename
2215
      uint32_t *lengths= drizzle_fetch_lengths(res);
1 by brian
clean slate
2216
      rownr++;
2217
      if (!extended_insert && !opt_xml)
2218
      {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2219
        fputs(insert_pat.c_str(),md_result_file);
1 by brian
clean slate
2220
        check_io(md_result_file);
2221
      }
206.3.1 by Patrick Galbraith
Most everything working with client rename
2222
      drizzle_field_seek(res,0);
1 by brian
clean slate
2223
2224
      if (opt_xml)
2225
      {
2226
        fputs("\t<row>\n", md_result_file);
2227
        check_io(md_result_file);
2228
      }
2229
206.3.1 by Patrick Galbraith
Most everything working with client rename
2230
      for (i= 0; i < drizzle_num_fields(res); i++)
1 by brian
clean slate
2231
      {
2232
        int is_blob;
288 by Brian Aker
ulong cleanp in client apps
2233
        uint32_t length= lengths[i];
1 by brian
clean slate
2234
206.3.1 by Patrick Galbraith
Most everything working with client rename
2235
        if (!(field= drizzle_fetch_field(res)))
1 by brian
clean slate
2236
          die(EX_CONSCHECK,
2237
                      "Not enough fields from table %s! Aborting.\n",
2238
                      result_table);
2239
2240
        /*
2241
           63 is my_charset_bin. If charsetnr is not 63,
2242
           we have not a BLOB but a TEXT column.
2243
           we'll dump in hex only BLOB columns.
2244
        */
2245
        is_blob= (opt_hex_blob && field->charsetnr == 63 &&
241 by Brian Aker
First pass of CHAR removal.
2246
                  (field->type == DRIZZLE_TYPE_VARCHAR ||
212.2.2 by Patrick Galbraith
Renamed FIELD_TYPE to DRIZZLE_TYPE
2247
                   field->type == DRIZZLE_TYPE_BLOB)) ? 1 : 0;
1 by brian
clean slate
2248
        if (extended_insert && !opt_xml)
2249
        {
2250
          if (i == 0)
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2251
            extended_row= "(";
1 by brian
clean slate
2252
          else
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2253
            extended_row.append(",");
1 by brian
clean slate
2254
2255
          if (row[i])
2256
          {
2257
            if (length)
2258
            {
2259
              if (!IS_NUM_FIELD(field))
2260
              {
2261
                /*
2262
                  "length * 2 + 2" is OK for both HEX and non-HEX modes:
2263
                  - In HEX mode we need exactly 2 bytes per character
2264
                  plus 2 bytes for '0x' prefix.
2265
                  - In non-HEX mode we need up to 2 bytes per character,
2266
                  plus 2 bytes for leading and trailing '\'' characters.
2267
                  Also we need to reserve 1 byte for terminating '\0'.
2268
                */
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2269
                char * tmp_str= (char *)malloc(length * 2 + 2 + 1);
2270
                memset(tmp_str, '\0', length * 2 + 2 + 1);
1 by brian
clean slate
2271
                if (opt_hex_blob && is_blob)
2272
                {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2273
                  extended_row.append("0x");
2274
                  drizzle_hex_string(tmp_str, row[i], length);
2275
                  extended_row.append(tmp_str);
1 by brian
clean slate
2276
                }
2277
                else
2278
                {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2279
                  extended_row.append("'");
383.1.38 by Monty Taylor
Reworked drizzle_escape_string.
2280
                  drizzle_escape_string(tmp_str,
2281
                                        row[i],length);
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2282
                  extended_row.append(tmp_str);
2283
                  extended_row.append("'");
1 by brian
clean slate
2284
                }
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2285
                free(tmp_str);
1 by brian
clean slate
2286
              }
2287
              else
2288
              {
2289
                /* change any strings ("inf", "-inf", "nan") into NULL */
2290
                char *ptr= row[i];
2291
                if (my_isalpha(charset_info, *ptr) || (*ptr == '-' &&
2292
                    my_isalpha(charset_info, ptr[1])))
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2293
                  extended_row.append( "NULL");
1 by brian
clean slate
2294
                else
2295
                {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2296
                  extended_row.append( ptr);
1 by brian
clean slate
2297
                }
2298
              }
2299
            }
2300
            else
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2301
              extended_row.append("''");
1 by brian
clean slate
2302
          }
2303
          else
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2304
            extended_row.append("NULL");
1 by brian
clean slate
2305
        }
2306
        else
2307
        {
2308
          if (i && !opt_xml)
2309
          {
2310
            fputc(',', md_result_file);
2311
            check_io(md_result_file);
2312
          }
2313
          if (row[i])
2314
          {
2315
            if (!IS_NUM_FIELD(field))
2316
            {
2317
              if (opt_xml)
2318
              {
2319
                if (opt_hex_blob && is_blob && length)
2320
                {
2321
                  /* Define xsi:type="xs:hexBinary" for hex encoded data */
2322
                  print_xml_tag(md_result_file, "\t\t", "", "field", "name=",
2323
                                field->name, "xsi:type=", "xs:hexBinary", NullS);
2324
                  print_blob_as_hex(md_result_file, row[i], length);
2325
                }
2326
                else
2327
                {
2328
                  print_xml_tag(md_result_file, "\t\t", "", "field", "name=", 
2329
                                field->name, NullS);
2330
                  print_quoted_xml(md_result_file, row[i], length);
2331
                }
2332
                fputs("</field>\n", md_result_file);
2333
              }
2334
              else if (opt_hex_blob && is_blob && length)
2335
              {
2336
                fputs("0x", md_result_file);
2337
                print_blob_as_hex(md_result_file, row[i], length);
2338
              }
2339
              else
2340
                unescape(md_result_file, row[i], length);
2341
            }
2342
            else
2343
            {
2344
              /* change any strings ("inf", "-inf", "nan") into NULL */
2345
              char *ptr= row[i];
2346
              if (opt_xml)
2347
              {
2348
                print_xml_tag(md_result_file, "\t\t", "", "field", "name=",
2349
                        field->name, NullS);
2350
                fputs(!my_isalpha(charset_info, *ptr) ? ptr: "NULL",
2351
                      md_result_file);
2352
                fputs("</field>\n", md_result_file);
2353
              }
2354
              else if (my_isalpha(charset_info, *ptr) ||
2355
                       (*ptr == '-' && my_isalpha(charset_info, ptr[1])))
2356
                fputs("NULL", md_result_file);
2357
              else
2358
                fputs(ptr, md_result_file);
2359
            }
2360
          }
2361
          else
2362
          {
2363
            /* The field value is NULL */
2364
            if (!opt_xml)
2365
              fputs("NULL", md_result_file);
2366
            else
2367
              print_xml_null_tag(md_result_file, "\t\t", "field name=",
2368
                                 field->name, "\n");
2369
          }
2370
          check_io(md_result_file);
2371
        }
2372
      }
2373
2374
      if (opt_xml)
2375
      {
2376
        fputs("\t</row>\n", md_result_file);
2377
        check_io(md_result_file);
2378
      }
2379
2380
      if (extended_insert)
2381
      {
288 by Brian Aker
ulong cleanp in client apps
2382
        uint32_t row_length;
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2383
        extended_row.append(")");
2384
        row_length= 2 + extended_row.length();
1 by brian
clean slate
2385
        if (total_length + row_length < opt_net_buffer_length)
2386
        {
2387
          total_length+= row_length;
2388
          fputc(',',md_result_file);            /* Always row break */
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2389
          fputs(extended_row.c_str(),md_result_file);
1 by brian
clean slate
2390
        }
2391
        else
2392
        {
2393
          if (row_break)
2394
            fputs(";\n", md_result_file);
2395
          row_break=1;                          /* This is first row */
2396
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2397
          fputs(insert_pat.c_str(),md_result_file);
2398
          fputs(extended_row.c_str(),md_result_file);
1 by brian
clean slate
2399
          total_length= row_length+init_length;
2400
        }
2401
        check_io(md_result_file);
2402
      }
2403
      else if (!opt_xml)
2404
      {
2405
        fputs(");\n", md_result_file);
2406
        check_io(md_result_file);
2407
      }
2408
    }
2409
2410
    /* XML - close table tag and supress regular output */
2411
    if (opt_xml)
2412
        fputs("\t</table_data>\n", md_result_file);
2413
    else if (extended_insert && row_break)
2414
      fputs(";\n", md_result_file);             /* If not empty table */
2415
    fflush(md_result_file);
2416
    check_io(md_result_file);
206.3.1 by Patrick Galbraith
Most everything working with client rename
2417
    if (drizzle_errno(drizzle))
1 by brian
clean slate
2418
    {
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
2419
      snprintf(buf, sizeof(buf),
288 by Brian Aker
ulong cleanp in client apps
2420
               "%s: Error %d: %s when dumping table %s at row: %d\n",
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
2421
               my_progname,
206.3.1 by Patrick Galbraith
Most everything working with client rename
2422
               drizzle_errno(drizzle),
2423
               drizzle_error(drizzle),
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
2424
               result_table,
2425
               rownr);
1 by brian
clean slate
2426
      fputs(buf,stderr);
2427
      error= EX_CONSCHECK;
2428
      goto err;
2429
    }
2430
2431
    /* Moved enable keys to before unlock per bug 15977 */
2432
    if (opt_disable_keys)
2433
    {
2434
      fprintf(md_result_file,"/*!40000 ALTER TABLE %s ENABLE KEYS */;\n",
2435
              opt_quoted_table);
2436
      check_io(md_result_file);
2437
    }
2438
    if (opt_lock)
2439
    {
2440
      fputs("UNLOCK TABLES;\n", md_result_file);
2441
      check_io(md_result_file);
2442
    }
2443
    if (opt_autocommit)
2444
    {
2445
      fprintf(md_result_file, "commit;\n");
2446
      check_io(md_result_file);
2447
    }
206.3.1 by Patrick Galbraith
Most everything working with client rename
2448
    drizzle_free_result(res);
1 by brian
clean slate
2449
  }
142.1.2 by Patrick
All DBUG_x removed from client/
2450
  return;
1 by brian
clean slate
2451
2452
err:
2453
  maybe_exit(error);
142.1.2 by Patrick
All DBUG_x removed from client/
2454
  return;
1 by brian
clean slate
2455
} /* dump_table */
2456
2457
2458
static char *getTableName(int reset)
2459
{
206.3.1 by Patrick Galbraith
Most everything working with client rename
2460
  static DRIZZLE_RES *res= NULL;
2461
  DRIZZLE_ROW    row;
1 by brian
clean slate
2462
2463
  if (!res)
2464
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2465
    if (!(res= drizzle_list_tables(drizzle,NullS)))
1 by brian
clean slate
2466
      return(NULL);
2467
  }
206.3.1 by Patrick Galbraith
Most everything working with client rename
2468
  if ((row= drizzle_fetch_row(res)))
1 by brian
clean slate
2469
    return((char*) row[0]);
2470
2471
  if (reset)
206.3.1 by Patrick Galbraith
Most everything working with client rename
2472
    drizzle_data_seek(res,0);      /* We want to read again */
1 by brian
clean slate
2473
  else
2474
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2475
    drizzle_free_result(res);
1 by brian
clean slate
2476
    res= NULL;
2477
  }
2478
  return(NULL);
2479
} /* getTableName */
2480
2481
2482
static int dump_all_databases()
2483
{
206.3.1 by Patrick Galbraith
Most everything working with client rename
2484
  DRIZZLE_ROW row;
2485
  DRIZZLE_RES *tableres;
1 by brian
clean slate
2486
  int result=0;
2487
206.3.1 by Patrick Galbraith
Most everything working with client rename
2488
  if (drizzle_query_with_error_report(drizzle, &tableres, "SHOW DATABASES"))
1 by brian
clean slate
2489
    return 1;
206.3.1 by Patrick Galbraith
Most everything working with client rename
2490
  while ((row= drizzle_fetch_row(tableres)))
1 by brian
clean slate
2491
  {
2492
    if (dump_all_tables_in_db(row[0]))
2493
      result=1;
2494
  }
2495
  return result;
2496
}
2497
/* dump_all_databases */
2498
2499
2500
static int dump_databases(char **db_names)
2501
{
2502
  int result=0;
2503
  char **db;
142.1.2 by Patrick
All DBUG_x removed from client/
2504
1 by brian
clean slate
2505
2506
  for (db= db_names ; *db ; db++)
2507
  {
2508
    if (dump_all_tables_in_db(*db))
2509
      result=1;
2510
  }
142.1.2 by Patrick
All DBUG_x removed from client/
2511
  return(result);
1 by brian
clean slate
2512
} /* dump_databases */
2513
2514
2515
/*
2516
Table Specific database initalization.
2517
2518
SYNOPSIS
2519
  init_dumping_tables
2520
  qdatabase      quoted name of the database
2521
2522
RETURN VALUES
2523
  0        Success.
2524
  1        Failure.
2525
*/
2526
2527
int init_dumping_tables(char *qdatabase)
2528
{
142.1.2 by Patrick
All DBUG_x removed from client/
2529
1 by brian
clean slate
2530
2531
  if (!opt_create_db)
2532
  {
2533
    char qbuf[256];
206.3.1 by Patrick Galbraith
Most everything working with client rename
2534
    DRIZZLE_ROW row;
2535
    DRIZZLE_RES *dbinfo;
1 by brian
clean slate
2536
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
2537
    snprintf(qbuf, sizeof(qbuf),
2538
             "SHOW CREATE DATABASE IF NOT EXISTS %s",
2539
             qdatabase);
1 by brian
clean slate
2540
206.3.1 by Patrick Galbraith
Most everything working with client rename
2541
    if (drizzle_query(drizzle, qbuf) || !(dbinfo = drizzle_store_result(drizzle)))
1 by brian
clean slate
2542
    {
2543
      /* Old server version, dump generic CREATE DATABASE */
2544
      if (opt_drop_database)
2545
        fprintf(md_result_file,
2546
                "\n/*!40000 DROP DATABASE IF EXISTS %s*/;\n",
2547
                qdatabase);
2548
      fprintf(md_result_file,
2549
              "\nCREATE DATABASE /*!32312 IF NOT EXISTS*/ %s;\n",
2550
              qdatabase);
2551
    }
2552
    else
2553
    {
2554
      if (opt_drop_database)
2555
        fprintf(md_result_file,
2556
                "\n/*!40000 DROP DATABASE IF EXISTS %s*/;\n",
2557
                qdatabase);
206.3.1 by Patrick Galbraith
Most everything working with client rename
2558
      row = drizzle_fetch_row(dbinfo);
1 by brian
clean slate
2559
      if (row[1])
2560
      {
2561
        fprintf(md_result_file,"\n%s;\n",row[1]);
2562
      }
206.3.1 by Patrick Galbraith
Most everything working with client rename
2563
      drizzle_free_result(dbinfo);
1 by brian
clean slate
2564
    }
2565
  }
142.1.2 by Patrick
All DBUG_x removed from client/
2566
  return(0);
1 by brian
clean slate
2567
} /* init_dumping_tables */
2568
2569
2570
static int init_dumping(char *database, int init_func(char*))
2571
{
206.3.1 by Patrick Galbraith
Most everything working with client rename
2572
  if (drizzle_get_server_version(drizzle) >= 50003 &&
383.1.12 by Brian Aker
Much closer toward UTF8 being around all the time...
2573
      !my_strcasecmp(&my_charset_utf8_general_ci, database, "information_schema"))
1 by brian
clean slate
2574
    return 1;
2575
206.3.1 by Patrick Galbraith
Most everything working with client rename
2576
  if (drizzle_select_db(drizzle, database))
1 by brian
clean slate
2577
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2578
    DB_error(drizzle, "when selecting the database");
1 by brian
clean slate
2579
    return 1;                   /* If --force */
2580
  }
2581
  if (!path && !opt_xml)
2582
  {
2583
    if (opt_databases || opt_alldbs)
2584
    {
2585
      /*
2586
        length of table name * 2 (if name contains quotes), 2 quotes and 0
2587
      */
2588
      char quoted_database_buf[NAME_LEN*2+3];
2589
      char *qdatabase= quote_name(database,quoted_database_buf,opt_quoted);
2590
      if (opt_comments)
2591
      {
2592
        fprintf(md_result_file,"\n--\n-- Current Database: %s\n--\n", qdatabase);
2593
        check_io(md_result_file);
2594
      }
2595
2596
      /* Call the view or table specific function */
2597
      init_func(qdatabase);
2598
2599
      fprintf(md_result_file,"\nUSE %s;\n", qdatabase);
2600
      check_io(md_result_file);
2601
    }
2602
  }
2603
  if (extended_insert)
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2604
    extended_row.clear();
1 by brian
clean slate
2605
  return 0;
2606
} /* init_dumping */
2607
2608
2609
/* Return 1 if we should copy the table */
2610
143 by Brian Aker
Bool cleanup.
2611
static bool include_table(const uchar *hash_key, size_t len)
1 by brian
clean slate
2612
{
2613
  return !hash_search(&ignore_table, hash_key, len);
2614
}
2615
2616
2617
static int dump_all_tables_in_db(char *database)
2618
{
2619
  char *table;
2620
  uint numrows;
2621
  char table_buff[NAME_LEN*2+3];
2622
  char hash_key[2*NAME_LEN+2];  /* "db.tablename" */
2623
  char *afterdot;
383.1.12 by Brian Aker
Much closer toward UTF8 being around all the time...
2624
  int using_mysql_db= my_strcasecmp(&my_charset_utf8_general_ci, database, "mysql");
142.1.2 by Patrick
All DBUG_x removed from client/
2625
1 by brian
clean slate
2626
266.1.21 by Monty Taylor
Removed references to strmov and strnmov
2627
  afterdot= stpcpy(hash_key, database);
1 by brian
clean slate
2628
  *afterdot++= '.';
2629
2630
  if (init_dumping(database, init_dumping_tables))
142.1.2 by Patrick
All DBUG_x removed from client/
2631
    return(1);
1 by brian
clean slate
2632
  if (opt_xml)
2633
    print_xml_tag(md_result_file, "", "\n", "database", "name=", database, NullS);
2634
  if (lock_tables)
2635
  {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2636
    string query;
2637
    query= "LOCK TABLES ";
1 by brian
clean slate
2638
    for (numrows= 0 ; (table= getTableName(1)) ; )
2639
    {
266.1.21 by Monty Taylor
Removed references to strmov and strnmov
2640
      char *end= stpcpy(afterdot, table);
1 by brian
clean slate
2641
      if (include_table((uchar*) hash_key,end - hash_key))
2642
      {
2643
        numrows++;
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2644
        query.append( quote_name(table, table_buff, 1));
2645
        query.append( " READ /*!32311 LOCAL */,");
1 by brian
clean slate
2646
      }
2647
    }
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2648
    if (numrows && drizzle_real_query(drizzle, query.c_str(), query.length()-1))
206.3.1 by Patrick Galbraith
Most everything working with client rename
2649
      DB_error(drizzle, "when using LOCK TABLES");
1 by brian
clean slate
2650
            /* We shall continue here, if --force was given */
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2651
    query.clear();
1 by brian
clean slate
2652
  }
2653
  if (flush_logs)
2654
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2655
    if (drizzle_refresh(drizzle, REFRESH_LOG))
2656
      DB_error(drizzle, "when doing refresh");
1 by brian
clean slate
2657
           /* We shall continue here, if --force was given */
2658
  }
2659
  while ((table= getTableName(0)))
2660
  {
266.1.21 by Monty Taylor
Removed references to strmov and strnmov
2661
    char *end= stpcpy(afterdot, table);
1 by brian
clean slate
2662
    if (include_table((uchar*) hash_key, end - hash_key))
2663
    {
2664
      dump_table(table,database);
2665
      my_free(order_by, MYF(MY_ALLOW_ZERO_PTR));
2666
      order_by= 0;
2667
    }
2668
  }
2669
  if (opt_xml)
2670
  {
2671
    fputs("</database>\n", md_result_file);
2672
    check_io(md_result_file);
2673
  }
2674
  if (lock_tables)
206.3.1 by Patrick Galbraith
Most everything working with client rename
2675
    VOID(drizzle_query_with_error_report(drizzle, 0, "UNLOCK TABLES"));
1 by brian
clean slate
2676
  if (flush_privileges && using_mysql_db == 0)
2677
  {
2678
    fprintf(md_result_file,"\n--\n-- Flush Grant Tables \n--\n");
2679
    fprintf(md_result_file,"\n/*! FLUSH PRIVILEGES */;\n");
2680
  }
142.1.2 by Patrick
All DBUG_x removed from client/
2681
  return(0);
1 by brian
clean slate
2682
} /* dump_all_tables_in_db */
2683
2684
2685
/*
2686
  get_actual_table_name -- executes a SHOW TABLES LIKE '%s' to get the actual
2687
  table name from the server for the table name given on the command line.
2688
  we do this because the table name given on the command line may be a
2689
  different case (e.g.  T1 vs t1)
2690
2691
  RETURN
2692
    pointer to the table name
2693
    0 if error
2694
*/
2695
2696
static char *get_actual_table_name(const char *old_table_name, MEM_ROOT *root)
2697
{
2698
  char *name= 0;
206.3.1 by Patrick Galbraith
Most everything working with client rename
2699
  DRIZZLE_RES  *table_res;
2700
  DRIZZLE_ROW  row;
1 by brian
clean slate
2701
  char query[50 + 2*NAME_LEN];
2702
  char show_name_buff[FN_REFLEN];
142.1.2 by Patrick
All DBUG_x removed from client/
2703
1 by brian
clean slate
2704
2705
  /* Check memory for quote_for_like() */
142.1.2 by Patrick
All DBUG_x removed from client/
2706
  assert(2*sizeof(old_table_name) < sizeof(show_name_buff));
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
2707
  snprintf(query, sizeof(query), "SHOW TABLES LIKE %s",
2708
           quote_for_like(old_table_name, show_name_buff));
1 by brian
clean slate
2709
206.3.1 by Patrick Galbraith
Most everything working with client rename
2710
  if (drizzle_query_with_error_report(drizzle, 0, query))
1 by brian
clean slate
2711
    return NullS;
2712
206.3.1 by Patrick Galbraith
Most everything working with client rename
2713
  if ((table_res= drizzle_store_result(drizzle)))
1 by brian
clean slate
2714
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2715
    uint64_t num_rows= drizzle_num_rows(table_res);
1 by brian
clean slate
2716
    if (num_rows > 0)
2717
    {
77.1.107 by Monty Taylor
Fixed build warnings.
2718
      uint32_t *lengths;
1 by brian
clean slate
2719
      /*
2720
        Return first row
2721
        TODO: Return all matching rows
2722
      */
206.3.1 by Patrick Galbraith
Most everything working with client rename
2723
      row= drizzle_fetch_row(table_res);
2724
      lengths= drizzle_fetch_lengths(table_res);
1 by brian
clean slate
2725
      name= strmake_root(root, row[0], lengths[0]);
2726
    }
206.3.1 by Patrick Galbraith
Most everything working with client rename
2727
    drizzle_free_result(table_res);
1 by brian
clean slate
2728
  }
142.1.2 by Patrick
All DBUG_x removed from client/
2729
  return(name);
1 by brian
clean slate
2730
}
2731
2732
2733
static int dump_selected_tables(char *db, char **table_names, int tables)
2734
{
2735
  char table_buff[NAME_LEN*2+3];
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2736
  string lock_tables_query;
1 by brian
clean slate
2737
  MEM_ROOT root;
2738
  char **dump_tables, **pos, **end;
142.1.2 by Patrick
All DBUG_x removed from client/
2739
1 by brian
clean slate
2740
2741
  if (init_dumping(db, init_dumping_tables))
142.1.2 by Patrick
All DBUG_x removed from client/
2742
    return(1);
1 by brian
clean slate
2743
2744
  init_alloc_root(&root, 8192, 0);
2745
  if (!(dump_tables= pos= (char**) alloc_root(&root, tables * sizeof(char *))))
2746
     die(EX_EOM, "alloc_root failure.");
2747
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2748
  lock_tables_query= "LOCK TABLES ";
1 by brian
clean slate
2749
  for (; tables > 0 ; tables-- , table_names++)
2750
  {
2751
    /* the table name passed on commandline may be wrong case */
2752
    if ((*pos= get_actual_table_name(*table_names, &root)))
2753
    {
2754
      /* Add found table name to lock_tables_query */
2755
      if (lock_tables)
2756
      {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2757
        lock_tables_query.append( quote_name(*pos, table_buff, 1));
2758
        lock_tables_query.append( " READ /*!32311 LOCAL */,");
1 by brian
clean slate
2759
      }
2760
      pos++;
2761
    }
2762
    else
2763
    {
2764
      if (!ignore_errors)
2765
      {
2766
        free_root(&root, MYF(0));
2767
      }
2768
      maybe_die(EX_ILLEGAL_TABLE, "Couldn't find table: \"%s\"", *table_names);
2769
      /* We shall countinue here, if --force was given */
2770
    }
2771
  }
2772
  end= pos;
2773
2774
  if (lock_tables)
2775
  {
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
2776
    if (drizzle_real_query(drizzle, lock_tables_query.c_str(),
2777
                         lock_tables_query.length()-1))
1 by brian
clean slate
2778
    {
2779
      if (!ignore_errors)
2780
      {
2781
        free_root(&root, MYF(0));
2782
      }
206.3.1 by Patrick Galbraith
Most everything working with client rename
2783
      DB_error(drizzle, "when doing LOCK TABLES");
1 by brian
clean slate
2784
       /* We shall countinue here, if --force was given */
2785
    }
2786
  }
2787
  if (flush_logs)
2788
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2789
    if (drizzle_refresh(drizzle, REFRESH_LOG))
1 by brian
clean slate
2790
    {
2791
      if (!ignore_errors)
2792
        free_root(&root, MYF(0));
206.3.1 by Patrick Galbraith
Most everything working with client rename
2793
      DB_error(drizzle, "when doing refresh");
1 by brian
clean slate
2794
    }
2795
     /* We shall countinue here, if --force was given */
2796
  }
2797
  if (opt_xml)
2798
    print_xml_tag(md_result_file, "", "\n", "database", "name=", db, NullS);
2799
2800
  /* Dump each selected table */
2801
  for (pos= dump_tables; pos < end; pos++)
2802
    dump_table(*pos, db);
2803
2804
  free_root(&root, MYF(0));
2805
  my_free(order_by, MYF(MY_ALLOW_ZERO_PTR));
2806
  order_by= 0;
2807
  if (opt_xml)
2808
  {
2809
    fputs("</database>\n", md_result_file);
2810
    check_io(md_result_file);
2811
  }
2812
  if (lock_tables)
206.3.1 by Patrick Galbraith
Most everything working with client rename
2813
    VOID(drizzle_query_with_error_report(drizzle, 0, "UNLOCK TABLES"));
142.1.2 by Patrick
All DBUG_x removed from client/
2814
  return(0);
1 by brian
clean slate
2815
} /* dump_selected_tables */
2816
2817
206.3.1 by Patrick Galbraith
Most everything working with client rename
2818
static int do_show_master_status(DRIZZLE *drizzle_con)
1 by brian
clean slate
2819
{
206.3.1 by Patrick Galbraith
Most everything working with client rename
2820
  DRIZZLE_ROW row;
2821
  DRIZZLE_RES *master;
1 by brian
clean slate
2822
  const char *comment_prefix=
206.3.1 by Patrick Galbraith
Most everything working with client rename
2823
    (opt_master_data == DRIZZLE_OPT_MASTER_DATA_COMMENTED_SQL) ? "-- " : "";
2824
  if (drizzle_query_with_error_report(drizzle_con, &master, "SHOW MASTER STATUS"))
1 by brian
clean slate
2825
  {
2826
    return 1;
2827
  }
2828
  else
2829
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2830
    row= drizzle_fetch_row(master);
1 by brian
clean slate
2831
    if (row && row[0] && row[1])
2832
    {
2833
      /* SHOW MASTER STATUS reports file and position */
2834
      if (opt_comments)
2835
        fprintf(md_result_file,
2836
                "\n--\n-- Position to start replication or point-in-time "
2837
                "recovery from\n--\n\n");
2838
      fprintf(md_result_file,
2839
              "%sCHANGE MASTER TO MASTER_LOG_FILE='%s', MASTER_LOG_POS=%s;\n",
2840
              comment_prefix, row[0], row[1]);
2841
      check_io(md_result_file);
2842
    }
2843
    else if (!ignore_errors)
2844
    {
2845
      /* SHOW MASTER STATUS reports nothing and --force is not enabled */
2846
      my_printf_error(0, "Error: Binlogging on server not active",
2847
                      MYF(0));
206.3.1 by Patrick Galbraith
Most everything working with client rename
2848
      drizzle_free_result(master);
2849
      maybe_exit(EX_DRIZZLEERR);
1 by brian
clean slate
2850
      return 1;
2851
    }
206.3.1 by Patrick Galbraith
Most everything working with client rename
2852
    drizzle_free_result(master);
1 by brian
clean slate
2853
  }
2854
  return 0;
2855
}
2856
206.3.1 by Patrick Galbraith
Most everything working with client rename
2857
static int do_stop_slave_sql(DRIZZLE *drizzle_con)
1 by brian
clean slate
2858
{
206.3.1 by Patrick Galbraith
Most everything working with client rename
2859
  DRIZZLE_RES *slave;
1 by brian
clean slate
2860
  /* We need to check if the slave sql is running in the first place */
206.3.1 by Patrick Galbraith
Most everything working with client rename
2861
  if (drizzle_query_with_error_report(drizzle_con, &slave, "SHOW SLAVE STATUS"))
1 by brian
clean slate
2862
    return(1);
2863
  else
2864
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2865
    DRIZZLE_ROW row= drizzle_fetch_row(slave);
1 by brian
clean slate
2866
    if (row && row[11])
2867
    {
2868
      /* if SLAVE SQL is not running, we don't stop it */
2869
      if (!strcmp(row[11],"No"))
2870
      {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2871
        drizzle_free_result(slave);
1 by brian
clean slate
2872
        /* Silently assume that they don't have the slave running */
2873
        return(0);
2874
      }
2875
    }
2876
  }
206.3.1 by Patrick Galbraith
Most everything working with client rename
2877
  drizzle_free_result(slave);
1 by brian
clean slate
2878
2879
  /* now, stop slave if running */
206.3.1 by Patrick Galbraith
Most everything working with client rename
2880
  if (drizzle_query_with_error_report(drizzle_con, 0, "STOP SLAVE SQL_THREAD"))
1 by brian
clean slate
2881
    return(1);
2882
2883
  return(0);
2884
}
2885
2886
static int add_stop_slave(void)
2887
{
2888
  if (opt_comments)
2889
    fprintf(md_result_file,
2890
            "\n--\n-- stop slave statement to make a recovery dump)\n--\n\n");
2891
  fprintf(md_result_file, "STOP SLAVE;\n");
2892
  return(0);
2893
}
2894
2895
static int add_slave_statements(void)
2896
{
2897
  if (opt_comments)
2898
    fprintf(md_result_file,
2899
            "\n--\n-- start slave statement to make a recovery dump)\n--\n\n");
2900
  fprintf(md_result_file, "START SLAVE;\n");
2901
  return(0);
2902
}
2903
206.3.1 by Patrick Galbraith
Most everything working with client rename
2904
static int do_show_slave_status(DRIZZLE *drizzle_con)
1 by brian
clean slate
2905
{
206.3.1 by Patrick Galbraith
Most everything working with client rename
2906
  DRIZZLE_RES *slave;
1 by brian
clean slate
2907
  const char *comment_prefix=
206.3.1 by Patrick Galbraith
Most everything working with client rename
2908
    (opt_slave_data == DRIZZLE_OPT_SLAVE_DATA_COMMENTED_SQL) ? "-- " : "";
2909
  if (drizzle_query_with_error_report(drizzle_con, &slave, "SHOW SLAVE STATUS"))
1 by brian
clean slate
2910
  {
2911
    if (!ignore_errors)
2912
    {
2913
      /* SHOW SLAVE STATUS reports nothing and --force is not enabled */
2914
      my_printf_error(0, "Error: Slave not set up", MYF(0));
2915
    }
2916
    return 1;
2917
  }
2918
  else
2919
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2920
    DRIZZLE_ROW row= drizzle_fetch_row(slave);
1 by brian
clean slate
2921
    if (row && row[9] && row[21])
2922
    {
2923
      /* SHOW MASTER STATUS reports file and position */
2924
      if (opt_comments)
2925
        fprintf(md_result_file,
2926
                "\n--\n-- Position to start replication or point-in-time "
2927
                "recovery from (the master of this slave)\n--\n\n");
2928
2929
      fprintf(md_result_file, "%sCHANGE MASTER TO ", comment_prefix);
2930
2931
      if (opt_include_master_host_port)
2932
      {
2933
        if (row[1])
2934
          fprintf(md_result_file, "MASTER_HOST='%s', ", row[1]);
2935
        if (row[3])
2936
          fprintf(md_result_file, "MASTER_PORT='%s', ", row[3]);
2937
      }
2938
      fprintf(md_result_file,
2939
              "MASTER_LOG_FILE='%s', MASTER_LOG_POS=%s;\n", row[9], row[21]);
2940
2941
      check_io(md_result_file);
2942
    }
206.3.1 by Patrick Galbraith
Most everything working with client rename
2943
    drizzle_free_result(slave);
1 by brian
clean slate
2944
  }
2945
  return 0;
2946
}
2947
206.3.1 by Patrick Galbraith
Most everything working with client rename
2948
static int do_start_slave_sql(DRIZZLE *drizzle_con)
1 by brian
clean slate
2949
{
206.3.1 by Patrick Galbraith
Most everything working with client rename
2950
  DRIZZLE_RES *slave;
1 by brian
clean slate
2951
  /* We need to check if the slave sql is stopped in the first place */
206.3.1 by Patrick Galbraith
Most everything working with client rename
2952
  if (drizzle_query_with_error_report(drizzle_con, &slave, "SHOW SLAVE STATUS"))
1 by brian
clean slate
2953
    return(1);
2954
  else
2955
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2956
    DRIZZLE_ROW row= drizzle_fetch_row(slave);
1 by brian
clean slate
2957
    if (row && row[11])
2958
    {
2959
      /* if SLAVE SQL is not running, we don't start it */
2960
      if (!strcmp(row[11],"Yes"))
2961
      {
206.3.1 by Patrick Galbraith
Most everything working with client rename
2962
        drizzle_free_result(slave);
1 by brian
clean slate
2963
        /* Silently assume that they don't have the slave running */
2964
        return(0);
2965
      }
2966
    }
2967
  }
206.3.1 by Patrick Galbraith
Most everything working with client rename
2968
  drizzle_free_result(slave);
1 by brian
clean slate
2969
2970
  /* now, start slave if stopped */
206.3.1 by Patrick Galbraith
Most everything working with client rename
2971
  if (drizzle_query_with_error_report(drizzle_con, 0, "START SLAVE"))
1 by brian
clean slate
2972
  {
2973
    my_printf_error(0, "Error: Unable to start slave", MYF(0));
2974
    return 1;
2975
  }
2976
  return(0);
2977
}
2978
2979
2980
206.3.1 by Patrick Galbraith
Most everything working with client rename
2981
static int do_flush_tables_read_lock(DRIZZLE *drizzle_con)
1 by brian
clean slate
2982
{
2983
  /*
2984
    We do first a FLUSH TABLES. If a long update is running, the FLUSH TABLES
2985
    will wait but will not stall the whole mysqld, and when the long update is
2986
    done the FLUSH TABLES WITH READ LOCK will start and succeed quickly. So,
2987
    FLUSH TABLES is to lower the probability of a stage where both mysqldump
2988
    and most client connections are stalled. Of course, if a second long
2989
    update starts between the two FLUSHes, we have that bad stall.
2990
  */
2991
  return
206.3.1 by Patrick Galbraith
Most everything working with client rename
2992
    ( drizzle_query_with_error_report(drizzle_con, 0, "FLUSH TABLES") ||
2993
      drizzle_query_with_error_report(drizzle_con, 0,
1 by brian
clean slate
2994
                                    "FLUSH TABLES WITH READ LOCK") );
2995
}
2996
2997
206.3.1 by Patrick Galbraith
Most everything working with client rename
2998
static int do_unlock_tables(DRIZZLE *drizzle_con)
1 by brian
clean slate
2999
{
206.3.1 by Patrick Galbraith
Most everything working with client rename
3000
  return drizzle_query_with_error_report(drizzle_con, 0, "UNLOCK TABLES");
1 by brian
clean slate
3001
}
3002
206.3.1 by Patrick Galbraith
Most everything working with client rename
3003
static int get_bin_log_name(DRIZZLE *drizzle_con,
1 by brian
clean slate
3004
                            char* buff_log_name, uint buff_len)
3005
{
206.3.1 by Patrick Galbraith
Most everything working with client rename
3006
  DRIZZLE_RES *res;
3007
  DRIZZLE_ROW row;
1 by brian
clean slate
3008
206.3.1 by Patrick Galbraith
Most everything working with client rename
3009
  if (drizzle_query(drizzle_con, "SHOW MASTER STATUS") ||
3010
      !(res= drizzle_store_result(drizzle)))
1 by brian
clean slate
3011
    return 1;
3012
206.3.1 by Patrick Galbraith
Most everything working with client rename
3013
  if (!(row= drizzle_fetch_row(res)))
1 by brian
clean slate
3014
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
3015
    drizzle_free_result(res);
1 by brian
clean slate
3016
    return 1;
3017
  }
3018
  /*
3019
    Only one row is returned, and the first column is the name of the
3020
    active log.
3021
  */
3022
  strmake(buff_log_name, row[0], buff_len - 1);
3023
206.3.1 by Patrick Galbraith
Most everything working with client rename
3024
  drizzle_free_result(res);
1 by brian
clean slate
3025
  return 0;
3026
}
3027
206.3.1 by Patrick Galbraith
Most everything working with client rename
3028
static int purge_bin_logs_to(DRIZZLE *drizzle_con, char* log_name)
1 by brian
clean slate
3029
{
3030
  int err;
279.2.6 by Monty Taylor
Replaced DYN string in drizzledump.
3031
  string str= "PURGE BINARY LOGS TO '";
3032
  str.append(log_name);
3033
  str.append("'");
3034
  err = drizzle_query_with_error_report(drizzle_con, 0, str.c_str());
1 by brian
clean slate
3035
  return err;
3036
}
3037
3038
206.3.1 by Patrick Galbraith
Most everything working with client rename
3039
static int start_transaction(DRIZZLE *drizzle_con)
1 by brian
clean slate
3040
{
3041
  /*
3042
    We use BEGIN for old servers. --single-transaction --master-data will fail
3043
    on old servers, but that's ok as it was already silently broken (it didn't
3044
    do a consistent read, so better tell people frankly, with the error).
3045
3046
    We want the first consistent read to be used for all tables to dump so we
3047
    need the REPEATABLE READ level (not anything lower, for example READ
3048
    COMMITTED would give one new consistent read per dumped table).
3049
  */
206.3.1 by Patrick Galbraith
Most everything working with client rename
3050
  if ((drizzle_get_server_version(drizzle_con) < 40100) && opt_master_data)
1 by brian
clean slate
3051
  {
3052
    fprintf(stderr, "-- %s: the combination of --single-transaction and "
206.3.1 by Patrick Galbraith
Most everything working with client rename
3053
            "--master-data requires a DRIZZLE server version of at least 4.1 "
1 by brian
clean slate
3054
            "(current server's version is %s). %s\n",
3055
            ignore_errors ? "Warning" : "Error",
206.3.1 by Patrick Galbraith
Most everything working with client rename
3056
            drizzle_con->server_version ? drizzle_con->server_version : "unknown",
1 by brian
clean slate
3057
            ignore_errors ? "Continuing due to --force, backup may not be consistent across all tables!" : "Aborting.");
3058
    if (!ignore_errors)
206.3.1 by Patrick Galbraith
Most everything working with client rename
3059
      exit(EX_DRIZZLEERR);
1 by brian
clean slate
3060
  }
3061
206.3.1 by Patrick Galbraith
Most everything working with client rename
3062
  return (drizzle_query_with_error_report(drizzle_con, 0,
1 by brian
clean slate
3063
                                        "SET SESSION TRANSACTION ISOLATION "
3064
                                        "LEVEL REPEATABLE READ") ||
206.3.1 by Patrick Galbraith
Most everything working with client rename
3065
          drizzle_query_with_error_report(drizzle_con, 0,
1 by brian
clean slate
3066
                                        "START TRANSACTION "
3067
                                        "/*!40100 WITH CONSISTENT SNAPSHOT */"));
3068
}
3069
3070
288 by Brian Aker
ulong cleanp in client apps
3071
static uint32_t find_set(TYPELIB *lib, const char *x, uint length,
1 by brian
clean slate
3072
                      char **err_pos, uint *err_len)
3073
{
3074
  const char *end= x + length;
288 by Brian Aker
ulong cleanp in client apps
3075
  uint32_t found= 0;
1 by brian
clean slate
3076
  uint find;
3077
  char buff[255];
3078
3079
  *err_pos= 0;                  /* No error yet */
3080
  while (end > x && my_isspace(charset_info, end[-1]))
3081
    end--;
3082
3083
  *err_len= 0;
3084
  if (x != end)
3085
  {
3086
    const char *start= x;
3087
    for (;;)
3088
    {
3089
      const char *pos= start;
297 by Brian Aker
Final ulong cleanup in clients
3090
      uint32_t var_len;
1 by brian
clean slate
3091
3092
      for (; pos != end && *pos != ','; pos++) ;
297 by Brian Aker
Final ulong cleanup in clients
3093
      var_len= (uint32_t) (pos - start);
3094
      strmake(buff, start, min(sizeof(buff), var_len));
1 by brian
clean slate
3095
      find= find_type(buff, lib, var_len);
3096
      if (!find)
3097
      {
3098
        *err_pos= (char*) start;
3099
        *err_len= var_len;
3100
      }
3101
      else
152 by Brian Aker
longlong replacement
3102
        found|= ((int64_t) 1 << (find - 1));
1 by brian
clean slate
3103
      if (pos == end)
3104
        break;
3105
      start= pos + 1;
3106
    }
3107
  }
3108
  return found;
3109
}
3110
3111
3112
/* Print a value with a prefix on file */
206.3.1 by Patrick Galbraith
Most everything working with client rename
3113
static void print_value(FILE *file, DRIZZLE_RES  *result, DRIZZLE_ROW row,
1 by brian
clean slate
3114
                        const char *prefix, const char *name,
3115
                        int string_value)
3116
{
206.3.1 by Patrick Galbraith
Most everything working with client rename
3117
  DRIZZLE_FIELD   *field;
3118
  drizzle_field_seek(result, 0);
1 by brian
clean slate
3119
206.3.1 by Patrick Galbraith
Most everything working with client rename
3120
  for ( ; (field= drizzle_fetch_field(result)) ; row++)
1 by brian
clean slate
3121
  {
3122
    if (!strcmp(field->name,name))
3123
    {
3124
      if (row[0] && row[0][0] && strcmp(row[0],"0")) /* Skip default */
3125
      {
3126
        fputc(' ',file);
3127
        fputs(prefix, file);
3128
        if (string_value)
3129
          unescape(file,row[0],(uint) strlen(row[0]));
3130
        else
3131
          fputs(row[0], file);
3132
        check_io(file);
3133
        return;
3134
      }
3135
    }
3136
  }
3137
  return;                                       /* This shouldn't happen */
3138
} /* print_value */
3139
3140
3141
/*
3142
  SYNOPSIS
3143
3144
  Check if we the table is one of the table types that should be ignored:
3145
  MRG_ISAM, MRG_MYISAM, if opt_delayed, if that table supports delayed inserts.
163 by Brian Aker
Merge Monty's code.
3146
  If the table should be altogether ignored, it returns a true, false if it
1 by brian
clean slate
3147
  should not be ignored. If the user has selected to use INSERT DELAYED, it
3148
  sets the value of the bool pointer supports_delayed_inserts to 0 if not
3149
  supported, 1 if it is supported.
3150
3151
  ARGS
3152
3153
    check_if_ignore_table()
3154
    table_name                  Table name to check
3155
    table_type                  Type of table
3156
3157
  GLOBAL VARIABLES
206.3.1 by Patrick Galbraith
Most everything working with client rename
3158
    drizzle                       Drizzle connection
1 by brian
clean slate
3159
    verbose                     Write warning messages
3160
3161
  RETURN
3162
    char (bit value)            See IGNORE_ values at top
3163
*/
3164
3165
char check_if_ignore_table(const char *table_name, char *table_type)
3166
{
3167
  char result= IGNORE_NONE;
3168
  char buff[FN_REFLEN+80], show_name_buff[FN_REFLEN];
206.3.1 by Patrick Galbraith
Most everything working with client rename
3169
  DRIZZLE_RES *res= NULL;
3170
  DRIZZLE_ROW row;
142.1.2 by Patrick
All DBUG_x removed from client/
3171
1 by brian
clean slate
3172
3173
  /* Check memory for quote_for_like() */
142.1.2 by Patrick
All DBUG_x removed from client/
3174
  assert(2*sizeof(table_name) < sizeof(show_name_buff));
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
3175
  snprintf(buff, sizeof(buff), "show table status like %s",
3176
           quote_for_like(table_name, show_name_buff));
206.3.1 by Patrick Galbraith
Most everything working with client rename
3177
  if (drizzle_query_with_error_report(drizzle, &res, buff))
1 by brian
clean slate
3178
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
3179
    if (drizzle_errno(drizzle) != ER_PARSE_ERROR)
3180
    {                                   /* If old DRIZZLE version */
1 by brian
clean slate
3181
      verbose_msg("-- Warning: Couldn't get status information for "
206.3.1 by Patrick Galbraith
Most everything working with client rename
3182
                  "table %s (%s)\n", table_name, drizzle_error(drizzle));
142.1.2 by Patrick
All DBUG_x removed from client/
3183
      return(result);                       /* assume table is ok */
1 by brian
clean slate
3184
    }
3185
  }
206.3.1 by Patrick Galbraith
Most everything working with client rename
3186
  if (!(row= drizzle_fetch_row(res)))
1 by brian
clean slate
3187
  {
3188
    fprintf(stderr,
3189
            "Error: Couldn't read status information for table %s (%s)\n",
206.3.1 by Patrick Galbraith
Most everything working with client rename
3190
            table_name, drizzle_error(drizzle));
3191
    drizzle_free_result(res);
142.1.2 by Patrick
All DBUG_x removed from client/
3192
    return(result);                         /* assume table is ok */
1 by brian
clean slate
3193
  }
3194
  if (!(row[1]))
3195
    strmake(table_type, "VIEW", NAME_LEN-1);
3196
  else
3197
  {
3198
    /*
3199
      If the table type matches any of these, we do support delayed inserts.
3200
      Note: we do not want to skip dumping this table if if is not one of
3201
      these types, but we do want to use delayed inserts in the dump if
3202
      the table type is _NOT_ one of these types
3203
    */
3204
    strmake(table_type, row[1], NAME_LEN-1);
3205
    if (opt_delayed)
3206
    {
3207
      if (strcmp(table_type,"MyISAM") &&
3208
          strcmp(table_type,"ISAM") &&
3209
          strcmp(table_type,"ARCHIVE") &&
3210
          strcmp(table_type,"HEAP") &&
3211
          strcmp(table_type,"MEMORY"))
3212
        result= IGNORE_INSERT_DELAYED;
3213
    }
3214
3215
    /*
3216
      If these two types, we do want to skip dumping the table
3217
    */
3218
    if (!opt_no_data &&
383.1.12 by Brian Aker
Much closer toward UTF8 being around all the time...
3219
        (!my_strcasecmp(&my_charset_utf8_general_ci, table_type, "MRG_MyISAM") ||
1 by brian
clean slate
3220
         !strcmp(table_type,"MRG_ISAM")))
3221
      result= IGNORE_DATA;
3222
  }
206.3.1 by Patrick Galbraith
Most everything working with client rename
3223
  drizzle_free_result(res);
142.1.2 by Patrick
All DBUG_x removed from client/
3224
  return(result);
1 by brian
clean slate
3225
}
3226
3227
3228
/*
3229
  Get string of comma-separated primary key field names
3230
3231
  SYNOPSIS
3232
    char *primary_key_fields(const char *table_name)
3233
    RETURNS     pointer to allocated buffer (must be freed by caller)
3234
    table_name  quoted table name
3235
3236
  DESCRIPTION
3237
    Use SHOW KEYS FROM table_name, allocate a buffer to hold the
3238
    field names, and then build that string and return the pointer
3239
    to that buffer.
3240
3241
    Returns NULL if there is no PRIMARY or UNIQUE key on the table,
3242
    or if there is some failure.  It is better to continue to dump
3243
    the table unsorted, rather than exit without dumping the data.
3244
*/
3245
3246
static char *primary_key_fields(const char *table_name)
3247
{
206.3.1 by Patrick Galbraith
Most everything working with client rename
3248
  DRIZZLE_RES  *res= NULL;
3249
  DRIZZLE_ROW  row;
1 by brian
clean slate
3250
  /* SHOW KEYS FROM + table name * 2 (escaped) + 2 quotes + \0 */
3251
  char show_keys_buff[15 + NAME_LEN * 2 + 3];
3252
  uint result_length= 0;
3253
  char *result= 0;
3254
  char buff[NAME_LEN * 2 + 3];
3255
  char *quoted_field;
3256
77.1.18 by Monty Taylor
Removed my_vsnprintf and my_snprintf.
3257
  snprintf(show_keys_buff, sizeof(show_keys_buff),
3258
           "SHOW KEYS FROM %s", table_name);
206.3.1 by Patrick Galbraith
Most everything working with client rename
3259
  if (drizzle_query(drizzle, show_keys_buff) ||
3260
      !(res= drizzle_store_result(drizzle)))
1 by brian
clean slate
3261
  {
3262
    fprintf(stderr, "Warning: Couldn't read keys from table %s;"
3263
            " records are NOT sorted (%s)\n",
206.3.1 by Patrick Galbraith
Most everything working with client rename
3264
            table_name, drizzle_error(drizzle));
1 by brian
clean slate
3265
    /* Don't exit, because it's better to print out unsorted records */
3266
    goto cleanup;
3267
  }
3268
3269
  /*
3270
   * Figure out the length of the ORDER BY clause result.
3271
   * Note that SHOW KEYS is ordered:  a PRIMARY key is always the first
3272
   * row, and UNIQUE keys come before others.  So we only need to check
3273
   * the first key, not all keys.
3274
   */
206.3.1 by Patrick Galbraith
Most everything working with client rename
3275
  if ((row= drizzle_fetch_row(res)) && atoi(row[1]) == 0)
1 by brian
clean slate
3276
  {
3277
    /* Key is unique */
3278
    do
3279
    {
3280
      quoted_field= quote_name(row[4], buff, 0);
3281
      result_length+= strlen(quoted_field) + 1; /* + 1 for ',' or \0 */
206.3.1 by Patrick Galbraith
Most everything working with client rename
3282
    } while ((row= drizzle_fetch_row(res)) && atoi(row[3]) > 1);
1 by brian
clean slate
3283
  }
3284
3285
  /* Build the ORDER BY clause result */
3286
  if (result_length)
3287
  {
3288
    char *end;
3289
    /* result (terminating \0 is already in result_length) */
279.2.4 by Monty Taylor
Moved import, check and dump to C++... fixed errors.
3290
    result= (char *)my_malloc(result_length + 10, MYF(MY_WME));
1 by brian
clean slate
3291
    if (!result)
3292
    {
3293
      fprintf(stderr, "Error: Not enough memory to store ORDER BY clause\n");
3294
      goto cleanup;
3295
    }
206.3.1 by Patrick Galbraith
Most everything working with client rename
3296
    drizzle_data_seek(res, 0);
3297
    row= drizzle_fetch_row(res);
1 by brian
clean slate
3298
    quoted_field= quote_name(row[4], buff, 0);
266.1.21 by Monty Taylor
Removed references to strmov and strnmov
3299
    end= stpcpy(result, quoted_field);
206.3.1 by Patrick Galbraith
Most everything working with client rename
3300
    while ((row= drizzle_fetch_row(res)) && atoi(row[3]) > 1)
1 by brian
clean slate
3301
    {
3302
      quoted_field= quote_name(row[4], buff, 0);
3303
      end= strxmov(end, ",", quoted_field, NullS);
3304
    }
3305
  }
3306
3307
cleanup:
3308
  if (res)
206.3.1 by Patrick Galbraith
Most everything working with client rename
3309
    drizzle_free_result(res);
1 by brian
clean slate
3310
3311
  return result;
3312
}
3313
3314
3315
int main(int argc, char **argv)
3316
{
3317
  char bin_log_name[FN_REFLEN];
3318
  int exit_code;
3319
  MY_INIT("mysqldump");
3320
3321
  compatible_mode_normal_str[0]= 0;
206.3.1 by Patrick Galbraith
Most everything working with client rename
3322
  default_charset= (char *)drizzle_universal_client_charset;
212.6.10 by Mats Kindahl
Removing redundant use of casts in client/ for memcmp(), memcpy(), memset(), and memmove().
3323
  memset(&ignore_table, 0, sizeof(ignore_table));
1 by brian
clean slate
3324
3325
  exit_code= get_options(&argc, &argv);
3326
  if (exit_code)
3327
  {
53.2.4 by Monty Taylor
Changes so that client/ builds cleanly with no warnings.
3328
    free_resources();
1 by brian
clean slate
3329
    exit(exit_code);
3330
  }
3331
3332
  if (log_error_file)
3333
  {
3334
    if(!(stderror_file= freopen(log_error_file, "a+", stderr)))
3335
    {
53.2.4 by Monty Taylor
Changes so that client/ builds cleanly with no warnings.
3336
      free_resources();
206.3.1 by Patrick Galbraith
Most everything working with client rename
3337
      exit(EX_DRIZZLEERR);
1 by brian
clean slate
3338
    }
3339
  }
3340
3341
  if (connect_to_db(current_host, current_user, opt_password))
3342
  {
53.2.4 by Monty Taylor
Changes so that client/ builds cleanly with no warnings.
3343
    free_resources();
206.3.1 by Patrick Galbraith
Most everything working with client rename
3344
    exit(EX_DRIZZLEERR);
1 by brian
clean slate
3345
  }
3346
  if (!path)
3347
    write_header(md_result_file, *argv);
3348
206.3.1 by Patrick Galbraith
Most everything working with client rename
3349
  if (opt_slave_data && do_stop_slave_sql(drizzle))
1 by brian
clean slate
3350
    goto err;
3351
3352
  if ((opt_lock_all_tables || opt_master_data) &&
206.3.1 by Patrick Galbraith
Most everything working with client rename
3353
      do_flush_tables_read_lock(drizzle))
1 by brian
clean slate
3354
    goto err;
206.3.1 by Patrick Galbraith
Most everything working with client rename
3355
  if (opt_single_transaction && start_transaction(drizzle))
1 by brian
clean slate
3356
      goto err;
3357
  if (opt_delete_master_logs)
3358
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
3359
    if (drizzle_refresh(drizzle, REFRESH_LOG) ||
3360
        get_bin_log_name(drizzle, bin_log_name, sizeof(bin_log_name)))
1 by brian
clean slate
3361
      goto err;
3362
    flush_logs= 0;
3363
  }
3364
  if (opt_lock_all_tables || opt_master_data)
3365
  {
206.3.1 by Patrick Galbraith
Most everything working with client rename
3366
    if (flush_logs && drizzle_refresh(drizzle, REFRESH_LOG))
1 by brian
clean slate
3367
      goto err;
3368
    flush_logs= 0; /* not anymore; that would not be sensible */
3369
  }
3370
  /* Add 'STOP SLAVE to beginning of dump */
3371
  if (opt_slave_apply && add_stop_slave())
3372
    goto err;
206.3.1 by Patrick Galbraith
Most everything working with client rename
3373
  if (opt_master_data && do_show_master_status(drizzle))
3374
    goto err;
3375
  if (opt_slave_data && do_show_slave_status(drizzle))
3376
    goto err;
3377
  if (opt_single_transaction && do_unlock_tables(drizzle)) /* unlock but no commit! */
1 by brian
clean slate
3378
    goto err;
3379
3380
  if (opt_alldbs)
3381
  {
3382
    dump_all_databases();
3383
  }
3384
  else if (argc > 1 && !opt_databases)
3385
  {
3386
    /* Only one database and selected table(s) */
3387
    dump_selected_tables(*argv, (argv + 1), (argc - 1));
3388
  }
3389
  else
3390
  {
3391
    dump_databases(argv);
3392
  }
3393
3394
  /* if --dump-slave , start the slave sql thread */
206.3.1 by Patrick Galbraith
Most everything working with client rename
3395
  if (opt_slave_data && do_start_slave_sql(drizzle))
1 by brian
clean slate
3396
    goto err;
3397
3398
  /* add 'START SLAVE' to end of dump */
3399
  if (opt_slave_apply && add_slave_statements())
3400
    goto err;
3401
3402
  /* ensure dumped data flushed */
3403
  if (md_result_file && fflush(md_result_file))
3404
  {
3405
    if (!first_error)
206.3.1 by Patrick Galbraith
Most everything working with client rename
3406
      first_error= EX_DRIZZLEERR;
1 by brian
clean slate
3407
    goto err;
3408
  }
3409
  /* everything successful, purge the old logs files */
206.3.1 by Patrick Galbraith
Most everything working with client rename
3410
  if (opt_delete_master_logs && purge_bin_logs_to(drizzle, bin_log_name))
1 by brian
clean slate
3411
    goto err;
3412
3413
  /*
3414
    No reason to explicitely COMMIT the transaction, neither to explicitely
3415
    UNLOCK TABLES: these will be automatically be done by the server when we
3416
    disconnect now. Saves some code here, some network trips, adds nothing to
3417
    server.
3418
  */
3419
err:
3420
  dbDisconnect(current_host);
3421
  if (!path)
3422
    write_footer(md_result_file);
3423
  free_resources();
3424
3425
  if (stderror_file)
3426
    fclose(stderror_file);
3427
3428
  return(first_error);
3429
} /* main */