我在我的应用程序中使用了两个mysql对象。我必须在退出线程之前只调用mysql_thread_end一次。是否有任何函数/回调,以便它在退出线程之前调用?
附加示例程序
using namespace std;
class MySql
{
public:
MySql()
{
mysql = mysql_init(NULL);
}
~MySql()
{
if(mysql)
{
mysql_close(mysql);
}
// Wrong: this will clear thread specific values twice. it may lead to crash the application.
// mysql_thread_end();
}
int Connect(const char *host,
const char *user,
const char *passwd,
const char *db,
unsigned int port,
const char *unix_socket,
unsigned long clientflag)
{
if(!mysql_real_connect(mysql, host,user,
passwd, db, port, unix_socket, clientflag))
{
return 1;
}
return 0;
}
int Execute(const char *query)
{
int status = mysql_query(mysql, query);
return status;
}
private:
MYSQL * mysql;
};
void createthreads();
static void StartThread(void * Arg);
int main(int argc, _TCHAR* argv[])
{
int i = mysql_library_init(0, NULL, NULL);
createthreads();
mysql_library_end();
return 0;
}
void createthreads()
{
PRThread *thread;
thread = PR_CreateThread(PR_USER_THREAD, StartThread, (void *)NULL, PR_PRIORITY_NORMAL, PR_GLOBAL_THREAD, PR_JOINABLE_THREAD, 0);
//Sleep(2000);
PR_JoinThread(thread);
}
void StartThread(void * Arg)
{
MySql mysqlsrc;
MySql mysqldest;
//Production server
if(!mysqlsrc.Connect("localhost","root", "root", NULL, 3306, NULL, 0))
{
cout<<"Connection to Src Failed";
return;
}
//Test Server
if(!mysqldest.Connect("localhost","root", "root", NULL, 3306, NULL, 0))
{
cout<<"Connection to Destn Failed";
return;
}
/// Sync databases.
}
答案 0 :(得分:0)
由于OP状态mysql_thread_end()
将在连接关闭后被调用和,文档声明它应该在线程结束之前调用我建议mod {{1 (线程函数)如下:
StartThread
答案 1 :(得分:0)
thread-specific data的标准pthread工具允许thread-specific data destructors注册,因此可用于implement a sort of "pthread exit hook"。
然后,那个钩子可以调用mysql_thread_end()
,其余的代码不需要知道这个:
using namespace std;
// --> XXX WARNING UNTESTED AND ERROR CHECKING OMITTED XXX <----
namespace {
pthread_key_t key;
pthread_key_once key_once = PTHREAD_ONCE_INIT;
void cleanup(void *dummy) // called at thread termination
{
mysql_thread_end();
}
void key_init() // called pthread_once and only once
{
(void)pthread_key_create(&key, mycleanup);
}
void workaround_bz66740() // call after you know mysql_thread_init has been called
{
(void)pthread_once(&key_once, key_init);
(void)pthread_setspecific(key, (const void *)1);
}
}
class MySql
{
public:
MySql()
{
mysql = mysql_init(NULL);
workaround_bz66740();
}
....
附注:你需要明确清理MySQL资源这一事实很麻烦,很遗憾,正如MySQL change request #66740中所阐述的那样。