2
* Drizzle Client & Protocol Library
4
* Copyright (C) 2008 Eric Day (eday@oddments.org)
7
* Use and distribution licensed under the BSD license. See
8
* the COPYING file in this directory for full text.
13
* @brief Query definitions
18
drizzle_result_st *drizzle_query(drizzle_con_st *con, drizzle_result_st *result,
19
const char *query, size_t size,
20
drizzle_return_t *ret_ptr)
22
return drizzle_con_command_write(con, result, DRIZZLE_COMMAND_QUERY,
23
(uint8_t *)query, size, size, ret_ptr);
26
drizzle_result_st *drizzle_query_str(drizzle_con_st *con,
27
drizzle_result_st *result,
29
drizzle_return_t *ret_ptr)
35
return drizzle_con_command_write(con, result, DRIZZLE_COMMAND_QUERY,
36
(uint8_t *)query, size, size, ret_ptr);
39
drizzle_result_st *drizzle_query_inc(drizzle_con_st *con,
40
drizzle_result_st *result,
41
const char *query, size_t size,
42
size_t total, drizzle_return_t *ret_ptr)
44
return drizzle_con_command_write(con, result, DRIZZLE_COMMAND_QUERY,
45
(uint8_t *)query, size, total, ret_ptr);
48
drizzle_query_st *drizzle_query_add(drizzle_st *drizzle,
49
drizzle_query_st *query,
51
drizzle_result_st *result,
52
const char *query_string, size_t size,
53
drizzle_query_options_t options,
56
query= drizzle_query_create(drizzle, query);
60
drizzle_query_set_con(query, con);
61
drizzle_query_set_result(query, result);
62
drizzle_query_set_string(query, query_string, size);
63
drizzle_query_add_options(query, options);
64
drizzle_query_set_context(query, context);
69
drizzle_query_st *drizzle_query_create(drizzle_st *drizzle,
70
drizzle_query_st *query)
74
query= malloc(sizeof(drizzle_query_st));
77
drizzle_set_error(drizzle, "drizzle_query_create", "malloc");
81
memset(query, 0, sizeof(drizzle_query_st));
82
query->options|= DRIZZLE_CON_ALLOCATED;
85
memset(query, 0, sizeof(drizzle_query_st));
87
query->drizzle= drizzle;
89
if (drizzle->query_list)
90
drizzle->query_list->prev= query;
91
query->next= drizzle->query_list;
92
drizzle->query_list= query;
93
drizzle->query_count++;
99
void drizzle_query_free(drizzle_query_st *query)
101
if (query->context != NULL && query->context_free_fn != NULL)
102
query->context_free_fn(query, query->context);
104
if (query->drizzle->query_list == query)
105
query->drizzle->query_list= query->next;
107
query->prev->next= query->next;
109
query->next->prev= query->prev;
110
query->drizzle->query_count--;
112
if (query->options & DRIZZLE_QUERY_ALLOCATED)
116
void drizzle_query_free_all(drizzle_st *drizzle)
118
while (drizzle->query_list != NULL)
119
drizzle_query_free(drizzle->query_list);
122
drizzle_con_st *drizzle_query_con(drizzle_query_st *query)
127
void drizzle_query_set_con(drizzle_query_st *query, drizzle_con_st *con)
132
drizzle_result_st *drizzle_query_result(drizzle_query_st *query)
134
return query->result;
137
void drizzle_query_set_result(drizzle_query_st *query,
138
drizzle_result_st *result)
140
query->result= result;
143
char *drizzle_query_string(drizzle_query_st *query, size_t *size)
146
return (char *)(query->string);
149
void drizzle_query_set_string(drizzle_query_st *query, const char *string,
152
query->string= string;
156
drizzle_query_options_t drizzle_query_options(drizzle_query_st *query)
158
return query->options;
161
void drizzle_query_set_options(drizzle_query_st *query,
162
drizzle_query_options_t options)
164
query->options= options;
167
void drizzle_query_add_options(drizzle_query_st *query,
168
drizzle_query_options_t options)
170
query->options|= options;
173
void drizzle_query_remove_options(drizzle_query_st *query,
174
drizzle_query_options_t options)
176
query->options&= ~options;
179
void *drizzle_query_context(drizzle_query_st *query)
181
return query->context;
184
void drizzle_query_set_context(drizzle_query_st *query, void *context)
186
query->context= context;
189
void drizzle_query_set_context_free_fn(drizzle_query_st *query,
190
drizzle_query_context_free_fn *function)
192
query->context_free_fn= function;
195
static void drizzle_query_run_state(drizzle_query_st* query,
196
drizzle_return_t* ret_ptr)
198
switch (query->state)
200
case DRIZZLE_QUERY_STATE_INIT:
201
query->state= DRIZZLE_QUERY_STATE_QUERY;
202
case DRIZZLE_QUERY_STATE_QUERY:
203
query->result= drizzle_query(query->con, query->result, query->string,
204
query->size, ret_ptr);
205
if (*ret_ptr == DRIZZLE_RETURN_IO_WAIT)
209
else if (*ret_ptr != DRIZZLE_RETURN_OK)
211
query->state= DRIZZLE_QUERY_STATE_DONE;
215
query->state= DRIZZLE_QUERY_STATE_RESULT;
217
case DRIZZLE_QUERY_STATE_RESULT:
218
*ret_ptr= drizzle_result_buffer(query->result);
219
if (*ret_ptr == DRIZZLE_RETURN_IO_WAIT)
224
query->state= DRIZZLE_QUERY_STATE_DONE;
228
case DRIZZLE_QUERY_STATE_DONE:
233
drizzle_query_st *drizzle_query_run(drizzle_st *drizzle,
234
drizzle_return_t *ret_ptr)
236
drizzle_options_t options;
237
drizzle_query_st *query;
240
if (drizzle->query_new == 0 && drizzle->query_running == 0)
242
*ret_ptr= DRIZZLE_RETURN_OK;
246
options= drizzle->options;
247
drizzle->options|= DRIZZLE_NON_BLOCKING;
249
/* Check to see if any queries need to be started. */
250
if (drizzle->query_new > 0)
252
for (query= drizzle->query_list; query != NULL; query= query->next)
254
if (query->state != DRIZZLE_QUERY_STATE_INIT)
257
drizzle->query_new--;
258
drizzle->query_running++;
259
assert(query->con->query == NULL);
260
query->con->query= query;
262
drizzle_query_run_state(query, ret_ptr);
263
if (*ret_ptr != DRIZZLE_RETURN_IO_WAIT)
265
assert(query->state == DRIZZLE_QUERY_STATE_DONE);
266
drizzle->query_running--;
267
drizzle->options= options;
268
query->con->query= NULL;
269
if (*ret_ptr == DRIZZLE_RETURN_ERROR_CODE || *ret_ptr == DRIZZLE_RETURN_OK)
276
assert(drizzle->query_new == 0);
281
/* Loop through each active connection. */
282
while ((con= drizzle_con_ready(drizzle)) != NULL)
285
drizzle_query_run_state(query, ret_ptr);
286
if (query->state == DRIZZLE_QUERY_STATE_DONE)
288
drizzle->query_running--;
289
drizzle->options= options;
293
assert(*ret_ptr == DRIZZLE_RETURN_IO_WAIT);
296
if (options & DRIZZLE_NON_BLOCKING)
298
*ret_ptr= DRIZZLE_RETURN_IO_WAIT;
302
*ret_ptr= drizzle_con_wait(drizzle);
303
if (*ret_ptr != DRIZZLE_RETURN_OK)
305
drizzle->options= options;
311
drizzle_return_t drizzle_query_run_all(drizzle_st *drizzle)
313
drizzle_return_t ret;
315
while (drizzle->query_new > 0 || drizzle->query_running > 0)
317
(void)drizzle_query_run(drizzle, &ret);
318
if (ret != DRIZZLE_RETURN_OK && ret != DRIZZLE_RETURN_ERROR_CODE)
322
return DRIZZLE_RETURN_OK;
325
size_t drizzle_escape_string(char *to, const char *from, size_t from_size)
329
while (from_size > 0)
331
/* All multi-byte UTF8 characters have the high bit set for all bytes. */
360
size_t drizzle_hex_string(char *to, const char *from, size_t from_size)
362
static const char hex_map[]= "0123456789ABCDEF";
363
const char *from_end;
365
for (from_end= from + from_size; from != from_end; from++)
367
*to++= hex_map[((unsigned char) *from) >> 4];
368
*to++= hex_map[((unsigned char) *from) & 0xF];
373
return from_size * 2;
376
void drizzle_mysql_password_hash(char *to, const char *from, size_t from_size)
379
uint8_t hash_tmp1[SHA1_DIGEST_LENGTH];
380
uint8_t hash_tmp2[SHA1_DIGEST_LENGTH];
383
SHA1Update(&ctx, (const uint8_t*)from, from_size);
384
SHA1Final(hash_tmp1, &ctx);
387
SHA1Update(&ctx, hash_tmp1, SHA1_DIGEST_LENGTH);
388
SHA1Final(hash_tmp2, &ctx);
390
(void)drizzle_hex_string(to, (char*)hash_tmp2, SHA1_DIGEST_LENGTH);