IT技术博客大学习 共学习 共进步

memcache-2.2.4 中的一点小知识

PHPor 的Blog 2010-07-26 23:44:37 浏览 2,604 次
在一次抓包的过程中,发现我的PHP在访问memcache的时候时不时的会多出一个“version”的操作,结果就是返回memcached的版本号;疑惑不解,我发誓自己没有写这部分代码的,为什么会凭空多出一个“version”操作呢?看看源代码吧!

    源码中发现这么一段:

    int mmc_open(mmc_t *mmc, int force_connect, char **error_string, int *errnum TSRMLS_DC) /* {{{ */

    {

     switch (mmc->status) {

    case MMC_STATUS_DISCONNECTED:

    return _mmc_open(mmc, error_string, errnum TSRMLS_CC);

    case MMC_STATUS_CONNECTED:

    return 1;

    case MMC_STATUS_UNKNOWN:

    /* check connection if needed */

    if (force_connect) {

      char *version;

      if ((version = mmc_get_version(mmc TSRMLS_CC)) == NULL && !_mmc_open(mmc, error_string, errnum TSRMLS_CC)) {

          break;

      }

      if (version) {

          efree(version);

      }

      mmc->status = MMC_STATUS_CONNECTED;

    }

    return 1;

    case MMC_STATUS_FAILED:

    if (mmc->retry_interval >= 0 && (long)time(NULL) >= mmc->failed + mmc->retry_interval) {

      if (_mmc_open(mmc, error_string, errnum TSRMLS_CC) /*&& mmc_flush(mmc, 0 TSRMLS_CC) > 0*/) {

          return 1;

      }

    }

    break;

     }

     return 0;

    }

    如果连接状态为MMC_STATUS_UNKNOWN 就会通过“version”操作来检查连接的状态。那么什么情况下连接的状态会是MMC_STATUS_UNKNOWN 呢?

    参看函数: mmc_find_persistent , 其逻辑大致为:

    1. 如果在hash表中没有查到该连接,则初始化一个连接句柄,并注册一个长连接

    2. 如果查到了,发现连接明显有一些问题,比如根本没有成功连接,则从hash表中删除,重新初始化、注册;

    3. 如果查到了,并且没有发现明显的错误标识,则将状态置为MMC_STATUS_UNKNOWN,如此则发送一个“version”命令检查连接的有效性。

    如此看来,如果长连接被重用,则一定会先有一个version命令的。

    由此也可以看出,长连接关闭被动关闭时,PHP是没有被通知的,(猜测一下,通常这种情况下,连接是半关闭状态的) 

建议继续学习

  1. 关于memcache分布式一致性hash (阅读 11,661)
  2. Memcache分布式部署方案 (阅读 6,667)
  3. 关于session和memcache的若干问题 (阅读 5,186)
  4. Memcache mutex设计模式 (阅读 4,904)
  5. Memcache源代码分析之数据存储 (阅读 4,863)
  6. 解决memcache连接奇慢问题一例 (阅读 4,747)
  7. Memcache协议的学习 (阅读 4,704)
  8. 关于Memcache长连接自动重连的问题 (阅读 4,641)
  9. Memcache源代码分析之网络处理 (阅读 4,543)
  10. memcache的几点注意 (阅读 4,203)