LLM4Binary/decompile-bench-makefile huggingface dataset:
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: redisLog
void redisLog(int level, const char *fmt, ...) {
    va_list ap;
    char msg[REDIS_MAX_LOGMSG_LEN];

    if ((level&0xff) < server.verbosity) return;

    va_start(ap, fmt);
    vsnprintf(msg, sizeof(msg), fmt, ap);
    va_end(ap);

    redisLogRaw(level,msg);
}

// Assembly:
pushq %r14
pushq %rbx
subq $0x4d8, %rsp            # imm = 0x4D8
movl %edi, %ebx
movq %rdx, 0x30(%rsp)
movq %rcx, 0x38(%rsp)
movq %r8, 0x40(%rsp)
movq %r9, 0x48(%rsp)
testb %al, %al
je 0x2327e
movaps %xmm0, 0x50(%rsp)
movaps %xmm1, 0x60(%rsp)
movaps %xmm2, 0x70(%rsp)
movaps %xmm3, 0x80(%rsp)
movaps %xmm4, 0x90(%rsp)
movaps %xmm5, 0xa0(%rsp)
movaps %xmm6, 0xb0(%rsp)
movaps %xmm7, 0xc0(%rsp)
movzbl %bl, %eax
cmpl 0xa7185(%rip), %eax     # 0xca40c
jl 0x232d3
movq %rsi, %r10
leaq 0x20(%rsp), %rax
movq %rsp, %rcx
movq %rax, 0x10(%rcx)
leaq 0x4f0(%rsp), %rax
movq %rax, 0x8(%rcx)
movabsq $0x3000000010, %rax     # imm = 0x3000000010
movq %rax, (%rcx)
leaq 0xd0(%rsp), %r14
movl $0x400, %esi            # imm = 0x400
movq %r14, %rdi
movq %r10, %rdx
callq 0x1f7b0
movl %ebx, %edi
movq %r14, %rsi
callq 0x230d4
addq $0x4d8, %rsp            # imm = 0x4D8
popq %rbx
popq %r14
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: redisLogFromHandler
void redisLogFromHandler(int level, const char *msg) {
    int fd;
    int log_to_stdout = server.logfile[0] == '\0';
    char buf[64];

    if ((level&0xff) < server.verbosity || (log_to_stdout && server.daemonize))
        return;
    fd = log_to_stdout ? STDOUT_FILENO : 
                         open(server.logfile, O_APPEND|O_CREAT|O_WRONLY, 0644);
    if (fd == -1) return;
    ll2string(buf,sizeof(buf),getpid());
    if (write(fd,"[",1) == -1) goto err;
    if (write(fd,buf,strlen(buf)) == -1) goto err;
    if (write(fd," | signal handler] (",20) == -1) goto err;
    ll2string(buf,sizeof(buf),time(NULL));
    if (write(fd,buf,strlen(buf)) == -1) goto err;
    if (write(fd,") ",2) == -1) goto err;
    if (write(fd,msg,strlen(msg)) == -1) goto err;
    if (write(fd,"\n",1) == -1) goto err;
err:
    if (!log_to_stdout) close(fd);
}

// Assembly:
movzbl %dil, %eax
cmpl 0xa7124(%rip), %eax     # 0xca40c
jl 0x2343d
pushq %rbp
pushq %r15
pushq %r14
pushq %rbx
subq $0x48, %rsp
movq %rsi, %rbx
movq 0xa7276(%rip), %rdi     # 0xca578
movb (%rdi), %r15b
testb %r15b, %r15b
jne 0x23317
cmpl $0x0, 0xa711b(%rip)     # 0xca42c
jne 0x23433
testb %r15b, %r15b
je 0x23339
movl $0x441, %esi            # imm = 0x441
movl $0x1a4, %edx            # imm = 0x1A4
xorl %eax, %eax
callq 0x1f640
movl %eax, %ebp
cmpl $-0x1, %eax
jne 0x2333e
jmp 0x23433
movl $0x1, %ebp
callq 0x1f410
movslq %eax, %rdx
movq %rsp, %rdi
movl $0x40, %esi
callq 0x300c7
leaq 0x71396(%rip), %rsi     # 0x946f0
movl $0x1, %edx
movl %ebp, %edi
callq 0x1fb30
cmpq $-0x1, %rax
je 0x23427
movq %rsp, %r14
movq %r14, %rdi
callq 0x1f4f0
movl %ebp, %edi
movq %r14, %rsi
movq %rax, %rdx
callq 0x1fb30
cmpq $-0x1, %rax
je 0x23427
leaq 0x71359(%rip), %rsi     # 0x946f2
movl $0x14, %edx
movl %ebp, %edi
callq 0x1fb30
cmpq $-0x1, %rax
je 0x23427
xorl %edi, %edi
callq 0x1fc50
movq %rsp, %r14
movl $0x40, %esi
movq %r14, %rdi
movq %rax, %rdx
callq 0x300c7
movq %r14, %rdi
callq 0x1f4f0
movl %ebp, %edi
movq %r14, %rsi
movq %rax, %rdx
callq 0x1fb30
cmpq $-0x1, %rax
je 0x23427
leaq 0x7a95a(%rip), %rsi     # 0x9dd41
movl $0x2, %edx
movl %ebp, %edi
callq 0x1fb30
cmpq $-0x1, %rax
je 0x23427
movq %rbx, %rdi
callq 0x1f4f0
movl %ebp, %edi
movq %rbx, %rsi
movq %rax, %rdx
callq 0x1fb30
cmpq $-0x1, %rax
je 0x23427
leaq 0x73376(%rip), %rsi     # 0x96791
movl $0x1, %edx
movl %ebp, %edi
callq 0x1fb30
testb %r15b, %r15b
je 0x23433
movl %ebp, %edi
callq 0x1f170
addq $0x48, %rsp
popq %rbx
popq %r14
popq %r15
popq %rbp
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: dictEncObjHash
unsigned int dictEncObjHash(const void *key) {
    robj *o = (robj*) key;

    if (sdsEncodedObject(o)) {
        return dictGenHashFunction(o->ptr, sdslen((sds)o->ptr));
    } else {
        if (o->encoding == REDIS_ENCODING_INT) {
            char buf[32];
            int len;

            len = ll2string(buf,32,(long)o->ptr);
            return dictGenHashFunction((unsigned char*)buf, len);
        } else {
            unsigned int hash;

            o = getDecodedObject(o);
            hash = dictGenHashFunction(o->ptr, sdslen((sds)o->ptr));
            decrRefCount(o);
            return hash;
        }
    }
}

// Assembly:
pushq %rbp
pushq %rbx
subq $0x28, %rsp
movl (%rdi), %eax
shrl $0x4, %eax
andl $0xf, %eax
cmpl $0x8, %eax
je 0x235e3
cmpl $0x1, %eax
je 0x235f5
testl %eax, %eax
jne 0x23615
movq 0x8(%rdi), %rdi
movl -0x8(%rdi), %esi
addq $0x28, %rsp
popq %rbx
popq %rbp
jmp 0x220bc
movq 0x8(%rdi), %rdx
movq %rsp, %rbx
movl $0x20, %esi
movq %rbx, %rdi
callq 0x300c7
movq %rbx, %rdi
movl %eax, %esi
callq 0x220bc
jmp 0x23635
callq 0x30d93
movq %rax, %rbx
movq 0x8(%rax), %rdi
movl -0x8(%rdi), %esi
callq 0x220bc
movl %eax, %ebp
movq %rbx, %rdi
callq 0x30b0c
movl %ebp, %eax
addq $0x28, %rsp
popq %rbx
popq %rbp
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: trackOperationsPerSecond
void trackOperationsPerSecond(void) {

    // 计算两次抽样之间的时间长度，毫秒格式
    long long t = mstime() - server.ops_sec_last_sample_time;

    // 计算两次抽样之间，执行了多少个命令
    long long ops = server.stat_numcommands - server.ops_sec_last_sample_ops;

    long long ops_sec;

    // 计算距离上一次抽样之后，每秒执行命令的数量
    ops_sec = t > 0 ? (ops*1000/t) : 0;

    // 将计算出的执行命令数量保存到抽样数组
    server.ops_sec_samples[server.ops_sec_idx] = ops_sec;
    // 更新抽样数组的索引
    server.ops_sec_idx = (server.ops_sec_idx+1) % REDIS_OPS_SEC_SAMPLES;
    // 更新最后一次抽样的时间
    server.ops_sec_last_sample_time = mstime();
    // 更新最后一次抽样时的执行命令数量
    server.ops_sec_last_sample_ops = server.stat_numcommands;
}

