首页 > 代码库 > Memcached源码分析之memcached.h

Memcached源码分析之memcached.h

  1.  //memcached.h
  2.  
  3. //返回在item中data字段key的地址,即把指针指向key
  4. #define ITEM_key(item) (((char*)&((item)->data)) \
  5.          + (((item)->it_flags & ITEM_CAS) ? sizeof(uint64_t) : 0))
  6. //返回在item中data字段suffix的地址,即把指针指向suffix
  7. #define ITEM_suffix(item) ((char*) &((item)->data) + (item)->nkey + 1 \
  8.          + (((item)->it_flags & ITEM_CAS) ? sizeof(uint64_t) : 0))
  9.  //返回在item中data字段value的地址,即把指针指向value
  10. #define ITEM_data(item) ((char*) &((item)->data) + (item)->nkey + 1 \
  11.          + (item)->nsuffix \
  12.          + (((item)->it_flags & ITEM_CAS) ? sizeof(uint64_t) : 0))
  13. //item总字节数
  14. #define ITEM_ntotal(item) (sizeof(struct _stritem) + (item)->nkey + 1 \
  15.          + (item)->nsuffix + (item)->nbytes \
  16.          + (((item)->it_flags & ITEM_CAS) ? sizeof(uint64_t) : 0))
  17. //conn结构体中state字段的枚举,代表连接状态
  18. enum conn_states {
  19.     conn_listening, /**< the socket which listens for connections */
  20.     conn_new_cmd, /**< Prepare connection for next command */
  21.     conn_waiting, /**< waiting for a readable socket */
  22.     conn_read, /**< reading in a command line */
  23.     conn_parse_cmd, /**< try to parse a command from the input buffer */
  24.     conn_write, /**< writing out a simple response */
  25.     conn_nread, /**< reading in a fixed number of bytes */
  26.     conn_swallow, /**< swallowing unnecessary bytes w/o storing */
  27.     conn_closing, /**< closing this connection */
  28.     conn_mwrite, /**< writing out many items sequentially */
  29.     conn_closed, /**< connection is closed */
  30.     conn_max_state /**< Max state value (used for assertion) */
  31. };
  32. //item保存结果枚举
  33. enum store_item_type {
  34.     NOT_STORED=0, STORED, EXISTS, NOT_FOUND
  35. };
  36. //item结构体
  37. typedef struct _stritem {
  38.     struct _stritem *next; //链表中下一个,这个链表有可能是slots链表,也有可能是LRU链表,但一个item不可能同时这两个链表中,所以复用一个指针。
  39.     struct _stritem *prev; //链表中上一个。
  40.     struct _stritem *h_next;  //相同hash值中链表的下一个。
  41.     rel_time_t time;   //最近访问时间
  42.     rel_time_t exptime;  //过期时间
  43.     int nbytes;  //value的字节数
  44.     unsigned short refcount; //引用计数
  45.     uint8_t nsuffix;  //后缀长度
  46.     uint8_t it_flags;  //标记
  47.     uint8_t slabs_clsid;  //item所在的slabclass的id值
  48.     uint8_t nkey; //键长
  49.     /* this odd type prevents type-punning issues when we do
  50.      * the little shuffle to save space when not using CAS. */
  51.     union {
  52.         uint64_t cas;
  53.         char end;
  54.     } data[]; //数据,这个数据不仅仅包括key对应的value,还有key、CAS、后缀等等数据也存在此,所以它有4部分“拼”成:CAS(可选),KEY,后缀,VALUE。
  55.     /* if it_flags & ITEM_CAS we have 8 bytes CAS */
  56.     /* then null-terminated key */
  57.     /* then " flags length\r\n" (no terminating null) */
  58.     /* then data with terminating \r\n (no terminating null; it‘s binary!) */
  59. } item;
  60. /**
  61. worker线程结构体
  62. */
  63. typedef struct {
  64.     pthread_t thread_id; //线程id
  65.     struct event_base *base; //每个线程自己独立的event_base,监听的就是下面的notify_event事件对象
  66.     struct event notify_event; //事件对象,fd即为下面的notify_receive_fd
  67.     int notify_receive_fd; //管道接收fd
  68.     int notify_send_fd; //管道写入fd
  69.     struct thread_stats stats; //线程的一些统计
  70.     struct conn_queue *new_conn_queue; //连接参数对象CQ_ITEM队列
  71.     cache_t *suffix_cache;
  72.     uint8_t item_lock_type; //控制线程锁的粒度
  73. } LIBEVENT_THREAD;
  74. /**
  75. 主线程结构体
  76. */
  77. typedef struct {
  78.     pthread_t thread_id; //线程id
  79.     struct event_base *base; //event_base
  80. } LIBEVENT_DISPATCHER_THREAD;
  81. typedef struct conn conn;
  82. struct conn {
  83.     int sfd; //连接的socket fd
  84.     sasl_conn_t *sasl_conn;
  85.     bool authenticated;
  86.     enum conn_states state; //当前的连接状态
  87.     enum bin_substates substate;
  88.     rel_time_t last_cmd_time;
  89.     struct event event; // 监听的事件
  90.     short ev_flags; //监听的事件 类型
  91.     short which; /** which events were just triggered */ //刚触发的事件
  92.     /**
  93.         读buffer会涉及两个方向上的“读”:
  94.         一个是从socket读进来到rbuf里面
  95.         一个是从rbuf里面把数据读出去解析,读buffer相当于一个中介,从socket读进来最终还是得被别人读出去解析,而
  96.         rcurr工作指针与rbytes就是在rbuf数据被读出去解析的时候用到,用来控制可以读出去被解析的数据还剩余多少。
  97.     */
  98.     char *rbuf; /** buffer to read commands into */ //读buffer
  99.     char *rcurr; /** but if we parsed some already, this is where we stopped */ //读buffer的当前指针
  100.     int rsize; /** total allocated size of rbuf */ //读buffer大小
  101.     int rbytes; /** how much data, starting from rcur, do we have unparsed */ //剩余buffer字节数
  102.     //下面4个属性和上面4个类似
  103.     char *wbuf;
  104.     char *wcurr;
  105.     int wsize;
  106.     int wbytes;
  107.     /** which state to go into after finishing current write */
  108.     enum conn_states write_and_go; //完成当前写操作后,连接状态将会置为此状态
  109.     void *write_and_free; /** free this memory after finishing writing */
  110.     char *ritem; /** when we read in an item‘s value, it goes here */ //这个指针指向item结构体中data中的value地址
  111.     int rlbytes; //尚未读完item的data的value的字节数
  112.     void *item; /* for commands set/add/replace */ //当执行set/add/replace 命令时,此指针用于指向分配的item空间
  113.     /* data for the swallow state */
  114.     int sbytes; /* how many bytes to swallow */
  115.     //下面是往socket写出数据时用的字段
  116.     struct iovec *iov; //iovec结构体数组
  117.     int iovsize; //*iov数组大小
  118.     int iovused; //*iov数组已被使用的元素个数
  119.     struct msghdr *msglist; //msghdr结构体数组,表示sendmsg要发送的消息列表
  120.     int msgsize; //*msglist数组大小
  121.     int msgused; //*msglist数组已使用的元素个数
  122.     int msgcurr; //当前要发送的msghdr
  123.     int msgbytes; //当前msghdr的字节数
  124.     item **ilist; //get key1 key2命令时,要发送给客户端的item列表
  125.     int isize; //列表大小
  126.     item **icurr; //当前要发送的item
  127.     int ileft; //剩余数目
  128.     char **suffixlist;
  129.     int suffixsize;
  130.     char **suffixcurr;
  131.     int suffixleft;
  132.     enum protocol protocol; /* which protocol this connection speaks */
  133.     enum network_transport transport; /* what transport is used by this connection */
  134.     //UDP相关的字段
  135.     int request_id; /* Incoming UDP request ID, if this is a UDP "connection" */
  136.     struct sockaddr_in6 request_addr; /* udp: Who sent the most recent request */
  137.     socklen_t request_addr_size;
  138.     unsigned char *hdrbuf; /* udp packet headers */
  139.     int hdrsize; /* number of headers‘ worth of space is allocated */
  140.     bool noreply; /* True if the reply should not be sent. */
  141.     /* current stats command */
  142.     struct {
  143.         char *buffer;
  144.         size_t size;
  145.         size_t offset;
  146.     } stats;
  147.     // 二进制相关的字段
  148.     protocol_binary_request_header binary_header;
  149.     uint64_t cas; /* the cas to return */
  150.     short cmd; /* current command being processed */
  151.     int opaque;
  152.     int keylen;
  153.     conn *next; /* Used for generating a list of conn structures */
  154.     LIBEVENT_THREAD *thread; /* Pointer to the thread object serving this connection */
  155. };
  156. //非阻塞方式获取互斥锁
  157. static inline int mutex_lock(pthread_mutex_t *mutex)
  158. {
  159.     while (pthread_mutex_trylock(mutex));
  160.     return 0;
  161. }
  162. //释放锁
  163. #define mutex_unlock(x) pthread_mutex_unlock(x)
  164. #include "stats.h"
  165. #include "slabs.h"
  166. #include "assoc.h"
  167. #include "items.h"
  168. #include "trace.h"
  169. #include "hash.h"
  170. #include "util.h"

Memcached源码分析之memcached.h