LCOV - code coverage report
Current view: directory - redis/src - slowlog.c (source / functions) Found Hit Coverage
Test: redis.info Lines: 58 57 98.3 %
Date: 2012-04-04 Functions: 6 6 100.0 %
Colors: not hit hit

       1                 : #include "redis.h"
       2                 : #include "slowlog.h"
       3                 : 
       4                 : /* Slowlog implements a system that is able to remember the latest N
       5                 :  * queries that took more than M microseconds to execute.
       6                 :  *
       7                 :  * The execution time to reach to be logged in the slow log is set
       8                 :  * using the 'slowlog-log-slower-than' config directive, that is also
       9                 :  * readable and writable using the CONFIG SET/GET command.
      10                 :  *
      11                 :  * The slow queries log is actually not "logged" in the Redis log file
      12                 :  * but is accessible thanks to the SLOWLOG command. */
      13                 : 
      14                 : /* Create a new slowlog entry.
      15                 :  * Incrementing the ref count of all the objects retained is up to
      16                 :  * this function. */
      17             184 : slowlogEntry *slowlogCreateEntry(robj **argv, int argc, long long duration) {
      18             184 :     slowlogEntry *se = zmalloc(sizeof(*se));
      19                 :     int j;
      20                 : 
      21             184 :     se->argc = argc;
      22             184 :     se->argv = zmalloc(sizeof(robj*)*argc);
      23             436 :     for (j = 0; j < argc; j++) {
      24             252 :         se->argv[j] = argv[j];
      25             252 :         incrRefCount(argv[j]);
      26                 :     }
      27             184 :     se->time = time(NULL);
      28             184 :     se->duration = duration;
      29             184 :     se->id = server.slowlog_entry_id++;
      30             184 :     return se;
      31                 : }
      32                 : 
      33                 : /* Free a slow log entry. The argument is void so that the prototype of this
      34                 :  * function matches the one of the 'free' method of adlist.c.
      35                 :  *
      36                 :  * This function will take care to release all the retained object. */
      37             105 : void slowlogFreeEntry(void *septr) {
      38             105 :     slowlogEntry *se = septr;
      39                 :     int j;
      40                 : 
      41             221 :     for (j = 0; j < se->argc; j++)
      42             116 :         decrRefCount(se->argv[j]);
      43             105 :     zfree(se->argv);
      44             105 :     zfree(se);
      45             105 : }
      46                 : 
      47                 : /* Initialize the slow log. This function should be called a single time
      48                 :  * at server startup. */
      49              53 : void slowlogInit(void) {
      50              53 :     server.slowlog = listCreate();
      51              53 :     server.slowlog_entry_id = 0;
      52              53 :     listSetFreeMethod(server.slowlog,slowlogFreeEntry);
      53              53 : }
      54                 : 
      55                 : /* Push a new entry into the slow log.
      56                 :  * This function will make sure to trim the slow log accordingly to the
      57                 :  * configured max length. */
      58         1748530 : void slowlogPushEntryIfNeeded(robj **argv, int argc, long long duration) {
      59         1748530 :     if (server.slowlog_log_slower_than < 0) return; /* Slowlog disabled */
      60         1748530 :     if (duration >= server.slowlog_log_slower_than)
      61             184 :         listAddNodeHead(server.slowlog,slowlogCreateEntry(argv,argc,duration));
      62                 : 
      63                 :     /* Remove old entries if needed. */
      64         1748625 :     while (listLength(server.slowlog) > server.slowlog_max_len)
      65              95 :         listDelNode(server.slowlog,listLast(server.slowlog));
      66                 : }
      67                 : 
      68                 : /* Remove all the entries from the current slow log. */
      69               1 : void slowlogReset(void) {
      70              12 :     while (listLength(server.slowlog) > 0)
      71              10 :         listDelNode(server.slowlog,listLast(server.slowlog));
      72               1 : }
      73                 : 
      74                 : /* The SLOWLOG command. Implements all the subcommands needed to handle the
      75                 :  * Redis slow log. */
      76               8 : void slowlogCommand(redisClient *c) {
      77               9 :     if (c->argc == 2 && !strcasecmp(c->argv[1]->ptr,"reset")) {
      78               1 :         slowlogReset();
      79               1 :         addReply(c,shared.ok);
      80              12 :     } else if (c->argc == 2 && !strcasecmp(c->argv[1]->ptr,"len")) {
      81               5 :         addReplyLongLong(c,listLength(server.slowlog));
      82               6 :     } else if ((c->argc == 2 || c->argc == 3) &&
      83               2 :                !strcasecmp(c->argv[1]->ptr,"get"))
      84                 :     {
      85               2 :         long count = 10, sent = 0;
      86                 :         listIter li;
      87                 :         void *totentries;
      88                 :         listNode *ln;
      89                 :         slowlogEntry *se;
      90                 : 
      91               3 :         if (c->argc == 3 &&
      92               1 :             getLongFromObjectOrReply(c,c->argv[2],&count,NULL) != REDIS_OK)
      93                 :             return;
      94                 : 
      95               2 :         listRewind(server.slowlog,&li);
      96               2 :         totentries = addDeferredMultiBulkLength(c);
      97              10 :         while(count-- && (ln = listNext(&li))) {
      98                 :             int j;
      99                 : 
     100               6 :             se = ln->value;
     101               6 :             addReplyMultiBulkLen(c,4);
     102               6 :             addReplyLongLong(c,se->id);
     103               6 :             addReplyLongLong(c,se->time);
     104               6 :             addReplyLongLong(c,se->duration);
     105               6 :             addReplyMultiBulkLen(c,se->argc);
     106              15 :             for (j = 0; j < se->argc; j++)
     107               9 :                 addReplyBulk(c,se->argv[j]);
     108               6 :             sent++;
     109                 :         }
     110               2 :         setDeferredMultiBulkLength(c,totentries,sent);
     111                 :     } else {
     112               0 :         addReplyError(c,
     113                 :             "Unknown SLOWLOG subcommand or wrong # of args. Try GET, RESET, LEN.");
     114                 :     }
     115                 : }

Generated by: LCOV version 1.7