// Assembly:
pushq %r14
pushq %rbx
subq $0x18, %rsp
xorl %ebx, %ebx
leaq 0x8(%rsp), %r14
movq %r14, %rdi
xorl %esi, %esi
callq 0x1f2f0
imulq $0xf4240, (%r14), %rax  # imm = 0xF4240
addq 0x8(%r14), %rax
movabsq $0x20c49ba5e353f7cf, %r14 # imm = 0x20C49BA5E353F7CF
imulq %r14
movq %rdx, %rcx
movq %rdx, %rax
shrq $0x3f, %rax
sarq $0x7, %rcx
addq %rax, %rcx
subq 0xa68a3(%rip), %rcx     # 0xca378
jle 0x23af4
movq 0xa6812(%rip), %rax     # 0xca2f0
subq 0xa689b(%rip), %rax     # 0xca380
imulq $0x3e8, %rax, %rax      # imm = 0x3E8
cqto
idivq %rcx
movq %rax, %rbx
movslq 0xa690d(%rip), %rax     # 0xca408
leaq 0xa64a6(%rip), %rcx     # 0xc9fa8
movq %rbx, 0x3e0(%rcx,%rax,8)
leal 0x1(%rax), %ecx
leal 0x10(%rax), %edx
testl %ecx, %ecx
cmovnsl %ecx, %edx
andl $-0x10, %edx
negl %edx
addl %edx, %eax
incl %eax
movl %eax, 0xa68e4(%rip)     # 0xca408
leaq 0x8(%rsp), %rbx
movq %rbx, %rdi
xorl %esi, %esi
callq 0x1f2f0
imulq $0xf4240, (%rbx), %rax  # imm = 0xF4240
addq 0x8(%rbx), %rax
imulq %r14
movq %rdx, %rax
shrq $0x3f, %rax
sarq $0x7, %rdx
addq %rax, %rdx
movq %rdx, 0xa6822(%rip)     # 0xca378
movq 0xa6793(%rip), %rax     # 0xca2f0
movq %rax, 0xa681c(%rip)     # 0xca380
addq $0x18, %rsp
popq %rbx
popq %r14
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: getOperationsPerSecond
long long getOperationsPerSecond(void) {
    int j;
    long long sum = 0;

    // 计算所有取样值的总和
    for (j = 0; j < REDIS_OPS_SEC_SAMPLES; j++)
        sum += server.ops_sec_samples[j];

    // 计算取样的平均值
    return sum / REDIS_OPS_SEC_SAMPLES;
}

// Assembly:
pxor %xmm0, %xmm0
xorl %eax, %eax
leaq 0xa642f(%rip), %rcx     # 0xc9fa8
movdqu 0x3e0(%rcx,%rax,8), %xmm1
paddq %xmm1, %xmm0
addq $0x2, %rax
cmpq $0x10, %rax
jne 0x23b79
pshufd $0xee, %xmm0, %xmm1     # xmm1 = xmm0[2,3,2,3]
paddq %xmm0, %xmm1
movq %xmm1, %rcx
leaq 0xf(%rcx), %rax
testq %rcx, %rcx
cmovnsq %rcx, %rax
sarq $0x4, %rax
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: clientsCronHandleTimeout
int clientsCronHandleTimeout(redisClient *c) {

    // 获取当前时间
    time_t now = server.unixtime;

    // 服务器设置了 maxidletime 时间
    if (server.maxidletime &&
        // 不检查作为从服务器的客户端
        !(c->flags & REDIS_SLAVE) &&    /* no timeout for slaves */
        // 不检查作为主服务器的客户端
        !(c->flags & REDIS_MASTER) &&   /* no timeout for masters */
        // 不检查被阻塞的客户端
        !(c->flags & REDIS_BLOCKED) &&  /* no timeout for BLPOP */
        // 不检查订阅了频道的客户端
        dictSize(c->pubsub_channels) == 0 && /* no timeout for pubsub */
        // 不检查订阅了模式的客户端
        listLength(c->pubsub_patterns) == 0 &&
        // 客户端最后一次与服务器通讯的时间已经超过了 maxidletime 时间
        (now - c->lastinteraction > server.maxidletime))
    {
        redisLog(REDIS_VERBOSE,"Closing idle client");
        // 关闭超时客户端
        freeClient(c);
        return 1;
    } else if (c->flags & REDIS_BLOCKED) {

        /* Blocked OPS timeout is handled with milliseconds resolution.
         * However note that the actual resolution is limited by
         * server.hz. */
        // 获取最新的系统时间
        mstime_t now_ms = mstime();

        // 检查被 BLPOP 等命令阻塞的客户端的阻塞时间是否已经到达
        // 如果是的话，取消客户端的阻塞
        if (c->bpop.timeout != 0 && c->bpop.timeout < now_ms) {
            // 向客户端返回空回复
            replyToBlockedClientTimedOut(c);
            // 取消客户端的阻塞状态
            unblockClient(c);
        }
    }

    // 客户度没有被关闭
    return 0;
}

// Assembly:
pushq %r15
pushq %r14
pushq %rbx
subq $0x10, %rsp
movq %rdi, %rbx
movslq 0xa684f(%rip), %rcx     # 0xca410
testq %rcx, %rcx
setne %dl
movl 0x90(%rdi), %eax
testb $0x13, %al
sete %sil
andb %dl, %sil
cmpb $0x1, %sil
jne 0x23c31
movq 0x158(%rbx), %rdx
movq 0x28(%rdx), %rsi
addq 0x48(%rdx), %rsi
jne 0x23c31
movq 0x160(%rbx), %rdx
cmpq $0x0, 0x28(%rdx)
jne 0x23c31
movq 0xa6b3e(%rip), %rdx     # 0xca740
subq 0x80(%rbx), %rdx
cmpq %rcx, %rdx
jle 0x23c31
leaq 0x70afa(%rip), %rsi     # 0x9470f
movl $0x1, %r14d
movl $0x1, %edi
xorl %eax, %eax
callq 0x23223
movq %rbx, %rdi
callq 0x2e517
jmp 0x23c8f
xorl %r14d, %r14d
testb $0x10, %al
je 0x23c8f
xorl %r14d, %r14d
movq %rsp, %r15
movq %r15, %rdi
xorl %esi, %esi
callq 0x1f2f0
imulq $0xf4240, (%r15), %rax  # imm = 0xF4240
addq 0x8(%r15), %rax
movabsq $0x20c49ba5e353f7cf, %rcx # imm = 0x20C49BA5E353F7CF
imulq %rcx
movq 0x120(%rbx), %rax
testq %rax, %rax
je 0x23c8f
movq %rdx, %rcx
shrq $0x3f, %rcx
sarq $0x7, %rdx
addq %rcx, %rdx
cmpq %rdx, %rax
jge 0x23c8f
movq %rbx, %rdi
callq 0x609fc
movq %rbx, %rdi
callq 0x60977
movl %r14d, %eax
addq $0x10, %rsp
popq %rbx
popq %r14
popq %r15
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: databasesCron
void databasesCron(void) {

    // 函数先从数据库中删除过期键，然后再对数据库的大小进行修改

    /* Expire keys by random sampling. Not required for slaves
     * as master will synthesize DELs for us. */
    // 如果服务器不是从服务器，那么执行主动过期键清除
    if (server.active_expire_enabled && server.masterhost == NULL)
        // 清除模式为 CYCLE_SLOW ，这个模式会尽量多清除过期键
        activeExpireCycle(ACTIVE_EXPIRE_CYCLE_SLOW);

    /* Perform hash tables rehashing if needed, but only if there are no
     * other processes saving the DB on disk. Otherwise rehashing is bad
     * as will cause a lot of copy-on-write of memory pages. */
    // 在没有 BGSAVE 或者 BGREWRITEAOF 执行时，对哈希表进行 rehash
    if (server.rdb_child_pid == -1 && server.aof_child_pid == -1) {
        /* We use global counters so if we stop the computation at a given
         * DB we'll be able to start from the successive in the next
         * cron loop iteration. */
        static unsigned int resize_db = 0;
        static unsigned int rehash_db = 0;
        unsigned int dbs_per_call = REDIS_DBCRON_DBS_PER_CALL;
        unsigned int j;

        /* Don't test more DBs than we have. */
        // 设定要测试的数据库数量
        if (dbs_per_call > server.dbnum) dbs_per_call = server.dbnum;

        /* Resize */
        // 调整字典的大小
        for (j = 0; j < dbs_per_call; j++) {
            tryResizeHashTables(resize_db % server.dbnum);
            resize_db++;
        }

        /* Rehash */
        // 对字典进行渐进式 rehash
        if (server.activerehashing) {
            for (j = 0; j < dbs_per_call; j++) {
                int work_done = incrementallyRehash(rehash_db % server.dbnum);
                rehash_db++;
                if (work_done) {
                    /* If the function did some work, stop here, we'll do
                     * more at the next cron loop. */
                    break;
                }
            }
        }
    }
}

