00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00043 #include <libdrizzle/common.h>
00044
00054 static const char *_verbose_name[DRIZZLE_VERBOSE_MAX]=
00055 {
00056 "NEVER",
00057 "FATAL",
00058 "ERROR",
00059 "INFO",
00060 "DEBUG",
00061 "CRAZY"
00062 };
00063
00066
00067
00068
00069
00070 const char *drizzle_version(void)
00071 {
00072 return PACKAGE_VERSION;
00073 }
00074
00075 const char *drizzle_bugreport(void)
00076 {
00077 return PACKAGE_BUGREPORT;
00078 }
00079
00080 const char *drizzle_verbose_name(drizzle_verbose_t verbose)
00081 {
00082 if (verbose >= DRIZZLE_VERBOSE_MAX)
00083 {
00084 return "UNKNOWN";
00085 }
00086
00087 return _verbose_name[verbose];
00088 }
00089
00090 drizzle_st *drizzle_create(drizzle_st *drizzle)
00091 {
00092 #if defined(_WIN32)
00093
00094 WSADATA wsaData;
00095 if ( WSAStartup( MAKEWORD(2,2), &wsaData ) != 0 )
00096 printf("Error at WSAStartup()\n");
00097 #else
00098 struct sigaction act;
00099 memset(&act, 0, sizeof(act));
00100
00101 act.sa_handler = SIG_IGN;
00102 sigaction(SIGPIPE, &act, NULL);
00103 #endif
00104
00105 if (drizzle == NULL)
00106 {
00107 drizzle= new (std::nothrow) drizzle_st;
00108 if (drizzle == NULL)
00109 {
00110 return NULL;
00111 }
00112
00113 drizzle->options= DRIZZLE_ALLOCATED;
00114 }
00115 else
00116 {
00117 drizzle->options= DRIZZLE_NONE;
00118 }
00119
00120
00121 drizzle->options|= DRIZZLE_FREE_OBJECTS;
00122 drizzle->error_code= 0;
00123
00124 drizzle->verbose= DRIZZLE_VERBOSE_NEVER;
00125 drizzle->con_count= 0;
00126 drizzle->pfds_size= 0;
00127 drizzle->query_count= 0;
00128 drizzle->query_new= 0;
00129 drizzle->query_running= 0;
00130 drizzle->last_errno= 0;
00131 drizzle->timeout= -1;
00132 drizzle->con_list= NULL;
00133 drizzle->context= NULL;
00134 drizzle->context_free_fn= NULL;
00135 drizzle->event_watch_fn= NULL;
00136 drizzle->event_watch_context= NULL;
00137 drizzle->log_fn= NULL;
00138 drizzle->log_context= NULL;
00139 drizzle->pfds= NULL;
00140 drizzle->query_list= NULL;
00141 drizzle->sqlstate[0]= 0;
00142 drizzle->last_error[0]= 0;
00143
00144 return drizzle;
00145 }
00146
00147 drizzle_st *drizzle_clone(drizzle_st *drizzle, const drizzle_st *from)
00148 {
00149 drizzle= drizzle_create(drizzle);
00150 if (drizzle == NULL)
00151 {
00152 return NULL;
00153 }
00154
00155 drizzle->options|= (from->options & int(~DRIZZLE_ALLOCATED));
00156
00157 for (drizzle_con_st *con= from->con_list; con != NULL; con= con->next)
00158 {
00159 if (drizzle_con_clone(drizzle, NULL, con) == NULL)
00160 {
00161 drizzle_free(drizzle);
00162 return NULL;
00163 }
00164 }
00165
00166 return drizzle;
00167 }
00168
00169 void drizzle_free(drizzle_st *drizzle)
00170 {
00171 if (drizzle == NULL)
00172 {
00173 return;
00174 }
00175
00176 if (drizzle->context != NULL && drizzle->context_free_fn != NULL)
00177 {
00178 drizzle->context_free_fn(drizzle, drizzle->context);
00179 }
00180
00181 if (drizzle->options & DRIZZLE_FREE_OBJECTS)
00182 {
00183 drizzle_con_free_all(drizzle);
00184 drizzle_query_free_all(drizzle);
00185 }
00186 else if (drizzle->options & DRIZZLE_ASSERT_DANGLING)
00187 {
00188 assert(drizzle->con_list == NULL);
00189 assert(drizzle->query_list == NULL);
00190 }
00191
00192 free(drizzle->pfds);
00193
00194 if (drizzle->options & DRIZZLE_ALLOCATED)
00195 {
00196 delete drizzle;
00197 }
00198 #if defined(_WIN32)
00199
00200 WSACleanup();
00201 #endif
00202 }
00203
00204 const char *drizzle_error(const drizzle_st *drizzle)
00205 {
00206 if (drizzle == NULL)
00207 {
00208 return NULL;
00209 }
00210
00211 return (const char *)drizzle->last_error;
00212 }
00213
00214 int drizzle_errno(const drizzle_st *drizzle)
00215 {
00216 if (drizzle == NULL)
00217 {
00218 return 0;
00219 }
00220
00221 return drizzle->last_errno;
00222 }
00223
00224 uint16_t drizzle_error_code(const drizzle_st *drizzle)
00225 {
00226 if (drizzle == NULL)
00227 {
00228 return 0;
00229 }
00230
00231 return drizzle->error_code;
00232 }
00233
00234 const char *drizzle_sqlstate(const drizzle_st *drizzle)
00235 {
00236 if (drizzle == NULL)
00237 {
00238 return NULL;
00239 }
00240
00241 return drizzle->sqlstate;
00242 }
00243
00244 drizzle_options_t drizzle_options(const drizzle_st *drizzle)
00245 {
00246 if (drizzle == NULL)
00247 {
00248 return drizzle_options_t();
00249 }
00250
00251 return drizzle_options_t(drizzle->options);
00252 }
00253
00254 void drizzle_set_options(drizzle_st *drizzle, drizzle_options_t options)
00255 {
00256 if (drizzle == NULL)
00257 {
00258 return;
00259 }
00260
00261 drizzle->options= options;
00262 }
00263
00264 void drizzle_add_options(drizzle_st *drizzle, drizzle_options_t options)
00265 {
00266 if (drizzle == NULL)
00267 {
00268 return;
00269 }
00270
00271 drizzle->options|= options;
00272 }
00273
00274 void drizzle_remove_options(drizzle_st *drizzle, drizzle_options_t options)
00275 {
00276 if (drizzle == NULL)
00277 {
00278 return;
00279 }
00280
00281 drizzle->options&= ~options;
00282 }
00283
00284 void *drizzle_context(const drizzle_st *drizzle)
00285 {
00286 if (drizzle == NULL)
00287 {
00288 return NULL;
00289 }
00290
00291 return drizzle->context;
00292 }
00293
00294 void drizzle_set_context(drizzle_st *drizzle, void *context)
00295 {
00296 if (drizzle == NULL)
00297 {
00298 return;
00299 }
00300
00301 drizzle->context= context;
00302 }
00303
00304 void drizzle_set_context_free_fn(drizzle_st *drizzle,
00305 drizzle_context_free_fn *function)
00306 {
00307 if (drizzle == NULL)
00308 {
00309 return;
00310 }
00311
00312 drizzle->context_free_fn= function;
00313 }
00314
00315 int drizzle_timeout(const drizzle_st *drizzle)
00316 {
00317 if (drizzle == NULL)
00318 {
00319 return -1;
00320 }
00321
00322 return drizzle->timeout;
00323 }
00324
00325 void drizzle_set_timeout(drizzle_st *drizzle, int timeout)
00326 {
00327 if (drizzle == NULL)
00328 {
00329 return;
00330 }
00331
00332 drizzle->timeout= timeout;
00333 }
00334
00335 drizzle_verbose_t drizzle_verbose(const drizzle_st *drizzle)
00336 {
00337 if (drizzle == NULL)
00338 {
00339 return drizzle_verbose_t();
00340 }
00341
00342 return drizzle->verbose;
00343 }
00344
00345 void drizzle_set_verbose(drizzle_st *drizzle, drizzle_verbose_t verbose)
00346 {
00347 if (drizzle == NULL)
00348 {
00349 return;
00350 }
00351
00352 drizzle->verbose= verbose;
00353 }
00354
00355 void drizzle_set_log_fn(drizzle_st *drizzle, drizzle_log_fn *function,
00356 void *context)
00357 {
00358 if (drizzle == NULL)
00359 {
00360 return;
00361 }
00362
00363 drizzle->log_fn= function;
00364 drizzle->log_context= context;
00365 }
00366
00367 void drizzle_set_event_watch_fn(drizzle_st *drizzle,
00368 drizzle_event_watch_fn *function,
00369 void *context)
00370 {
00371 if (drizzle == NULL)
00372 {
00373 return;
00374 }
00375
00376 drizzle->event_watch_fn= function;
00377 drizzle->event_watch_context= context;
00378 }
00379
00380 drizzle_con_st *drizzle_con_create(drizzle_st *drizzle, drizzle_con_st *con)
00381 {
00382 if (drizzle == NULL)
00383 {
00384 return NULL;
00385 }
00386
00387 if (con == NULL)
00388 {
00389 con= new (std::nothrow) drizzle_con_st;
00390 if (con == NULL)
00391 {
00392 if (drizzle != NULL)
00393 {
00394 drizzle_set_error(drizzle, __func__, "Failed to allocate.");
00395 }
00396
00397 return NULL;
00398 }
00399
00400 con->options= DRIZZLE_CON_ALLOCATED;
00401 }
00402 else
00403 {
00404 con->options= 0;
00405 }
00406
00407 if (drizzle->con_list != NULL)
00408 {
00409 drizzle->con_list->prev= con;
00410 }
00411 con->next= drizzle->con_list;
00412 con->prev= NULL;
00413 drizzle->con_list= con;
00414 drizzle->con_count++;
00415
00416 con->packet_number= 0;
00417 con->protocol_version= 0;
00418 con->state_current= 0;
00419 con->events= 0;
00420 con->revents= 0;
00421 con->capabilities= DRIZZLE_CAPABILITIES_NONE;
00422 con->charset= 0;
00423 con->command= drizzle_command_t();
00424 con->options|= DRIZZLE_CON_MYSQL;
00425 con->socket_type= DRIZZLE_CON_SOCKET_TCP;
00426 con->status= DRIZZLE_CON_STATUS_NONE;
00427 con->max_packet_size= DRIZZLE_MAX_PACKET_SIZE;
00428 con->result_count= 0;
00429 con->thread_id= 0;
00430 con->backlog= DRIZZLE_DEFAULT_BACKLOG;
00431 con->fd= -1;
00432 con->buffer_size= 0;
00433 con->command_offset= 0;
00434 con->command_size= 0;
00435 con->command_total= 0;
00436 con->packet_size= 0;
00437 con->addrinfo_next= NULL;
00438 con->buffer_ptr= con->buffer;
00439 con->command_buffer= NULL;
00440 con->command_data= NULL;
00441 con->context= NULL;
00442 con->context_free_fn= NULL;
00443 con->drizzle= drizzle;
00444
00445
00446 con->query= NULL;
00447
00448 con->result_list= NULL;
00449 con->scramble= NULL;
00450 con->socket.tcp.addrinfo= NULL;
00451 con->socket.tcp.host= NULL;
00452 con->socket.tcp.port= 0;
00453
00454 con->db[0]= 0;
00455 con->password[0]= 0;
00456
00457 con->server_version[0]= 0;
00458
00459 con->user[0]= 0;
00460
00461 return con;
00462 }
00463
00464 drizzle_con_st *drizzle_con_clone(drizzle_st *drizzle, drizzle_con_st *con,
00465 const drizzle_con_st *from)
00466 {
00467 if (drizzle == NULL)
00468 {
00469 return NULL;
00470 }
00471
00472 con= drizzle_con_create(drizzle, con);
00473 if (con == NULL)
00474 {
00475 return NULL;
00476 }
00477
00478
00479 con->options|= (from->options & int(~(
00480 DRIZZLE_CON_ALLOCATED|DRIZZLE_CON_READY|
00481 DRIZZLE_CON_NO_RESULT_READ|DRIZZLE_CON_IO_READY|
00482 DRIZZLE_CON_LISTEN)));
00483 con->backlog= from->backlog;
00484 strcpy(con->db, from->db);
00485 strcpy(con->password, from->password);
00486 strcpy(con->user, from->user);
00487
00488 switch (from->socket_type)
00489 {
00490 case DRIZZLE_CON_SOCKET_TCP:
00491 drizzle_con_set_tcp(con, from->socket.tcp.host, from->socket.tcp.port);
00492 break;
00493
00494 case DRIZZLE_CON_SOCKET_UDS:
00495 drizzle_con_set_uds(con, from->socket.uds.sockaddr.sun_path);
00496 break;
00497
00498 default:
00499 break;
00500 }
00501
00502 return con;
00503 }
00504
00505 void drizzle_con_free(drizzle_con_st *con)
00506 {
00507 if (con == NULL)
00508 {
00509 return;
00510 }
00511
00512 if (con->context != NULL and con->context_free_fn != NULL)
00513 {
00514 con->context_free_fn(con, con->context);
00515 }
00516
00517 if (con->drizzle->options & DRIZZLE_FREE_OBJECTS)
00518 {
00519 drizzle_result_free_all(con);
00520 }
00521 else if (con->drizzle->options & DRIZZLE_ASSERT_DANGLING)
00522 {
00523 assert(con->result_list == NULL);
00524 }
00525
00526 if (con->fd != -1)
00527 {
00528 drizzle_con_close(con);
00529 }
00530
00531 drizzle_con_reset_addrinfo(con);
00532
00533 if (con->drizzle->con_list == con)
00534 con->drizzle->con_list= con->next;
00535
00536 if (con->prev != NULL)
00537 con->prev->next= con->next;
00538
00539 if (con->next != NULL)
00540 con->next->prev= con->prev;
00541
00542 con->drizzle->con_count--;
00543
00544 if (con->options & DRIZZLE_CON_ALLOCATED)
00545 {
00546 delete con;
00547 }
00548 }
00549
00550 void drizzle_con_free_all(drizzle_st *drizzle)
00551 {
00552 while (drizzle->con_list != NULL)
00553 drizzle_con_free(drizzle->con_list);
00554 }
00555
00556 drizzle_return_t drizzle_con_wait(drizzle_st *drizzle)
00557 {
00558 if (drizzle == NULL)
00559 {
00560 return DRIZZLE_RETURN_INVALID_ARGUMENT;
00561 }
00562
00563 struct pollfd *pfds;
00564 if (drizzle->pfds_size < drizzle->con_count)
00565 {
00566 pfds= (struct pollfd *)realloc(drizzle->pfds, drizzle->con_count * sizeof(struct pollfd));
00567 if (pfds == NULL)
00568 {
00569 drizzle_set_error(drizzle, __func__, "Failed to realloc file descriptors.");
00570 return DRIZZLE_RETURN_MEMORY;
00571 }
00572
00573 drizzle->pfds= pfds;
00574 drizzle->pfds_size= drizzle->con_count;
00575 }
00576 else
00577 {
00578 pfds= drizzle->pfds;
00579 }
00580
00581 uint32_t x= 0;
00582 for (drizzle_con_st *con= drizzle->con_list; con != NULL; con= con->next)
00583 {
00584 if (con->events == 0)
00585 {
00586 continue;
00587 }
00588
00589 pfds[x].fd= con->fd;
00590 pfds[x].events= con->events;
00591 pfds[x].revents= 0;
00592 x++;
00593 }
00594
00595 if (x == 0)
00596 {
00597 drizzle_set_error(drizzle, __func__, "no active file descriptors");
00598 return DRIZZLE_RETURN_NO_ACTIVE_CONNECTIONS;
00599 }
00600
00601 int ret;
00602 while (1)
00603 {
00604 drizzle_log_crazy(drizzle, "poll count=%d timeout=%d", x,
00605 drizzle->timeout);
00606
00607 ret= poll(pfds, x, drizzle->timeout);
00608
00609 drizzle_log_crazy(drizzle, "poll return=%d errno=%d", ret, errno);
00610
00611 if (ret == -1)
00612 {
00613 if (errno == EINTR)
00614 {
00615 continue;
00616 }
00617
00618 drizzle_set_error(drizzle, "drizzle_con_wait", "poll:%d", errno);
00619 drizzle->last_errno= errno;
00620 return DRIZZLE_RETURN_ERRNO;
00621 }
00622
00623 break;
00624 }
00625
00626 if (ret == 0)
00627 {
00628 drizzle_set_error(drizzle, "drizzle_con_wait", "timeout reached");
00629 return DRIZZLE_RETURN_TIMEOUT;
00630 }
00631
00632 x= 0;
00633 for (drizzle_con_st *con= drizzle->con_list; con != NULL; con= con->next)
00634 {
00635 if (con->events == 0)
00636 {
00637 continue;
00638 }
00639
00640 drizzle_return_t dret= drizzle_con_set_revents(con, pfds[x].revents);
00641 if (dret != DRIZZLE_RETURN_OK)
00642 {
00643 return dret;
00644 }
00645
00646 x++;
00647 }
00648
00649 return DRIZZLE_RETURN_OK;
00650 }
00651
00652 drizzle_con_st *drizzle_con_ready(drizzle_st *drizzle)
00653 {
00654 if (drizzle == NULL)
00655 {
00656 return NULL;
00657 }
00658
00659
00660
00661
00662 for (drizzle_con_st *con= drizzle->con_list; con != NULL; con= con->next)
00663 {
00664 if (con->options & DRIZZLE_CON_IO_READY)
00665 {
00666 con->options&= int(~DRIZZLE_CON_IO_READY);
00667 return con;
00668 }
00669 }
00670
00671 return NULL;
00672 }
00673
00674 drizzle_con_st *drizzle_con_ready_listen(drizzle_st *drizzle)
00675 {
00676 if (drizzle == NULL)
00677 {
00678 return NULL;
00679 }
00680
00681
00682
00683
00684 for (drizzle_con_st *con= drizzle->con_list; con != NULL; con= con->next)
00685 {
00686 if ((con->options & (DRIZZLE_CON_IO_READY | DRIZZLE_CON_LISTEN)) ==
00687 (DRIZZLE_CON_IO_READY | DRIZZLE_CON_LISTEN))
00688 {
00689 con->options&= int(~DRIZZLE_CON_IO_READY);
00690 return con;
00691 }
00692 }
00693
00694 return NULL;
00695 }
00696
00697
00698
00699
00700
00701 drizzle_con_st *drizzle_con_add_tcp(drizzle_st *drizzle, drizzle_con_st *con,
00702 const char *host, in_port_t port,
00703 const char *user, const char *password,
00704 const char *db,
00705 drizzle_con_options_t options)
00706 {
00707 if (drizzle == NULL)
00708 {
00709 return NULL;
00710 }
00711
00712 con= drizzle_con_create(drizzle, con);
00713 if (con == NULL)
00714 {
00715 return NULL;
00716 }
00717
00718 drizzle_con_set_tcp(con, host, port);
00719 drizzle_con_set_auth(con, user, password);
00720 drizzle_con_set_db(con, db);
00721 drizzle_con_add_options(con, options);
00722
00723 return con;
00724 }
00725
00726 drizzle_con_st *drizzle_con_add_uds(drizzle_st *drizzle, drizzle_con_st *con,
00727 const char *uds, const char *user,
00728 const char *password, const char *db,
00729 drizzle_con_options_t options)
00730 {
00731 if (drizzle == NULL)
00732 {
00733 return NULL;
00734 }
00735
00736 con= drizzle_con_create(drizzle, con);
00737 if (con == NULL)
00738 {
00739 return NULL;
00740 }
00741
00742 drizzle_con_set_uds(con, uds);
00743 drizzle_con_set_auth(con, user, password);
00744 drizzle_con_set_db(con, db);
00745 drizzle_con_add_options(con, options);
00746
00747 return con;
00748 }
00749
00750
00751
00752
00753
00754 drizzle_con_st *drizzle_con_add_tcp_listen(drizzle_st *drizzle,
00755 drizzle_con_st *con,
00756 const char *host, in_port_t port,
00757 int backlog,
00758 drizzle_con_options_t options)
00759 {
00760 if (drizzle == NULL)
00761 {
00762 return NULL;
00763 }
00764
00765 con= drizzle_con_create(drizzle, con);
00766 if (con == NULL)
00767 {
00768 return NULL;
00769 }
00770
00771 drizzle_con_set_tcp(con, host, port);
00772 drizzle_con_set_backlog(con, backlog);
00773 drizzle_con_add_options(con, drizzle_con_options_t(DRIZZLE_CON_LISTEN | int(options)));
00774
00775 return con;
00776 }
00777
00778 drizzle_con_st *drizzle_con_add_uds_listen(drizzle_st *drizzle,
00779 drizzle_con_st *con,
00780 const char *uds, int backlog,
00781 drizzle_con_options_t options)
00782 {
00783 if (drizzle == NULL)
00784 {
00785 return NULL;
00786 }
00787
00788 con= drizzle_con_create(drizzle, con);
00789 if (con == NULL)
00790 {
00791 return NULL;
00792 }
00793
00794 drizzle_con_set_uds(con, uds);
00795 drizzle_con_set_backlog(con, backlog);
00796 drizzle_con_add_options(con, drizzle_con_options_t(DRIZZLE_CON_LISTEN | int(options)));
00797
00798 return con;
00799 }
00800
00801 drizzle_con_st *drizzle_con_accept(drizzle_st *drizzle, drizzle_con_st *con,
00802 drizzle_return_t *ret_ptr)
00803 {
00804 drizzle_return_t unused_ret;
00805 if (ret_ptr == NULL)
00806 {
00807 ret_ptr= &unused_ret;
00808 }
00809
00810 if (drizzle == NULL)
00811 {
00812 return NULL;
00813 }
00814
00815 while (1)
00816 {
00817 drizzle_con_st *ready;
00818
00819 if ((ready= drizzle_con_ready_listen(drizzle)) != NULL)
00820 {
00821 int fd= accept(ready->fd, NULL, NULL);
00822
00823 con= drizzle_con_create(drizzle, con);
00824 if (con == NULL)
00825 {
00826 (void)closesocket(fd);
00827 *ret_ptr= DRIZZLE_RETURN_MEMORY;
00828 return NULL;
00829 }
00830
00831 *ret_ptr= drizzle_con_set_fd(con, fd);
00832 if (*ret_ptr != DRIZZLE_RETURN_OK)
00833 {
00834 (void)closesocket(fd);
00835 return NULL;
00836 }
00837
00838 if (ready->options & DRIZZLE_CON_MYSQL)
00839 drizzle_con_add_options(con, DRIZZLE_CON_MYSQL);
00840
00841 *ret_ptr= DRIZZLE_RETURN_OK;
00842 return con;
00843 }
00844
00845 if (drizzle->options & DRIZZLE_NON_BLOCKING)
00846 {
00847 *ret_ptr= DRIZZLE_RETURN_IO_WAIT;
00848 return NULL;
00849 }
00850
00851 for (ready= drizzle->con_list; ready != NULL; ready= ready->next)
00852 {
00853 if (ready->options & DRIZZLE_CON_LISTEN)
00854 drizzle_con_set_events(ready, POLLIN);
00855 }
00856
00857 *ret_ptr= drizzle_con_wait(drizzle);
00858 if (*ret_ptr != DRIZZLE_RETURN_OK)
00859 return NULL;
00860 }
00861 }
00862
00863
00864
00865
00866
00867 void drizzle_set_error(drizzle_st *drizzle, const char *function,
00868 const char *format, ...)
00869 {
00870 if (drizzle == NULL)
00871 {
00872 return;
00873 }
00874
00875 size_t size;
00876 int written;
00877 char log_buffer[DRIZZLE_MAX_ERROR_SIZE];
00878 va_list args;
00879
00880 size= strlen(function);
00881 char *ptr= (char *)memcpy(log_buffer, function, size);
00882 ptr+= size;
00883 ptr[0]= ':';
00884 size++;
00885 ptr++;
00886
00887 va_start(args, format);
00888 written= vsnprintf(ptr, DRIZZLE_MAX_ERROR_SIZE - size, format, args);
00889 va_end(args);
00890
00891 if (written < 0)
00892 {
00893 size= DRIZZLE_MAX_ERROR_SIZE;
00894 }
00895 else
00896 {
00897 size+= written;
00898 }
00899
00900 if (size >= DRIZZLE_MAX_ERROR_SIZE)
00901 {
00902 size= DRIZZLE_MAX_ERROR_SIZE - 1;
00903 }
00904 log_buffer[size]= 0;
00905
00906 if (drizzle->log_fn == NULL)
00907 {
00908 memcpy(drizzle->last_error, log_buffer, size + 1);
00909 }
00910 else
00911 {
00912 drizzle->log_fn(log_buffer, DRIZZLE_VERBOSE_ERROR, drizzle->log_context);
00913 }
00914 }
00915
00916 void drizzle_log(drizzle_st *drizzle, drizzle_verbose_t verbose,
00917 const char *format, va_list args)
00918 {
00919 if (drizzle == NULL)
00920 {
00921 return;
00922 }
00923
00924 char log_buffer[DRIZZLE_MAX_ERROR_SIZE];
00925
00926 if (drizzle->log_fn == NULL)
00927 {
00928 printf("%5s: ", drizzle_verbose_name(verbose));
00929 vprintf(format, args);
00930 printf("\n");
00931 }
00932 else
00933 {
00934 vsnprintf(log_buffer, DRIZZLE_MAX_ERROR_SIZE, format, args);
00935 log_buffer[DRIZZLE_MAX_ERROR_SIZE-1]= 0;
00936 drizzle->log_fn(log_buffer, verbose, drizzle->log_context);
00937 }
00938 }