void fiber_io_check(void) { if (__thread_fiber != NULL) return; acl_assert(acl_pthread_once(&__once_control, thread_init) == 0); __maxfd = acl_open_limit(0); if (__maxfd <= 0) __maxfd = MAXFD; __thread_fiber = (FIBER_TLS *) acl_mymalloc(sizeof(FIBER_TLS)); __thread_fiber->event = event_create(__maxfd); __thread_fiber->io_fibers = (ACL_FIBER **) acl_mycalloc(__maxfd, sizeof(ACL_FIBER *)); __thread_fiber->ev_fiber = acl_fiber_create(fiber_io_loop, __thread_fiber->event, STACK_SIZE); __thread_fiber->io_count = 0; __thread_fiber->nsleeping = 0; __thread_fiber->io_stop = 0; acl_ring_init(&__thread_fiber->ev_timer); if ((unsigned long) acl_pthread_self() == acl_main_thread_self()) { __main_fiber = __thread_fiber; atexit(fiber_io_main_free); } else if (acl_pthread_setspecific(__fiber_key, __thread_fiber) != 0) acl_msg_fatal("acl_pthread_setspecific error!"); }
db_mysql::db_mysql(const char* dbaddr, const char* dbname, const char* dbuser, const char* dbpass, unsigned long dbflags /* = 0 */, bool auto_commit /* = true */, int conn_timeout /* = 60 */, int rw_timeout /* = 60 */) { acl_assert(dbaddr && *dbaddr); acl_assert(dbname && *dbname); dbaddr_ = acl_mystrdup(dbaddr); dbname_ = acl_mystrdup(dbname); if (dbuser) dbuser_ = acl_mystrdup(dbuser); else dbuser_ = NULL; if (dbpass) dbpass_ = acl_mystrdup(dbpass); else dbpass_ = NULL; dbflags_ = dbflags; auto_commit_ = auto_commit; conn_timeout_ = conn_timeout; rw_timeout_ = rw_timeout; #if defined(ACL_CPP_DLL) || defined(USE_DYNAMIC) acl_pthread_once(&__mysql_once, __mysql_dll_load); #endif conn_ = NULL; }
int acl_xml_decode(const char *in, ACL_VSTRING *out) { int n = 0, len; const char *ptr = in, *pre; const ACL_TOKEN *token; const XML_SPEC *spec; acl_pthread_once(&__token_once, xml_decode_init); if (__token_tree == NULL) acl_msg_fatal("__token_tree null"); while (*ptr != 0) { pre = ptr; token = acl_token_tree_match(__token_tree, &ptr, NULL, NULL); if (token == NULL) { pre = markup_unescape(pre, out); len = (int) (ptr - pre); if (len > 0) acl_vstring_memcat(out, pre, len); break; } spec = (const XML_SPEC*) token->ctx; acl_assert(spec != NULL); len = (int) (ptr - pre - spec->len); if (len > 0) acl_vstring_memcat(out, pre, len); acl_vstring_strcat(out, spec->str); n++; } ACL_VSTRING_TERMINATE(out); return (n); }
static void fiber_check(void) { if (__thread_fiber != NULL) return; acl_assert(acl_pthread_once(&__once_control, thread_init) == 0); __thread_fiber = (FIBER_TLS *) acl_mycalloc(1, sizeof(FIBER_TLS)); #ifdef USE_JMP /* set context NULL when using setjmp that setcontext will not be * called in fiber_swap. */ __thread_fiber->original.context = NULL; #else __thread_fiber->original.context = (ucontext_t *) acl_mycalloc(1, sizeof(ucontext_t)); #endif __thread_fiber->fibers = NULL; __thread_fiber->size = 0; __thread_fiber->slot = 0; __thread_fiber->idgen = 0; __thread_fiber->count = 0; acl_ring_init(&__thread_fiber->ready); acl_ring_init(&__thread_fiber->dead); if ((unsigned long) acl_pthread_self() == acl_main_thread_self()) { __main_fiber = __thread_fiber; atexit(fiber_schedule_main_free); } else if (acl_pthread_setspecific(__fiber_key, __thread_fiber) != 0) acl_msg_fatal("acl_pthread_setspecific error!"); }
void db_pgsql::load(void) { #ifdef HAS_PGSQL_DLL acl_pthread_once(&__pgsql_once, __pgsql_dll_load); #else logger_warn("link pgsql library in static way!"); #endif }
int acl_read_wait(ACL_SOCKET fd, int timeout) { const char *myname = "acl_read_wait"; int op = EPOLL_CTL_ADD, delay = timeout * 1000, *epoll_fd; struct epoll_event ee, events[1]; acl_assert(acl_pthread_once(&epoll_once, thread_epoll_init) == 0); epoll_fd = (int*) acl_pthread_getspecific(epoll_key); if (epoll_fd == NULL) { epoll_fd = (int*) acl_mymalloc(sizeof(int)); acl_assert(acl_pthread_setspecific(epoll_key, epoll_fd) == 0); if ((unsigned long) acl_pthread_self() == acl_main_thread_self()) { main_epoll_read_fd = epoll_fd; atexit(main_epoll_end); } *epoll_fd = epoll_create(1); } ee.events = EPOLLIN | EPOLLHUP | EPOLLERR; ee.data.u64 = 0; ee.data.fd = fd; if (epoll_ctl(*epoll_fd, op, fd, &ee) == -1) { acl_msg_error("%s(%d): epoll_ctl error: %s, fd: %d", myname, __LINE__, acl_last_serror(), fd); return -1; } if (epoll_wait(*epoll_fd, events, 1, delay) == -1) { acl_msg_error("%s(%d): epoll_wait error: %s, fd: %d", myname, __LINE__, acl_last_serror(), fd); return -1; } if ((events[0].events & (EPOLLERR | EPOLLHUP)) != 0) return -1; if ((events[0].events & EPOLLIN) == 0) { acl_set_error(ACL_ETIMEDOUT); return -1; } ee.events = 0; ee.data.u64 = 0; ee.data.fd = fd; if (epoll_ctl(*epoll_fd, EPOLL_CTL_DEL, fd, &ee) == -1) { acl_msg_error("%s(%d): epoll_ctl error: %s, fd: %d", myname, __LINE__, acl_last_serror(), fd); return -1; } return 0; }
unsigned long acl_main_thread_self() { #ifdef ACL_UNIX return ((unsigned long) acl_var_main_tid); #elif defined(WIN32) if (acl_var_main_tid == (unsigned long) -1) acl_pthread_once(&__once_control, get_main_thread_id); return (acl_var_main_tid); #else #error "Unknown OS" #endif }
static void *tls_calloc(size_t len) { void *ptr; (void) acl_pthread_once(&once_control, once_init); ptr = (void*) acl_pthread_getspecific(once_key); if (ptr == NULL) { ptr = acl_mycalloc(1, len); acl_pthread_setspecific(once_key, ptr); if ((unsigned long) acl_pthread_self() == acl_main_thread_self()) __tls = ptr; } return ptr; }
HTTP_HDR_REQ *http_hdr_req_new(void) { HTTP_HDR_REQ *hh; ACL_ARRAY *pool; if (var_http_tls_cache <= 0) { hh = (HTTP_HDR_REQ *) http_hdr_new(sizeof(HTTP_HDR_REQ)); __hdr_init(hh); return hh; } #ifdef USE_TLS_EX pool = (ACL_ARRAY*) acl_pthread_tls_get(&cache_key); if (pool == NULL) { pool = acl_array_create(100); acl_pthread_tls_set(cache_key, pool, (void (*)(void*)) thread_cache_free); } pool = (ACL_ARRAY*) acl_pthread_tls_get(&cache_key); hh = (HTTP_HDR_REQ*) pool->pop_back(pool); if (hh) { __hdr_reset(hh, 1); http_hdr_reset((HTTP_HDR *) hh); return hh; } #else acl_pthread_once(&once_control, cache_init); pool = (ACL_ARRAY*) acl_pthread_getspecific(cache_key); if (pool == NULL) { pool = acl_array_create(100); acl_pthread_setspecific(cache_key, pool); if ((unsigned long) acl_pthread_self() == acl_main_thread_self()) { cache_pool = pool; atexit(main_cache_free); } } hh = (HTTP_HDR_REQ*) pool->pop_back(pool); if (hh) { __hdr_reset(hh, 1); http_hdr_reset((HTTP_HDR *) hh); return hh; } #endif hh = (HTTP_HDR_REQ *) http_hdr_new(sizeof(HTTP_HDR_REQ)); __hdr_init(hh); return hh; }
const char *acl_xml_decode2(const char *in, char **out, size_t *size) { size_t len; const char *ptr = in, *pre; const ACL_TOKEN *token; const XML_SPEC *spec; if (*size == 0) return in; *size -= 1; /* reserve space for '\0' */ acl_pthread_once(&__token_once, xml_decode_init); if (__token_tree == NULL) acl_msg_fatal("__token_tree null"); while (*ptr != 0) { pre = ptr; token = acl_token_tree_match(__token_tree, &ptr, NULL, NULL); if (token == NULL) { pre = markup_unescape2(pre, out, size); if (*size == 0) break; if (ptr > pre) (void) copy_buf(out, size, pre, ptr - pre); break; } spec = (const XML_SPEC*) token->ctx; acl_assert(spec != NULL); len = ptr - pre - spec->len; if (len > 0) copy_buf(out, size, pre, len); if (*size == 0) break; (void) copy_buf(out, size, spec->str, strlen(spec->str)); if (*size == 0) break; } **out = '\0'; *out += 1; return ptr; }
charset_conv::charset_conv() : m_addInvalid(true) , m_errmsg("ok") , m_pBuf(NULL) { m_fromCharset[0] = 0; m_toCharset[0] = 0; #ifdef HAVE_H_ICONV m_iconv = (iconv_t) -1; m_pInBuf = NULL; m_pOutBuf = NULL; # ifdef WIN32 # ifndef USE_WIN_ICONV acl_pthread_once(&__iconv_once, __iconv_dll_load); # endif # endif #endif }
const char *acl_last_serror(void) { char *buf; int error = acl_last_error(); static int __buf_size = 4096; (void) acl_pthread_once(&once_control, thread_buf_init); buf = acl_pthread_getspecific(__errbuf_key); if (buf == NULL) { buf = acl_mymalloc(__buf_size); acl_pthread_setspecific(__errbuf_key, buf); if ((unsigned long) acl_pthread_self() == acl_main_thread_self()) { __main_buf = buf; atexit(main_free_buf); } } return acl_strerror(error, buf, __buf_size); }
void db_mysql::sane_mysql_init(const char* dbaddr, const char* dbname, const char* dbuser, const char* dbpass, unsigned long dbflags, bool auto_commit, int conn_timeout, int rw_timeout, const char* charset) { if (dbaddr == NULL || *dbaddr == 0) logger_fatal("dbaddr null"); if (dbname == NULL || *dbname == 0) logger_fatal("dbname null"); // 地址格式:[dbname@]dbaddr const char* ptr = strchr(dbaddr, '@'); if (ptr) ptr++; else ptr = dbaddr; acl_assert(*ptr); dbaddr_ = acl_mystrdup(ptr); dbname_ = acl_mystrdup(dbname); if (dbuser && *dbuser) dbuser_ = acl_mystrdup(dbuser); else dbuser_ = NULL; if (dbpass && *dbpass) dbpass_ = acl_mystrdup(dbpass); else dbpass_ = NULL; if (charset && *charset) charset_ = charset; dbflags_ = dbflags; auto_commit_ = auto_commit; conn_timeout_ = conn_timeout; rw_timeout_ = rw_timeout; #ifdef HAS_MYSQL_DLL acl_pthread_once(&__mysql_once, __mysql_dll_load); #endif conn_ = NULL; }
void db_pgsql::sane_pgsql_init(const char* dbaddr, const char* dbname, const char* dbuser, const char* dbpass, int conn_timeout, int rw_timeout, const char* charset) { affect_count_ = 0; if (dbaddr == NULL || *dbaddr == 0) logger_fatal("dbaddr null"); if (dbname == NULL || *dbname == 0) logger_fatal("dbname null"); // 地址格式:[dbname@]dbaddr const char* ptr = strchr(dbaddr, '@'); if (ptr) ptr++; else ptr = dbaddr; acl_assert(*ptr); dbaddr_ = acl_mystrdup(ptr); dbname_ = acl_mystrdup(dbname); if (dbuser && *dbuser) dbuser_ = acl_mystrdup(dbuser); else dbuser_ = NULL; if (dbpass && *dbpass) dbpass_ = acl_mystrdup(dbpass); else dbpass_ = NULL; if (charset && *charset) charset_ = charset; conn_timeout_ = conn_timeout; rw_timeout_ = rw_timeout; #ifdef HAS_PGSQL_DLL acl_pthread_once(&__pgsql_once, __pgsql_dll_load); #endif conn_ = NULL; }
virtual bool thread_on_init() { acl_pthread_once(&stream_once, thread_init_once); acl::socket_stream* conn = (acl::socket_stream*) acl_pthread_getspecific(stream_key); if (conn != NULL) return true; conn = new acl::socket_stream; if (conn->bind_udp(var_cfg_local_addr) == false) { logger_error("bind %s error %s", var_cfg_local_addr, acl::last_serror()); delete conn; return false; } acl_pthread_setspecific(stream_key, conn); return true; }
static ACL_MEM_SLICE *mem_slice_create(void) { const char *myname = "mem_slice_create"; ACL_MEM_SLICE *mem_slice; acl_pthread_once(&once_control, slice_key_init); if (__mem_slice_key == (acl_pthread_key_t) -1) acl_msg_fatal("%s(%d): __mem_slice_key(%d) invalid," " call acl_mem_slice_init or acl_mem_slice_set first", myname, __LINE__, (int) __mem_slice_key); mem_slice = acl_pthread_getspecific(__mem_slice_key); if (mem_slice != NULL) return mem_slice; mem_slice = (ACL_MEM_SLICE*) acl_default_calloc(__FILE__, __LINE__, 1, sizeof(ACL_MEM_SLICE)); if (mem_slice == NULL) acl_msg_fatal("%s(%d): can't alloc for mem_slice(%s)", myname, __LINE__, acl_last_serror()); mem_slice->slice_pool = acl_slice_pool_create(__mem_base, __mem_nslice, __mem_slice_flag); mem_slice->tid = (unsigned long) acl_pthread_self(); mem_slice->list = private_array_create(__mem_list_init_size); MUTEX_INIT(mem_slice); mem_slice->tls_key = __mem_slice_key; mem_slice->nalloc_gc = __mem_nalloc_gc; mem_slice->slice_flag = __mem_slice_flag; acl_pthread_setspecific(__mem_slice_key, mem_slice); if ((unsigned long) acl_pthread_self() == acl_main_thread_self()) __main_mem_slice = mem_slice; acl_msg_info("%s(%d): thread(%ld) set myown mem_slice(%p)", myname, __LINE__, (long) mem_slice->tid, mem_slice); return mem_slice; }
int acl_pthread_key_create(acl_pthread_key_t *key_ptr, void (*destructor)(void*)) { const char *myname = "acl_pthread_key_create"; acl_pthread_once(&__create_thread_control_once, acl_pthread_init_once); *key_ptr = TlsAlloc(); if (*key_ptr == ACL_TLS_OUT_OF_INDEXES) { acl_set_error(ACL_ENOMEM); return ACL_ENOMEM; } else if (*key_ptr >= ACL_PTHREAD_KEYS_MAX) { acl_msg_error("%s(%d): key(%d) > ACL_PTHREAD_KEYS_MAX(%d)", myname, __LINE__, *key_ptr, ACL_PTHREAD_KEYS_MAX); TlsFree(*key_ptr); *key_ptr = ACL_TLS_OUT_OF_INDEXES; acl_set_error(ACL_ENOMEM); return ACL_ENOMEM; } __tls_key_list[*key_ptr].destructor = destructor; __tls_key_list[*key_ptr].key = *key_ptr; return 0; }
int acl_pthread_create(acl_pthread_t *thread, acl_pthread_attr_t *attr, void *(*start_routine)(void *), void *arg) { const char *myname = "acl_pthread_create"; acl_pthread_t *h_thread; HANDLE handle; unsigned long id, flag; if (thread == NULL) { acl_msg_error("%s, %s(%d): input invalid", __FILE__, myname, __LINE__); acl_set_error(ACL_EINVAL); return ACL_EINVAL; } acl_pthread_once(&__create_thread_control_once, acl_pthread_init_once); memset(thread, 0, sizeof(acl_pthread_t)); h_thread = acl_default_calloc(__FILE__, __LINE__, 1, sizeof(acl_pthread_t)); if (h_thread == NULL) { acl_msg_error("%s, %s(%d): calloc error(%s)", __FILE__, myname, __LINE__, acl_last_serror()); acl_set_error(ACL_ENOMEM); return ACL_ENOMEM; } if (attr != NULL) h_thread->detached = attr->detached; else h_thread->detached = 1; h_thread->start_routine = start_routine; h_thread->routine_arg = arg; if (__thread_inited) { acl_pthread_mutex_lock(&__thread_lock); flag = 0; } else flag = CREATE_SUSPENDED; #ifdef ACL_WIN32_STDC h_thread->handle = handle = (HANDLE) _beginthreadex(NULL, attr ? (unsigned int) attr->stacksize : 0, RunThreadWrap, (void *) h_thread, flag, &id); #else h_thread->handle = handle = CreateThread(NULL, attr ? attr->stacksize : 0,, RunThreadWrap, h_thread, flag, &id); #endif if (__thread_inited) acl_pthread_mutex_unlock(&__thread_lock); else if (flag == CREATE_SUSPENDED && handle != 0) ResumeThread(handle); if (handle == 0) { acl_msg_error("%s, %s(%d): CreateThread error(%s)", __FILE__, myname, __LINE__, acl_last_serror()); return -1; } thread->start_routine = start_routine; thread->routine_arg = arg; thread->id = id; thread->handle = 0; /* 根据线程的属性来确定线程创建时是分离模式还是非分离模式 */ if (attr == NULL || attr->detached) { thread->detached = 1; return 0; } thread->detached = 0; thread->handle = handle; return 0; }
int acl_read_wait(ACL_SOCKET fd, int timeout) { const char *myname = "acl_read_wait"; int delay = timeout * 1000, ret; EPOLL_CTX *epoll_ctx; struct epoll_event ee, events[1]; time_t begin; acl_assert(acl_pthread_once(&epoll_once, thread_epoll_once) == 0); epoll_ctx = (EPOLL_CTX*) acl_pthread_getspecific(epoll_key); if (epoll_ctx == NULL) epoll_ctx = thread_epoll_init(); ee.events = EPOLLIN | EPOLLHUP | EPOLLERR; ee.data.u64 = 0; ee.data.fd = fd; if (epoll_ctl(epoll_ctx->epfd, EPOLL_CTL_ADD, fd, &ee) == -1 && acl_last_error() != EEXIST) { acl_msg_error("%s(%d): epoll_ctl error: %s, fd: %d, epfd: %d," " tid: %lu, %lu", myname, __LINE__, acl_last_serror(), fd, epoll_ctx->epfd, epoll_ctx->tid, acl_pthread_self()); return -1; } for (;;) { time(&begin); ret = epoll_wait(epoll_ctx->epfd, events, 1, delay); if (ret == -1) { if (acl_last_error() == ACL_EINTR) { acl_msg_warn(">>>>catch EINTR, try again<<<"); continue; } acl_msg_error("%s(%d): epoll_wait error: %s, fd: %d," " epfd: %d, tid: %lu, %lu", myname, __LINE__, acl_last_serror(), fd, epoll_ctx->epfd, epoll_ctx->tid, acl_pthread_self()); ret = -1; break; } else if (ret == 0) { acl_msg_warn("%s(%d), %s: poll timeout: %s, fd: %d, " "delay: %d, spent: %ld", __FILE__, __LINE__, myname, acl_last_serror(), fd, delay, (long) (time(NULL) - begin)); acl_set_error(ACL_ETIMEDOUT); ret = -1; break; } else if ((events[0].events & (EPOLLERR | EPOLLHUP)) != 0) { acl_msg_warn("%s(%d), %s: poll error: %s, fd: %d, " "delay: %d, spent: %ld", __FILE__, __LINE__, myname, acl_last_serror(), fd, delay, (long) (time(NULL) - begin)); ret = -1; } else if ((events[0].events & EPOLLIN) == 0) { acl_msg_warn("%s(%d), %s: poll error: %s, fd: %d, " "delay: %d, spent: %ld", __FILE__, __LINE__, myname, acl_last_serror(), fd, delay, (long) (time(NULL) - begin)); acl_set_error(ACL_ETIMEDOUT); ret = -1; } else ret = 0; break; } ee.events = 0; ee.data.u64 = 0; ee.data.fd = fd; if (epoll_ctl(epoll_ctx->epfd, EPOLL_CTL_DEL, fd, &ee) == -1) { acl_msg_error("%s(%d): epoll_ctl error: %s, fd: %d, epfd: %d," " tid: %lu, %lu", myname, __LINE__, acl_last_serror(), fd, epoll_ctx->epfd, epoll_ctx->tid, acl_pthread_self()); return -1; } return ret; }
bool db_pgsql::dbopen(const char* /* charset = NULL */) { if (conn_) return true; char tmpbuf[256]; char *db_host, *db_unix; int db_port; char* ptr = strchr(dbaddr_, '/'); if (ptr == NULL) { ACL_SAFE_STRNCPY(tmpbuf, dbaddr_, sizeof(tmpbuf)); ptr = strchr(tmpbuf, ':'); if (ptr == NULL || *(ptr + 1) == 0) { logger_error("invalid db_addr=%s", dbaddr_); return false; } else *ptr++ = 0; db_host = tmpbuf; db_port = atoi(ptr); if (db_port <= 0) { logger_error("invalid port=%d", db_port); return false; } db_unix = NULL; } else { db_unix = dbaddr_; db_host = db_unix; db_port = 0; } int* dummy; if (acl_pthread_once(&__thread_once_control, thread_once) != 0) logger_error("call thread_once error: %s", acl_last_serror()); else if (!(dummy = (int*) acl_pthread_getspecific(__thread_key))) { dummy = (int*) acl_mymalloc(sizeof(int)); *dummy = 1; acl_assert(!acl_pthread_setspecific(__thread_key, dummy)); if ((unsigned long) acl_pthread_self() == acl_main_thread_self()) { __main_dummy = dummy; atexit(main_free_dummy); } } string info; info.format("host=%s dbname=%s", db_host, dbname_); if (db_unix == NULL) info.format_append(" port=%d", db_port); if (dbuser_) info.format_append(" user=%s", dbuser_); if (dbpass_) info.format_append(" password=%s", dbpass_); conn_ = __dbconnect(info.c_str()); if (conn_ == NULL || __dbstatus(conn_) != CONNECTION_OK) { logger_error("connect pgsql error(%s), db_host=%s, db_port=%d," " db_unix=%s, db_name=%s, db_user=%s, db_pass=%s", conn_ ? __dberror_message(conn_) : "connect error", db_host ? db_host : "null", db_port, db_unix ? db_unix : "null", dbname_ ? dbname_ : "null", dbuser_ ? dbuser_ : "null", dbpass_ ? dbpass_ : "null"); if (conn_) { __dbfinish(conn_); conn_ = NULL; } return false; } return true; }
bool db_mysql::dbopen(const char* charset /* = NULL */) { if (conn_) return true; char tmpbuf[256]; char *db_host, *db_unix; int db_port; char* ptr = strchr(dbaddr_, '/'); if (ptr == NULL) { ACL_SAFE_STRNCPY(tmpbuf, dbaddr_, sizeof(tmpbuf)); ptr = strchr(tmpbuf, ':'); if (ptr == NULL || *(ptr + 1) == 0) { logger_error("invalid db_addr=%s", dbaddr_); return false; } else *ptr++ = 0; db_host = tmpbuf; db_port = atoi(ptr); if (db_port <= 0) { logger_error("invalid port=%d", db_port); return false; } db_unix = NULL; } else { db_unix = dbaddr_; db_host = NULL; db_port = 0; } int* dummy; if (acl_pthread_once(&__thread_once_control, thread_once) != 0) logger_error("call thread_once error: %s", acl_last_serror()); else if (!(dummy = (int*) acl_pthread_getspecific(__thread_key))) { dummy = (int*) acl_mymalloc(sizeof(int)); *dummy = 1; acl_assert(!acl_pthread_setspecific(__thread_key, dummy)); // 调用下面函数可能会造成内存越界 //if (__mysql_thread_init != NULL) // __mysql_thread_init(); if ((unsigned long) acl_pthread_self() == acl_main_thread_self()) { __main_dummy = dummy; atexit(main_free_dummy); } } conn_ = __mysql_init(NULL); if (conn_ == NULL) { logger_error("mysql init error"); return false; } if (conn_timeout_ > 0) #if MYSQL_VERSION_ID >= 50500 __mysql_options(conn_, MYSQL_OPT_CONNECT_TIMEOUT, (const void*) &conn_timeout_); #else __mysql_options(conn_, MYSQL_OPT_CONNECT_TIMEOUT, (const char*) &conn_timeout_); #endif if (rw_timeout_ > 0) { #if MYSQL_VERSION_ID >= 50500 __mysql_options(conn_, MYSQL_OPT_READ_TIMEOUT, (const void*) &rw_timeout_); __mysql_options(conn_, MYSQL_OPT_WRITE_TIMEOUT, (const void*) &rw_timeout_); #else __mysql_options(conn_, MYSQL_OPT_READ_TIMEOUT, (const char*) &rw_timeout_); __mysql_options(conn_, MYSQL_OPT_WRITE_TIMEOUT, (const char*) &rw_timeout_); #endif } my_bool reconnect = 1; #if MYSQL_VERSION_ID >= 50500 __mysql_options(conn_, MYSQL_OPT_RECONNECT, (const void*) &reconnect); #else __mysql_options(conn_, MYSQL_OPT_RECONNECT, (const char*) &reconnect); #endif if (__mysql_open(conn_, db_host, dbuser_ ? dbuser_ : "", dbpass_ ? dbpass_ : "", dbname_, db_port, db_unix, dbflags_) == NULL) { logger_error("connect mysql error(%s), db_host=%s, db_port=%d," " db_unix=%s, db_name=%s, db_user=%s, db_pass=%s," " dbflags=%ld", __mysql_error(conn_), db_host ? db_host : "null", db_port, db_unix ? db_unix : "null", dbname_ ? dbname_ : "null", dbuser_ ? dbuser_ : "null", dbpass_ ? dbpass_ : "null", dbflags_); __mysql_close(conn_); conn_ = NULL; return false; } #if 0 logger("connect mysql ok(%s), db_host=%s, db_port=%d, " "db_unix=%s, db_name=%s, db_user=%s, db_pass=%s, dbflags=%ld", __mysql_error(conn_), db_host ? db_host : "null", db_port, db_unix ? db_unix : "null", dbname_ ? dbname_ : "null", dbuser_ ? dbuser_ : "null", dbpass_ ? dbpass_ : "null", dbflags_); #endif if (charset != NULL && *charset != 0) charset_ = charset; if (!charset_.empty()) { if (!__mysql_set_character_set(conn_, charset_.c_str())) logger("set mysql charset to %s, %s", charset_.c_str(), __mysql_character_set_name(conn_)); else logger_error("set mysql to %s error %s", charset_.c_str(), __mysql_error(conn_)); } #if MYSQL_VERSION_ID >= 50000 if (__mysql_autocommit(conn_, auto_commit_ ? 1 : 0) != 0) { logger_error("mysql_autocommit error"); __mysql_close(conn_); conn_ = NULL; return (false); } #else auto_commit_ = false; #endif return true; }