// Assembly:
pushq %rbp
pushq %rbx
pushq %rax
cmpl $0x0, 0xa6690(%rip)     # 0xca418
je 0x23d9b
cmpq $0x0, 0xa6866(%rip)     # 0xca5f8
jne 0x23d9b
xorl %edi, %edi
callq 0x237cd
cmpl $-0x1, 0xa6776(%rip)    # 0xca518
jne 0x23e2d
cmpl $-0x1, 0xa66fd(%rip)    # 0xca4ac
jne 0x23e2d
movl 0xa6671(%rip), %eax     # 0xca428
cmpl $0x10, %eax
movl $0x10, %ebx
cmovbl %eax, %ebx
testl %eax, %eax
je 0x23e2d
movl 0xa6a2c(%rip), %eax     # 0xca7f8
movl %ebx, %ebp
xorl %edx, %edx
divl 0xa6652(%rip)           # 0xca428
movl %edx, %edi
callq 0x23678
movl 0xa6a15(%rip), %eax     # 0xca7f8
incl %eax
movl %eax, 0xa6a0d(%rip)     # 0xca7f8
decl %ebp
jne 0x23dce
cmpl $0x0, 0xa61ea(%rip)     # 0xc9fe0
je 0x23e2d
movl 0xa69fe(%rip), %eax     # 0xca7fc
decl %ebx
xorl %edx, %edx
divl 0xa6620(%rip)           # 0xca428
movl %edx, %edi
callq 0x2370a
movl %eax, %ecx
movl 0xa69e5(%rip), %eax     # 0xca7fc
incl %eax
movl %eax, 0xa69dd(%rip)     # 0xca7fc
subl $0x1, %ebx
setb %dl
testl %ecx, %ecx
jne 0x23e2d
testb %dl, %dl
je 0x23e00
addq $0x8, %rsp
popq %rbx
popq %rbp
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: beforeSleep
void beforeSleep(struct aeEventLoop *eventLoop) {
    REDIS_NOTUSED(eventLoop);

    /* Run a fast expire cycle (the called function will return
     * ASAP if a fast cycle is not needed). */
    // 执行一次快速的主动过期检查
    if (server.active_expire_enabled && server.masterhost == NULL)
        activeExpireCycle(ACTIVE_EXPIRE_CYCLE_FAST);

    /* Send all the slaves an ACK request if at least one client blocked
     * during the previous event loop iteration. */
    if (server.get_ack_from_slaves) {
        robj *argv[3];

        argv[0] = createStringObject("REPLCONF",8);
        argv[1] = createStringObject("GETACK",6);
        argv[2] = createStringObject("*",1); /* Not used argument. */
        replicationFeedSlaves(server.slaves, server.slaveseldb, argv, 3);
        decrRefCount(argv[0]);
        decrRefCount(argv[1]);
        decrRefCount(argv[2]);
        server.get_ack_from_slaves = 0;
    }

    /* Unblock all the clients blocked for synchronous replication
     * in WAIT. */
    if (listLength(server.clients_waiting_acks))
        processClientsWaitingReplicas();

    /* Try to process pending commands for clients that were just unblocked. */
    if (listLength(server.unblocked_clients))
        processUnblockedClients();

    /* Write the AOF buffer on disk */
    // 将 AOF 缓冲区的内容写入到 AOF 文件
    flushAppendOnlyFile(0);

    /* Call the Redis Cluster before sleep function. */
    // 在进入下个事件循环前，执行一些集群收尾工作
    if (server.cluster_enabled) clusterBeforeSleep();
}

// Assembly:
pushq %rbx
subq $0x20, %rsp
cmpl $0x0, 0xa6017(%rip)     # 0xca418
je 0x24417
cmpq $0x0, 0xa61ed(%rip)     # 0xca5f8
jne 0x24417
movl $0x1, %edi
callq 0x237cd
cmpl $0x0, 0xa62a2(%rip)     # 0xca6c0
je 0x2449f
leaq 0x7044d(%rip), %rdi     # 0x94874
movl $0x8, %esi
callq 0x3068f
movq %rsp, %rbx
movq %rax, (%rbx)
leaq 0x7043f(%rip), %rdi     # 0x9487d
movl $0x6, %esi
callq 0x3068f
movq %rax, 0x8(%rbx)
leaq 0x70431(%rip), %rdi     # 0x94884
movl $0x1, %esi
callq 0x3068f
movq %rax, 0x10(%rbx)
movq 0xa5d00(%rip), %rdi     # 0xca168
movl 0xa6126(%rip), %esi     # 0xca594
movq %rbx, %rdx
movl $0x3, %ecx
callq 0x33795
movq (%rbx), %rdi
callq 0x30b0c
movq 0x8(%rbx), %rdi
callq 0x30b0c
movq 0x10(%rbx), %rdi
callq 0x30b0c
movl $0x0, 0xa6221(%rip)     # 0xca6c0
movq 0xa6212(%rip), %rax     # 0xca6b8
cmpq $0x0, 0x28(%rax)
je 0x244b2
callq 0x35d44
movq 0xa6227(%rip), %rax     # 0xca6e0
cmpq $0x0, 0x28(%rax)
je 0x244c5
callq 0x608e7
xorl %edi, %edi
callq 0x491a7
cmpl $0x0, 0xa6291(%rip)     # 0xca764
je 0x244da
callq 0x53d34
addq $0x20, %rsp
popq %rbx
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: resetServerStats
void resetServerStats(void) {
    server.stat_numcommands = 0;
    server.stat_numconnections = 0;
    server.stat_expiredkeys = 0;
    server.stat_evictedkeys = 0;
    server.stat_keyspace_misses = 0;
    server.stat_keyspace_hits = 0;
    server.stat_fork_time = 0;
    server.stat_rejected_conn = 0;
    server.stat_sync_full = 0;
    server.stat_sync_partial_ok = 0;
    server.stat_sync_partial_err = 0;
    memset(server.ops_sec_samples,0,sizeof(server.ops_sec_samples));
    server.ops_sec_idx = 0;
    server.ops_sec_last_sample_time = mstime();
    server.ops_sec_last_sample_ops = 0;
}

// Assembly:
pushq %r14
pushq %rbx
subq $0x18, %rsp
xorps %xmm0, %xmm0
movups %xmm0, 0xa4ec1(%rip)    # 0xca310
movups %xmm0, 0xa4eaa(%rip)    # 0xca300
movups %xmm0, 0xa4e93(%rip)    # 0xca2f0
movups %xmm0, 0xa4ec4(%rip)    # 0xca328
movups %xmm0, 0xa4ecd(%rip)    # 0xca338
xorl %r14d, %r14d
movq %r14, 0xa4ed3(%rip)     # 0xca348
leaq 0xa4f0c(%rip), %rdi     # 0xca388
movl $0x84, %edx
xorl %esi, %esi
callq 0x1f110
leaq 0x8(%rsp), %rbx
movq %rbx, %rdi
xorl %esi, %esi
callq 0x1f2f0
imulq $0xf4240, (%rbx), %rax  # imm = 0xF4240
addq 0x8(%rbx), %rax
movabsq $0x20c49ba5e353f7cf, %rcx # imm = 0x20C49BA5E353F7CF
imulq %rcx
movq %rdx, %rax
shrq $0x3f, %rax
sarq $0x7, %rdx
addq %rax, %rdx
movq %rdx, 0xa4eb4(%rip)     # 0xca378
movq %r14, 0xa4eb5(%rip)     # 0xca380
addq $0x18, %rsp
popq %rbx
popq %r14
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: lookupCommandOrOriginal
struct redisCommand *lookupCommandOrOriginal(sds name) {

    // 查找当前表
    struct redisCommand *cmd = dictFetchValue(server.commands, name);

    // 如果有需要的话，查找原始表
    if (!cmd) cmd = dictFetchValue(server.orig_commands,name);

    return cmd;
}

// Assembly:
pushq %rbx
movq %rdi, %rbx
movq 0xa4386(%rip), %rdi     # 0xc9fc0
movq %rbx, %rsi
callq 0x229cf
testq %rax, %rax
je 0x25c49
popq %rbx
retq
movq 0xa4378(%rip), %rdi     # 0xc9fc8
movq %rbx, %rsi
popq %rbx
jmp 0x229cf
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: propagate
void propagate(struct redisCommand *cmd, int dbid, robj **argv, int argc,
               int flags)
{
    // 传播到 AOF
    if (server.aof_state != REDIS_AOF_OFF && flags & REDIS_PROPAGATE_AOF)
        feedAppendOnlyFile(cmd,dbid,argv,argc);

    // 传播到 slave
    if (flags & REDIS_PROPAGATE_REPL)
        replicationFeedSlaves(server.slaves,dbid,argv,argc);
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %rbx
pushq %rax
movl %r8d, %r15d
movl %ecx, %ebx
movq %rdx, %r14
movl %esi, %ebp
testb $0x1, %r15b
je 0x25c85
cmpl $0x0, 0xa4801(%rip)     # 0xca478
je 0x25c85
movl %ebp, %esi
movq %r14, %rdx
movl %ebx, %ecx
callq 0x498f0
testb $0x2, %r15b
jne 0x25c96
addq $0x8, %rsp
popq %rbx
popq %r14
popq %r15
popq %rbp
retq
movq 0xa44cb(%rip), %rdi     # 0xca168
movl %ebp, %esi
movq %r14, %rdx
movl %ebx, %ecx
addq $0x8, %rsp
popq %rbx
popq %r14
popq %r15
popq %rbp
jmp 0x33795
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: closeListeningSockets
void closeListeningSockets(int unlink_unix_socket) {
    int j;

    for (j = 0; j < server.ipfd_count; j++) close(server.ipfd[j]);

    if (server.sofd != -1) close(server.sofd);

    if (server.cluster_enabled)
        for (j = 0; j < server.cfd_count; j++) close(server.cfd[j]);

    if (unlink_unix_socket && server.unixsocket) {
        redisLog(REDIS_NOTICE,"Removing the unix socket file.");
        unlink(server.unixsocket); /* don't care if this fails */
    }
}

// Assembly:
pushq %r15
pushq %r14
pushq %rbx
movl %edi, %ebx
cmpl $0x0, 0xa3928(%rip)     # 0xca10c
leaq 0xa37bd(%rip), %r14     # 0xc9fa8
jle 0x2680c
xorl %r15d, %r15d
movl 0x124(%r14,%r15,4), %edi
callq 0x1f170
incq %r15
movslq 0xa3905(%rip), %rax     # 0xca10c
cmpq %rax, %r15
jl 0x267f0
movl 0xa38fe(%rip), %edi     # 0xca110
cmpl $-0x1, %edi
je 0x2681c
callq 0x1f170
cmpl $0x0, 0xa3f41(%rip)     # 0xca764
je 0x2684d
cmpl $0x0, 0xa3928(%rip)     # 0xca154
jle 0x2684d
xorl %r15d, %r15d
movl 0x16c(%r14,%r15,4), %edi
callq 0x1f170
incq %r15
movslq 0xa390c(%rip), %rax     # 0xca154
cmpq %rax, %r15
jl 0x26831
testl %ebx, %ebx
je 0x2687f
cmpq $0x0, 0xa3867(%rip)     # 0xca0c0
je 0x2687f
leaq 0x6eb4e(%rip), %rsi     # 0x953b0
movl $0x2, %edi
xorl %eax, %eax
callq 0x23223
movq 0xa384b(%rip), %rdi     # 0xca0c0
popq %rbx
popq %r14
popq %r15
jmp 0x1f3a0
popq %rbx
popq %r14
popq %r15
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: time_independent_strcmp
int time_independent_strcmp(char *a, char *b) {
    char bufa[REDIS_AUTHPASS_MAX_LEN], bufb[REDIS_AUTHPASS_MAX_LEN];
    /* The above two strlen perform len(a) + len(b) operations where either
     * a or b are fixed (our password) length, and the difference is only
     * relative to the length of the user provided string, so no information
     * leak is possible in the following two lines of code. */
    int alen = strlen(a);
    int blen = strlen(b);
    int j;
    int diff = 0;

    /* We can't compare strings longer than our static buffers.
     * Note that this will never pass the first test in practical circumstances
     * so there is no info leak. */
    if (alen > sizeof(bufa) || blen > sizeof(bufb)) return 1;

    memset(bufa,0,sizeof(bufa));        /* Constant time. */
    memset(bufb,0,sizeof(bufb));        /* Constant time. */
    /* Again the time of the following two copies is proportional to
     * len(a) + len(b) so no info is leaked. */
    memcpy(bufa,a,alen);
    memcpy(bufb,b,blen);

    /* Always compare all the chars in the two buffers without
     * conditional expressions. */
    for (j = 0; j < sizeof(bufa); j++) {
        diff |= (bufa[j] ^ bufb[j]);
    }
    /* Length must be equal as well. */
    diff |= alen ^ blen;
    return diff; /* If zero strings are the same. */
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x418, %rsp            # imm = 0x418
movq %rsi, %r15
movq %rdi, %r12
callq 0x1f4f0
movq %rax, %rbx
movq %r15, %rdi
callq 0x1f4f0
movq %rax, %r14
movslq %ebx, %rbp
movl $0x201, %eax            # imm = 0x201
cmpq %rax, %rbp
setae %cl
movslq %r14d, %r13
cmpq %rax, %r13
setae %al
orb %cl, %al
movl $0x1, %eax
jne 0x26ace
movq %rbx, 0x8(%rsp)
leaq 0x210(%rsp), %rdi
xorl %ebx, %ebx
movl $0x200, %edx            # imm = 0x200
xorl %esi, %esi
callq 0x1f110
leaq 0x10(%rsp), %rdi
movl $0x200, %edx            # imm = 0x200
xorl %esi, %esi
callq 0x1f110
leaq 0x210(%rsp), %rdi
movq %r12, %rsi
movq %rbp, %rdx
callq 0x1fbd0
leaq 0x10(%rsp), %rdi
movq %r15, %rsi
movq %r13, %rdx
callq 0x1fbd0
pxor %xmm0, %xmm0
movl 0x10(%rsp,%rbx), %eax
xorl 0x210(%rsp,%rbx), %eax
movd %eax, %xmm1
punpcklbw %xmm1, %xmm1    # xmm1 = xmm1[0,0,1,1,2,2,3,3,4,4,5,5,6,6,7,7]
punpcklwd %xmm1, %xmm1    # xmm1 = xmm1[0,0,1,1,2,2,3,3]
psrad $0x18, %xmm1
por %xmm1, %xmm0
addq $0x4, %rbx
cmpq $0x200, %rbx            # imm = 0x200
jne 0x26a80
pshufd $0xee, %xmm0, %xmm1     # xmm1 = xmm0[2,3,2,3]
por %xmm0, %xmm1
pshufd $0x55, %xmm1, %xmm0     # xmm0 = xmm1[1,1,1,1]
por %xmm1, %xmm0
movd %xmm0, %eax
xorl 0x8(%rsp), %r14d
orl %eax, %r14d
movl %r14d, %eax
addq $0x418, %rsp            # imm = 0x418
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: bytesToHuman
void bytesToHuman(char *s, unsigned long long n) {
    double d;

    if (n < 1024) {
        /* Bytes */
        sprintf(s,"%lluB",n);
        return;
    } else if (n < (1024*1024)) {
        d = (double)n/(1024);
        sprintf(s,"%.2fK",d);
    } else if (n < (1024LL*1024*1024)) {
        d = (double)n/(1024*1024);
        sprintf(s,"%.2fM",d);
    } else if (n < (1024LL*1024*1024*1024)) {
        d = (double)n/(1024LL*1024*1024);
        sprintf(s,"%.2fG",d);
    }
}

// Assembly:
movq %rsi, %rdx
cmpq $0x3ff, %rsi            # imm = 0x3FF
ja 0x26afa
leaq 0x6ea50(%rip), %rsi     # 0x95543
xorl %eax, %eax
jmp 0x1f570
cmpq $0xfffff, %rdx          # imm = 0xFFFFF
ja 0x26b19
cvtsi2sd %rdx, %xmm0
mulsd 0x6d798(%rip), %xmm0    # 0x942a8
leaq 0x6ea32(%rip), %rsi     # 0x95549
jmp 0x26b55
cmpq $0x3fffffff, %rdx       # imm = 0x3FFFFFFF
ja 0x26b38
cvtsi2sd %rdx, %xmm0
mulsd 0x6d771(%rip), %xmm0    # 0x942a0
leaq 0x6ea19(%rip), %rsi     # 0x9554f
jmp 0x26b55
movq %rdx, %rax
shrq $0x28, %rax
jne 0x26b5c
cvtsi2sd %rdx, %xmm0
mulsd 0x6d74a(%rip), %xmm0    # 0x94298
leaq 0x6ea00(%rip), %rsi     # 0x95555
movb $0x1, %al
jmp 0x1f570
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: redisAsciiArt
void redisAsciiArt(void) {
#include "asciilogo.h"
    char *buf = zmalloc(1024*16);
    char *mode = "stand alone";

    if (server.cluster_enabled) mode = "cluster";
    else if (server.sentinel_mode) mode = "sentinel";

    snprintf(buf,1024*16,ascii_logo,
        REDIS_VERSION,
        redisGitSHA1(),
        strtol(redisGitDirty(),NULL,10) > 0,
        (sizeof(long) == 8) ? "64" : "32",
        mode, server.port,
        (long) getpid()
    );
    redisLogRaw(REDIS_NOTICE|REDIS_LOG_RAW,buf);
    zfree(buf);
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r12
pushq %rbx
movl $0x4000, %edi           # imm = 0x4000
callq 0x299b5
cmpl $0x0, 0xa22cb(%rip)     # 0xca02c
leaq 0x6ea2b(%rip), %rcx     # 0x96793
leaq 0x7796b(%rip), %rdx     # 0x9f6da
cmoveq %rcx, %rdx
cmpl $0x0, 0xa29ea(%rip)     # 0xca764
movq %rax, %rbx
leaq 0x6c8a3(%rip), %r15     # 0x94627
cmoveq %rdx, %r15
callq 0x2cf50
movq %rax, %r14
callq 0x2cf58
movq %rax, %rdi
xorl %esi, %esi
movl $0xa, %edx
callq 0x1f6d0
xorl %ebp, %ebp
testq %rax, %rax
setg %bpl
movl 0xa227c(%rip), %r12d    # 0xca030
callq 0x1f410
movslq %eax, %r10
leaq 0x6e9dc(%rip), %r11     # 0x9679f
leaq 0x6e55c(%rip), %rdx     # 0x96326
leaq 0x6ebe9(%rip), %rcx     # 0x969ba
movl $0x4000, %esi           # imm = 0x4000
movq %rbx, %rdi
movq %r14, %r8
movl %ebp, %r9d
xorl %eax, %eax
pushq %r10
pushq %r12
pushq %r15
pushq %r11
callq 0x1f120
addq $0x20, %rsp
movl $0x402, %edi            # imm = 0x402
movq %rbx, %rsi
callq 0x230d4
movq %rbx, %rdi
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
jmp 0x29af7
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/redis.c
// Function: loadDataFromDisk
void loadDataFromDisk(void) {
    // 记录开始时间
    long long start = ustime();

    // AOF 持久化已打开？
    if (server.aof_state == REDIS_AOF_ON) {
        // 尝试载入 AOF 文件
        if (loadAppendOnlyFile(server.aof_filename) == REDIS_OK)
            // 打印载入信息，并计算载入耗时长度
            redisLog(REDIS_NOTICE,"DB loaded from append only file: %.3f seconds",(float)(ustime()-start)/1000000);
    // AOF 持久化未打开
    } else {
        // 尝试载入 RDB 文件
        if (rdbLoad(server.rdb_filename) == REDIS_OK) {
            // 打印载入信息，并计算载入耗时长度
            redisLog(REDIS_NOTICE,"DB loaded from disk: %.3f seconds",
                (float)(ustime()-start)/1000000);
        } else if (errno != ENOENT) {
            redisLog(REDIS_WARNING,"Fatal error loading the DB: %s. Exiting.",strerror(errno));
            exit(1);
        }
    }
}

// Assembly:
pushq %r14
pushq %rbx
subq $0x18, %rsp
leaq 0x8(%rsp), %rbx
movq %rbx, %rdi
xorl %esi, %esi
callq 0x1f2f0
imulq $-0xf4240, (%rbx), %r14 # imm = 0xFFF0BDC0
subq 0x8(%rbx), %r14
cmpl $0x1, 0xa25ba(%rip)     # 0xca478
jne 0x27eef
movq 0xa25b9(%rip), %rdi     # 0xca480
callq 0x49b45
testl %eax, %eax
jne 0x27f0b
leaq 0x8(%rsp), %rbx
movq %rbx, %rdi
xorl %esi, %esi
callq 0x1f2f0
movq (%rbx), %rcx
movq 0x8(%rbx), %rax
leaq 0x6e8cf(%rip), %rsi     # 0x967bc
jmp 0x27f30
movq 0xa263a(%rip), %rdi     # 0xca530
callq 0x3829e
testl %eax, %eax
je 0x27f13
callq 0x1f810
movl (%rax), %edi
cmpl $0x2, %edi
jne 0x27f61
addq $0x18, %rsp
popq %rbx
popq %r14
retq
leaq 0x8(%rsp), %rbx
movq %rbx, %rdi
xorl %esi, %esi
callq 0x1f2f0
movq (%rbx), %rcx
movq 0x8(%rbx), %rax
leaq 0x6e8ba(%rip), %rsi     # 0x967ea
imulq $0xf4240, %rcx, %rcx    # imm = 0xF4240
addq %rax, %rcx
addq %r14, %rcx
cvtsi2ss %rcx, %xmm0
divss 0x6c36e(%rip), %xmm0    # 0x942b8
cvtss2sd %xmm0, %xmm0
movl $0x2, %edi
movb $0x1, %al
addq $0x18, %rsp
popq %rbx
popq %r14
jmp 0x23223
callq 0x1f630
leaq 0x6e89f(%rip), %rsi     # 0x9680c
movl $0x3, %edi
movq %rax, %rdx
xorl %eax, %eax
callq 0x23223
movl $0x1, %edi
callq 0x1f2b0
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/sds.c
// Function: sdsnewlen
sds sdsnewlen(const void *init, size_t initlen) {

    struct sdshdr *sh;

    // 根据是否有初始化内容，选择适当的内存分配方式
    // T = O(N)
    if (init) {
        // zmalloc 不初始化所分配的内存
        sh = zmalloc(sizeof(struct sdshdr)+initlen+1);
    } else {
        // zcalloc 将分配的内存全部初始化为 0
        sh = zcalloc(sizeof(struct sdshdr)+initlen+1);
    }

    // 内存分配失败，返回
    if (sh == NULL) return NULL;

    // 设置初始化长度
    sh->len = initlen;
    // 新 sds 不预留任何空间
    sh->free = 0;
    // 如果有指定初始化内容，将它们复制到 sdshdr 的 buf 中
    // T = O(N)
    if (initlen && init)
        memcpy(sh->buf, init, initlen);
    // 以 \0 结尾
    sh->buf[initlen] = '\0';

    // 返回 buf 部分，而不是整个 sdshdr
    return (char*)sh->buf;
}

// Assembly:
pushq %r15
pushq %r14
pushq %rbx
movq %rsi, %rbx
movq %rdi, %r14
leaq 0x9(%rsi), %rdi
testq %r14, %r14
je 0x2840f
callq 0x299b5
jmp 0x28414
callq 0x29a07
movq %rax, %r15
testq %rax, %rax
je 0x28452
testq %r14, %r14
sete %al
movl %ebx, (%r15)
movl $0x0, 0x4(%r15)
testq %rbx, %rbx
sete %cl
orb %al, %cl
jne 0x28446
leaq 0x8(%r15), %rdi
movq %r14, %rsi
movq %rbx, %rdx
callq 0x1fbd0
movb $0x0, 0x8(%r15,%rbx)
addq $0x8, %r15
jmp 0x28455
xorl %r15d, %r15d
movq %r15, %rax
popq %rbx
popq %r14
popq %r15
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/sds.c
// Function: sdsIncrLen
void sdsIncrLen(sds s, int incr) {
    struct sdshdr *sh = (void*) (s-(sizeof(struct sdshdr)));

    // 确保 sds 空间足够
    assert(sh->free >= incr);

    // 更新属性
    sh->len += incr;
    sh->free -= incr;

    // 这个 assert 其实可以忽略
    // 因为前一个 assert 已经确保 sh->free - incr >= 0 了
    assert(sh->free >= 0);

    // 放置新的结尾符号
    s[sh->len] = '\0';
}

// Assembly:
pushq %rax
movl -0x4(%rdi), %eax
cmpl %esi, %eax
jl 0x285eb
movslq -0x8(%rdi), %rdx
movslq %esi, %rcx
addq %rdx, %rcx
movl %ecx, -0x8(%rdi)
subl %esi, %eax
movl %eax, -0x4(%rdi)
js 0x2860a
movb $0x0, (%rdi,%rcx)
popq %rax
retq
leaq 0x6e5da(%rip), %rdi     # 0x96bcc
leaq 0x6e5e4(%rip), %rsi     # 0x96bdd
leaq 0x6e5e3(%rip), %rcx     # 0x96be3
movl $0x164, %edx            # imm = 0x164
callq 0x1f2c0
leaq 0x6e5ec(%rip), %rdi     # 0x96bfd
leaq 0x6e5c5(%rip), %rsi     # 0x96bdd
leaq 0x6e5c4(%rip), %rcx     # 0x96be3
movl $0x16c, %edx            # imm = 0x16C
callq 0x1f2c0
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/sds.c
// Function: sdsgrowzero
sds sdsgrowzero(sds s, size_t len) {
    struct sdshdr *sh = (void*)(s-(sizeof(struct sdshdr)));
    size_t totlen, curlen = sh->len;

    // 如果 len 比字符串的现有长度小，
    // 那么直接返回，不做动作
    if (len <= curlen) return s;

    // 扩展 sds
    // T = O(N)
    s = sdsMakeRoomFor(s,len-curlen);
    // 如果内存不足，直接返回
    if (s == NULL) return NULL;

    /* Make sure added region doesn't contain garbage */
    // 将新分配的空间用 0 填充，防止出现垃圾内容
    // T = O(N)
    sh = (void*)(s-(sizeof(struct sdshdr)));
    memset(s+curlen,0,(len-curlen+1)); /* also set trailing \0 byte */

    // 更新属性
    totlen = sh->len+sh->free;
    sh->len = len;
    sh->free = totlen-sh->len;

    // 返回新的 sds
    return s;
}

// Assembly:
pushq %r15
pushq %r14
pushq %r12
pushq %rbx
pushq %rax
movq %rdi, %rbx
movslq -0x8(%rdi), %r12
movq %rsi, %r15
subq %r12, %r15
jbe 0x2867a
movq %rsi, %r14
movq %rbx, %rdi
movq %r15, %rsi
callq 0x28543
testq %rax, %rax
je 0x28678
movq %rax, %rbx
addq %rax, %r12
incq %r15
movq %r12, %rdi
xorl %esi, %esi
movq %r15, %rdx
callq 0x1f110
movl -0x8(%rbx), %eax
movl %r14d, -0x8(%rbx)
subl %r14d, %eax
addl %eax, -0x4(%rbx)
jmp 0x2867a
xorl %ebx, %ebx
movq %rbx, %rax
addq $0x8, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/sds.c
// Function: sdscatlen
sds sdscatlen(sds s, const void *t, size_t len) {
    
    struct sdshdr *sh;
    
    // 原有字符串长度
    size_t curlen = sdslen(s);

    // 扩展 sds 空间
    // T = O(N)
    s = sdsMakeRoomFor(s,len);

    // 内存不足？直接返回
    if (s == NULL) return NULL;

    // 复制 t 中的内容到字符串后部
    // T = O(N)
    sh = (void*) (s-(sizeof(struct sdshdr)));
    memcpy(s+curlen, t, len);

    // 更新属性
    sh->len = curlen+len;
    sh->free = sh->free-len;

    // 添加新结尾符号
    s[curlen+len] = '\0';

    // 返回新 sds
    return s;
}

// Assembly:
pushq %r15
pushq %r14
pushq %r12
pushq %rbx
pushq %rax
movq %rdx, %rbx
movq %rsi, %r15
movslq -0x8(%rdi), %r12
movq %rdx, %rsi
callq 0x28543
movq %rax, %r14
testq %rax, %rax
je 0x286cc
movq %r14, %rdi
addq %r12, %rdi
movq %r15, %rsi
movq %rbx, %rdx
callq 0x1fbd0
addq %rbx, %r12
movl %r12d, -0x8(%r14)
subl %ebx, -0x4(%r14)
movb $0x0, (%r14,%r12)
movq %r14, %rax
addq $0x8, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/sds.c
// Function: sdscpylen
sds sdscpylen(sds s, const char *t, size_t len) {

    struct sdshdr *sh = (void*) (s-(sizeof(struct sdshdr)));

    // sds 现有 buf 的长度
    size_t totlen = sh->free+sh->len;

    // 如果 s 的 buf 长度不满足 len ，那么扩展它
    if (totlen < len) {
        // T = O(N)
        s = sdsMakeRoomFor(s,len-sh->len);
        if (s == NULL) return NULL;
        sh = (void*) (s-(sizeof(struct sdshdr)));
        totlen = sh->free+sh->len;
    }

    // 复制内容
    // T = O(N)
    memcpy(s, t, len);

    // 添加终结符号
    s[len] = '\0';

    // 更新属性
    sh->len = len;
    sh->free = totlen-len;

    // 返回新的 sds
    return s;
}

// Assembly:
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
movq %rdx, %r14
movq %rsi, %r15
movq %rdi, %rbx
movslq -0x4(%rdi), %r12
movslq -0x8(%rdi), %rax
addq %rax, %r12
cmpq %rdx, %r12
jae 0x287da
movq %r14, %rsi
subq %rax, %rsi
movq %rbx, %rdi
callq 0x28543
testq %rax, %rax
je 0x28809
movq %rax, %rbx
movq %rax, %r13
addq $-0x8, %r13
movl -0x8(%rax), %r12d
addl -0x4(%rax), %r12d
jmp 0x287de
leaq -0x8(%rbx), %r13
movq %rbx, %rdi
movq %r15, %rsi
movq %r14, %rdx
callq 0x1fbd0
movb $0x0, (%rbx,%r14)
movl %r14d, -0x8(%rbx)
subl %r14d, %r12d
movl %r12d, 0x4(%r13)
movq %rbx, %rax
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
retq
xorl %ebx, %ebx
jmp 0x287fc
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/sds.c
// Function: sdscatvprintf
sds sdscatvprintf(sds s, const char *fmt, va_list ap) {
    va_list cpy;
    char staticbuf[1024], *buf = staticbuf, *t;
    size_t buflen = strlen(fmt)*2;

    /* We try to start using a static buffer for speed.
     * If not possible we revert to heap allocation. */
    if (buflen > sizeof(staticbuf)) {
        buf = zmalloc(buflen);
        if (buf == NULL) return NULL;
    } else {
        buflen = sizeof(staticbuf);
    }

    /* Try with buffers two times bigger every time we fail to
     * fit the string in the current buffer size. */
    while(1) {
        buf[buflen-2] = '\0';
        va_copy(cpy,ap);
        // T = O(N)
        vsnprintf(buf, buflen, fmt, cpy);
        if (buf[buflen-2] != '\0') {
            if (buf != staticbuf) zfree(buf);
            buflen *= 2;
            buf = zmalloc(buflen);
            if (buf == NULL) return NULL;
            continue;
        }
        break;
    }

    /* Finally concat the obtained string to the SDS string and return it. */
    t = sdscat(s, buf);
    if (buf != staticbuf) zfree(buf);
    return t;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x438, %rsp            # imm = 0x438
movq %rdx, %r14
movq %rsi, %r15
movq %rdi, 0x8(%rsp)
movq %rsi, %rdi
callq 0x1f4f0
movq %rax, %rbx
addq %rax, %rbx
movl $0x400, %ebp            # imm = 0x400
leaq 0x30(%rsp), %r12
movq %r12, %r13
cmpq $0x401, %rbx            # imm = 0x401
jb 0x289cd
movq %rbx, %rdi
callq 0x299b5
movq %rax, %r13
movq %rbx, %rbp
testq %rax, %rax
je 0x28a23
leaq 0x10(%rsp), %rbx
movb $0x0, -0x2(%rbp,%r13)
movq 0x10(%r14), %rax
movq %rax, 0x20(%rsp)
movups (%r14), %xmm0
movaps %xmm0, 0x10(%rsp)
movq %r13, %rdi
movq %rbp, %rsi
movq %r15, %rdx
movq %rbx, %rcx
callq 0x1f7b0
cmpb $0x0, -0x2(%rbp,%r13)
je 0x28a27
cmpq %r12, %r13
je 0x28a10
movq %r13, %rdi
callq 0x29af7
addq %rbp, %rbp
movq %rbp, %rdi
callq 0x299b5
movq %rax, %r13
testq %rax, %rax
jne 0x289d2
xorl %ebx, %ebx
jmp 0x28a49
movq 0x8(%rsp), %rdi
movq %r13, %rsi
callq 0x286db
movq %rax, %rbx
leaq 0x30(%rsp), %rax
cmpq %rax, %r13
je 0x28a49
movq %r13, %rdi
callq 0x29af7
movq %rbx, %rax
addq $0x438, %rsp            # imm = 0x438
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/sds.c
// Function: sdscatprintf
sds sdscatprintf(sds s, const char *fmt, ...) {
    va_list ap;
    char *t;
    va_start(ap, fmt);
    // T = O(N^2)
    t = sdscatvprintf(s,fmt,ap);
    va_end(ap);
    return t;
}

// Assembly:
subq $0xd8, %rsp
leaq 0x20(%rsp), %r10
movq %rdx, 0x10(%r10)
movq %rcx, 0x18(%r10)
movq %r8, 0x20(%r10)
movq %r9, 0x28(%r10)
testb %al, %al
je 0x28ab5
movaps %xmm0, 0x50(%rsp)
movaps %xmm1, 0x60(%rsp)
movaps %xmm2, 0x70(%rsp)
movaps %xmm3, 0x80(%rsp)
movaps %xmm4, 0x90(%rsp)
movaps %xmm5, 0xa0(%rsp)
movaps %xmm6, 0xb0(%rsp)
movaps %xmm7, 0xc0(%rsp)
movq %rsp, %rdx
movq %r10, 0x10(%rdx)
leaq 0xe0(%rsp), %rax
movq %rax, 0x8(%rdx)
movabsq $0x3000000010, %rax     # imm = 0x3000000010
movq %rax, (%rdx)
callq 0x2897a
addq $0xd8, %rsp
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/sds.c
// Function: sdstrim
sds sdstrim(sds s, const char *cset) {
    struct sdshdr *sh = (void*) (s-(sizeof(struct sdshdr)));
    char *start, *end, *sp, *ep;
    size_t len;

    // 设置和记录指针
    sp = start = s;
    ep = end = s+sdslen(s)-1;

    // 修剪, T = O(N^2)
    while(sp <= end && strchr(cset, *sp)) sp++;
    while(ep > start && strchr(cset, *ep)) ep--;

    // 计算 trim 完毕之后剩余的字符串长度
    len = (sp > ep) ? 0 : ((ep-sp)+1);
    
    // 如果有需要，前移字符串内容
    // T = O(N)
    if (sh->buf != sp) memmove(sh->buf, sp, len);

    // 添加终结符
    sh->buf[len] = '\0';

    // 更新属性
    sh->free = sh->free+(sh->len-len);
    sh->len = len;

    // 返回修剪后的 sds
    return s;
}

// Assembly:
pushq %r15
pushq %r14
pushq %r12
pushq %rbx
pushq %rax
movq %rsi, %r15
movq %rdi, %rbx
movslq -0x8(%rdi), %rax
leaq (%rdi,%rax), %r12
decq %r12
movq %rdi, %r14
cmpq %rdi, %r12
jb 0x28ed4
movq %rbx, %r14
movsbl (%r14), %esi
movq %r15, %rdi
callq 0x1f790
testq %rax, %rax
je 0x28ed4
incq %r14
cmpq %r12, %r14
jbe 0x28ebb
cmpq %rbx, %r12
jbe 0x28ef6
movsbl (%r12), %esi
movq %r15, %rdi
callq 0x1f790
testq %rax, %rax
je 0x28ef6
decq %r12
cmpq %rbx, %r12
ja 0x28ed9
movq %rbx, %r12
xorl %r15d, %r15d
subq %r14, %r12
leaq 0x1(%r12), %rax
cmovaeq %rax, %r15
cmpq %rbx, %r14
je 0x28f18
movq %rbx, %rdi
movq %r14, %rsi
movq %r15, %rdx
callq 0x1f780
movb $0x0, (%rbx,%r15)
movl -0x4(%rbx), %eax
subl %r15d, %eax
addl -0x8(%rbx), %eax
movl %eax, -0x4(%rbx)
movl %r15d, -0x8(%rbx)
movq %rbx, %rax
addq $0x8, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/sds.c
// Function: sdsrange
void sdsrange(sds s, int start, int end) {
    struct sdshdr *sh = (void*) (s-(sizeof(struct sdshdr)));
    size_t newlen, len = sdslen(s);

    if (len == 0) return;
    if (start < 0) {
        start = len+start;
        if (start < 0) start = 0;
    }
    if (end < 0) {
        end = len+end;
        if (end < 0) end = 0;
    }
    newlen = (start > end) ? 0 : (end-start)+1;
    if (newlen != 0) {
        if (start >= (signed)len) {
            newlen = 0;
        } else if (end >= (signed)len) {
            end = len-1;
            newlen = (start > end) ? 0 : (end-start)+1;
        }
    } else {
        start = 0;
    }

    // 如果有需要，对字符串进行移动
    // T = O(N)
    if (start && newlen) memmove(sh->buf, sh->buf+start, newlen);

    // 添加终结符
    sh->buf[newlen] = 0;

    // 更新属性
    sh->free = sh->free+(sh->len-newlen);
    sh->len = newlen;
}

// Assembly:
movl -0x8(%rdi), %ecx
testl %ecx, %ecx
je 0x28fcc
pushq %r14
pushq %rbx
pushq %rax
movq %rdi, %rbx
leal (%rcx,%rsi), %eax
xorl %r14d, %r14d
testl %eax, %eax
cmovlel %r14d, %eax
testl %esi, %esi
cmovnsl %esi, %eax
leal (%rcx,%rdx), %esi
testl %esi, %esi
cmovlel %r14d, %esi
testl %edx, %edx
cmovnsl %edx, %esi
movl %esi, %edx
subl %eax, %edx
leal 0x1(%rdx), %edi
cmovbl %r14d, %edi
movl %ecx, %edx
subl %eax, %edx
jle 0x28fb0
testl %edi, %edi
je 0x28fb0
leal -0x1(%rcx), %r8d
xorl %r9d, %r9d
cmpl %r8d, %eax
cmoval %r9d, %edx
cmpl %ecx, %esi
cmovbl %edi, %edx
movslq %edx, %r14
testl %eax, %eax
je 0x28fb0
testl %edx, %edx
je 0x28fb0
movl %eax, %esi
addq %rbx, %rsi
movq %rbx, %rdi
movq %r14, %rdx
callq 0x1f780
movb $0x0, (%rbx,%r14)
movl -0x4(%rbx), %eax
subl %r14d, %eax
addl -0x8(%rbx), %eax
movl %eax, -0x4(%rbx)
movl %r14d, -0x8(%rbx)
addq $0x8, %rsp
popq %rbx
popq %r14
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/sds.c
// Function: sdsfreesplitres
void sdsfreesplitres(sds *tokens, int count) {
    if (!tokens) return;
    while(count--)
        sdsfree(tokens[count]);
    zfree(tokens);
}

// Assembly:
testq %rdi, %rdi
je 0x29258
pushq %r14
pushq %rbx
pushq %rax
movq %rdi, %rbx
testl %esi, %esi
je 0x29249
movslq %esi, %r14
movq -0x8(%rbx,%r14,8), %rdi
testq %rdi, %rdi
je 0x29244
addq $-0x8, %rdi
callq 0x29af7
decq %r14
jne 0x29231
movq %rbx, %rdi
addq $0x8, %rsp
popq %rbx
popq %r14
jmp 0x29af7
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/zmalloc.c
// Function: zmalloc_get_private_dirty
size_t zmalloc_get_private_dirty(void) {
    char line[1024];
    size_t pd = 0;
    FILE *fp = fopen("/proc/self/smaps","r");

    if (!fp) return 0;
    while(fgets(line,sizeof(line),fp) != NULL) {
        if (strncmp(line,"Private_Dirty:",14) == 0) {
            char *p = strchr(line,'k');
            if (p) {
                *p = '\0';
                pd += strtol(line+14,NULL,10) * 1024;
            }
        }
    }
    fclose(fp);
    return pd;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x408, %rsp            # imm = 0x408
leaq 0x6cf55(%rip), %rdi     # 0x96c24
leaq 0x78444(%rip), %rsi     # 0xa211a
callq 0x1f360
testq %rax, %rax
je 0x29d71
movq %rax, %rbx
movq %rsp, %rdi
movl $0x400, %esi            # imm = 0x400
movq %rax, %rdx
callq 0x1f430
testq %rax, %rax
je 0x29d76
leaq 0xe(%rsp), %r15
xorl %r14d, %r14d
movabsq $0x5f65746176697250, %r13 # imm = 0x5F65746176697250
movabsq $0x3a79747269445f65, %rbp # imm = 0x3A79747269445F65
movq %rsp, %r12
movq (%rsp), %rax
xorq %r13, %rax
movq 0x6(%rsp), %rcx
xorq %rbp, %rcx
orq %rax, %rcx
jne 0x29d5a
movq %r12, %rdi
movl $0x6b, %esi
callq 0x1f790
testq %rax, %rax
je 0x29d5a
movb $0x0, (%rax)
movq %r15, %rdi
xorl %esi, %esi
movl $0xa, %edx
callq 0x1f6d0
shlq $0xa, %rax
addq %rax, %r14
movq %r12, %rdi
movl $0x400, %esi            # imm = 0x400
movq %rbx, %rdx
callq 0x1f430
testq %rax, %rax
jne 0x29d1b
jmp 0x29d79
xorl %r14d, %r14d
jmp 0x29d81
xorl %r14d, %r14d
movq %rbx, %rdi
callq 0x1f9a0
movq %r14, %rax
addq $0x408, %rsp            # imm = 0x408
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/zipmap.c
// Function: zipmapLookupRaw
static unsigned char *zipmapLookupRaw(unsigned char *zm, unsigned char *key, unsigned int klen, unsigned int *totlen) {

    // zm+1 略过 <zmlen> 属性，将 p 指向 zipmap 的首个节点
    unsigned char *p = zm+1, *k = NULL;
    unsigned int l,llen;

    // 遍历整个 zipmap 来寻找
    // T = O(N^2)
    while(*p != ZIPMAP_END) {
        unsigned char free;

        /* Match or skip the key */
        // 计算键的长度
        l = zipmapDecodeLength(p);
        // 计算编码键的长度所需的字节数
        llen = zipmapEncodeLength(NULL,l);
        // 对比 key
        // T = O(N)
        if (key != NULL && k == NULL && l == klen && !memcmp(p+llen,key,l)) {
            /* Only return when the user doesn't care
             * for the total length of the zipmap. */
            if (totlen != NULL) {
                // 如果调用者需要知道整个 zipmap 的长度，那么记录找到的指针到变量 k
                // 之后遍历时，程序只计算 zipmap 剩余节点的长度，不再用 memcmp 进行对比
                // 因为 k 已经不为 NULL 了
                k = p;
            } else {
                // 如果调用者不需要知道整个 zipmap 的长度，那么直接返回 p 
                return p;
            }
        }

        // 越过键节点，指向值节点
        p += llen+l;

        /* Skip the value as well */
        // 计算值的长度
        l = zipmapDecodeLength(p);
        // 计算编码值的长度所需的字节数，
        // 并移动指针 p ，越过该 <len> 属性，指向 <free> 属性
        p += zipmapEncodeLength(NULL,l);
        // 取出 <free> 属性的值
        free = p[0];
        // 略过值节点，指向下一节点
        p += l+1+free; /* +1 to skip the free byte */
    }

    // 计算并记录 zipmap 的空间长度
    // + 1 是将 ZIPMAP_END 也计算在内
    if (totlen != NULL) *totlen = (unsigned int)(p-zm)+1;

    // 返回找到 key 的指针
    return k;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x18, %rsp
movq %rcx, %rbp
movl %edx, %r15d
movq %rsi, %r12
movq %rdi, 0x8(%rsp)
leaq 0x1(%rdi), %r13
movl %edx, %eax
movq %rax, 0x10(%rsp)
xorl %eax, %eax
movzbl (%r13), %r14d
cmpl $0xfe, %r14d
je 0x2a826
cmpl $0xff, %r14d
jne 0x2a82a
jmp 0x2a8c1
movl 0x1(%r13), %r14d
xorl %edx, %edx
cmpl $0xfe, %r14d
setae %dl
leal 0x1(,%rdx,4), %ebx
testq %r12, %r12
je 0x2a87e
testq %rax, %rax
jne 0x2a87e
cmpl %r15d, %r14d
jne 0x2a87c
testq %rbp, %rbp
sete 0x7(%rsp)
movl %ebx, %edi
addq %r13, %rdi
movq %r12, %rsi
movq 0x10(%rsp), %rdx
callq 0x1f6a0
testl %eax, %eax
sete %dl
movl $0x0, %eax
cmoveq %r13, %rax
testb %dl, 0x7(%rsp)
je 0x2a87e
jmp 0x2a8d4
xorl %eax, %eax
addl %r14d, %ebx
leaq (%rbx,%r13), %rdx
movzbl (%r13,%rbx), %r8d
cmpl $0xfd, %r8d
jbe 0x2a898
movl 0x1(%rdx), %r8d
xorl %r10d, %r10d
cmpl $0xfe, %r8d
setae %r10b
leaq (%rdx,%r10,4), %rdi
movzbl 0x1(%rdx,%r10,4), %edx
addl %r8d, %edx
incl %edx
leaq (%rdx,%rdi), %r13
incq %r13
jmp 0x2a80a
testq %rbp, %rbp
je 0x2a8d7
subl 0x8(%rsp), %r13d
incl %r13d
movl %r13d, (%rbp)
jmp 0x2a8d7
movq %r13, %rax
addq $0x18, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
// File: /workspace/github_c_makefile_star2_O3/nilyang[P]redis-tdd-annotation/src/zipmap.c
// Function: zipmapGet
int zipmapGet(unsigned char *zm, unsigned char *key, unsigned int klen, unsigned char **value, unsigned int *vlen) {
    unsigned char *p;

    // 在 zipmap 中按 key 查找
    // 没找到直接返回 0 
    // T = O(N^2)
    if ((p = zipmapLookupRaw(zm,key,klen,NULL)) == NULL) return 0;

    // 越过键，指向值
    p += zipmapRawKeyLength(p);
    // 取出值的长度
    *vlen = zipmapDecodeLength(p);
    // 将 *value 指向值， +1 为越过 <free> 属性
    *value = p + ZIPMAP_LEN_BYTES(*vlen) + 1;

    // 找到，返回 1 
    return 1;
}

// Assembly:
pushq %r15
pushq %r14
pushq %rbx
movq %r8, %r14
movq %rcx, %rbx
xorl %r15d, %r15d
xorl %ecx, %ecx
callq 0x2a7e1
testq %rax, %rax
je 0x2aae2
movq %rax, %rcx
movzbl (%rax), %edx
cmpl $0xfd, %edx
jbe 0x2aaa0
movl 0x1(%rcx), %edx
xorl %esi, %esi
cmpl $0xfe, %edx
setae %sil
leal (%rdx,%rsi,4), %edx
incl %edx
addq %rdx, %rax
movzbl (%rcx,%rdx), %ecx
cmpl $0xfd, %ecx
jbe 0x2aac3
movl 0x1(%rax), %ecx
movl %ecx, (%r14)
xorl %edx, %edx
cmpl $0xfe, %ecx
setae %dl
leaq (%rax,%rdx,4), %rax
addq $0x2, %rax
movq %rax, (%rbx)
movl $0x1, %r15d
movl %r15d, %eax
popq %rbx
popq %r14
popq %r15
retq