首页  >  文章  >  数据库  >  从MySQL Signal 14 Warning看MySQL的线程信号处理模型_MySQL

从MySQL Signal 14 Warning看MySQL的线程信号处理模型_MySQL

WBOY
WBOY原创
2016-06-01 13:51:211270浏览

“MySQL Signal 14 Warning”这个问题来源于在使用我们的存储引擎时会在MySQL的log中发现大量的“Got signal 14 from

thread 0?”的警告信息,并且我们移植的MySQL测试用例也会不确定地失败,除非显式指定忽略警告信息,但这也导致一些有用

的warning也被忽略了。在很长的一段时间里我们都没有能够找到真实的原因,后来我才在阅读了MySQL上层的代码和我们的代码,

以及加上一些trace后确定了问题的所在。这其实是我们没有按照MySQL预想的方式使用后台线程导致,但在MySQL的手册和网站

上似乎也没有发现这方面的tips。

MySQL的线程工作模型是(From MySQL Doc):

1、Connection manager threads handle client connection requests on the network interfaces that the server<br> listens to.<br><br>2、A signal thread handles all signals. This thread also normally handles alarms and calls process_alarm() <br>to force timeouts on connections that have been idle too long. <br><br>3、If mysqld is compiled with -DUSE_ALARM_THREAD, a dedicated thread that handles alarms is created. <br>This is only used on some systems where there are problems with sigwait()  or if you want to use the thr_alarm() <br> code in your application without a dedicated signal handling thread.<br><br><p>从mysql的main函数中可以看到,虽然mysql的主线程注册了SIGALARM的信号处理函数,但是实际上mysql是采用在指定的线程</p><p>中同步的方式处理异步信号的,即主线程在系统初始化时先进行信号的初始化,包括设置主线程的信号掩码,以统一抛给信号处理</p><p>线程去处理,主线程的信号掩码会被它的所有子线程继承,之后进程收到的信号都会由信号处理线程去处理。但前提是所有的子线</p><p>程都继承了主线程的信号掩码,否则异步信号总能够传递给进程。</p><p>我们的问题出在有两个后台线程是在静态变量中初始化和启动的,这时候mysql的主线程根本还没进行信号掩码的设置,所以SIGALARM这个</p><p>本来应该由信号处理线程处理的信号,却通过我们的后台线程handle给了MySQL的主进程,并调用信号处理函数打出这个warning。</p>后来发邮件给MySQL的开发人员(http://lists.mysql.com/internals/38057), 他们确认了我的理解是对的, 并且指出了我们这样使用线程<br>可能导致其他的问题, 包括:<br><p>1、在静态变量的构造函数中执行代码,可能导致代码执行权限被提升,有安全问题;</p><p> 2、如果把存储引擎编译成动态链接库的形式的话,只有init()回调函数会被调用到,静态变量的构造函数永远不会被执行。</p><p>他们的建议是:Please don't execute any code before mysql asks you to initialide the engine.</p>而innodb默认也有几个后台的io线程,之所以没这个问题,是因为这些后台线程是在innobase_init()函数中创建的,这些线程都继承了主线程的信号掩码。<br>
声明:
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn