// File: /workspace/github_c_makefile_star2_O0/nilyang[P]redis-tdd-annotation/src/t_string.c
// Function: incrbyfloatCommand
void incrbyfloatCommand(redisClient *c) {
    long double incr, value;
    robj *o, *new, *aux;

    // 取出值对象
    o = lookupKeyWrite(c->db,c->argv[1]);

    // 检查对象是否存在，以及类型是否正确
    if (o != NULL && checkType(c,o,REDIS_STRING)) return;

    // 将对象的整数值保存到 value 参数中
    // 并取出 incr 参数的值
    if (getLongDoubleFromObjectOrReply(c,o,&value,NULL) != REDIS_OK ||
        getLongDoubleFromObjectOrReply(c,c->argv[2],&incr,NULL) != REDIS_OK)
        return;

    // 进行加法计算，并检查是否溢出
    value += incr;
    if (isnan(value) || isinf(value)) {
        addReplyError(c,"increment would produce NaN or Infinity");
        return;
    }

    // 用一个包含新值的新对象替换现有的值对象
    new = createStringObjectFromLongDouble(value);
    if (o)
        dbOverwrite(c->db,c->argv[1],new);
    else
        dbAdd(c->db,c->argv[1],new);

    // 向数据库发送键被修改的信号
    signalModifiedKey(c->db,c->argv[1]);

    // 发送事件通知
    notifyKeyspaceEvent(REDIS_NOTIFY_STRING,"incrbyfloat",c->argv[1],c->db->id);

    // 将服务器设为脏
    server.dirty++;

    // 回复
    addReplyBulk(c,new);

    /* Always replicate INCRBYFLOAT as a SET command with the final value
     * in order to make sure that differences in float precision or formatting
     * will not create differences in replicas or after an AOF restart. */
    // 在传播 INCRBYFLOAT 命令时，总是用 SET 命令来替换 INCRBYFLOAT 命令
    // 从而防止因为不同的浮点精度和格式化造成 AOF 重启时的数据不一致
    aux = createStringObject("SET",3);
    rewriteClientCommandArgument(c,0,aux);
    decrRefCount(aux);
    rewriteClientCommandArgument(c,2,new);
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x70, %rsp
movq %rdi, -0x8(%rbp)
movq -0x8(%rbp), %rax
movq 0x8(%rax), %rdi
movq -0x8(%rbp), %rax
movq 0x38(%rax), %rax
movq 0x8(%rax), %rsi
callq 0x3c090
movq %rax, -0x38(%rbp)
cmpq $0x0, -0x38(%rbp)
je 0x47879
movq -0x8(%rbp), %rdi
movq -0x38(%rbp), %rsi
xorl %edx, %edx
callq 0x3abb0
cmpl $0x0, %eax
je 0x47879
jmp 0x47a15
movq -0x8(%rbp), %rdi
movq -0x38(%rbp), %rsi
leaq -0x30(%rbp), %rdx
xorl %eax, %eax
movl %eax, %ecx
callq 0x3b700
cmpl $0x0, %eax
jne 0x478b5
movq -0x8(%rbp), %rdi
movq -0x8(%rbp), %rax
movq 0x38(%rax), %rax
movq 0x10(%rax), %rsi
leaq -0x20(%rbp), %rdx
xorl %eax, %eax
movl %eax, %ecx
callq 0x3b700
cmpl $0x0, %eax
je 0x478ba
jmp 0x47a15
fldt -0x20(%rbp)
fldt -0x30(%rbp)
faddp %st, %st(1)
fstpt -0x30(%rbp)
fldt -0x30(%rbp)
fucompi %st(0), %st
setp %al
testb $0x1, %al
jne 0x478ff
fldt -0x30(%rbp)
fld %st(0)
fstpt -0x60(%rbp)
movswq -0x58(%rbp), %rax
fabs
shrq $0xf, %rax
movl %eax, %ecx
orl $0x1, %ecx
xorl %eax, %eax
flds 0x9b66b(%rip)           # 0xe2f5c
fxch %st(1)
fucompi %st(1), %st
fstp %st(0)
cmovael %ecx, %eax
cmpl $0x0, %eax
je 0x47914
movq -0x8(%rbp), %rdi
leaq 0x9b6d3(%rip), %rsi     # 0xe2fdd
callq 0x35d40
jmp 0x47a15
fldt -0x30(%rbp)
movq %rsp, %rax
fstpt (%rax)
callq 0x3a410
movq %rax, -0x40(%rbp)
cmpq $0x0, -0x38(%rbp)
je 0x4794b
movq -0x8(%rbp), %rax
movq 0x8(%rax), %rdi
movq -0x8(%rbp), %rax
movq 0x38(%rax), %rax
movq 0x8(%rax), %rsi
movq -0x40(%rbp), %rdx
callq 0x3c250
jmp 0x47968
movq -0x8(%rbp), %rax
movq 0x8(%rax), %rdi
movq -0x8(%rbp), %rax
movq 0x38(%rax), %rax
movq 0x8(%rax), %rsi
movq -0x40(%rbp), %rdx
callq 0x3c160
movq -0x8(%rbp), %rax
movq 0x8(%rax), %rdi
movq -0x8(%rbp), %rax
movq 0x38(%rax), %rax
movq 0x8(%rax), %rsi
callq 0x3c3d0
movq -0x8(%rbp), %rax
movq 0x38(%rax), %rax
movq 0x8(%rax), %rdx
movq -0x8(%rbp), %rax
movq 0x8(%rax), %rax
movl 0x30(%rax), %ecx
movl $0x8, %edi
leaq 0x96b54(%rip), %rsi     # 0xde4f8
callq 0x814a0
leaq 0xcbf48(%rip), %rax     # 0x1138f8
movq 0x560(%rax), %rcx
addq $0x1, %rcx
leaq 0xcbf36(%rip), %rax     # 0x1138f8
movq %rcx, 0x560(%rax)
movq -0x8(%rbp), %rdi
movq -0x40(%rbp), %rsi
callq 0x36620
leaq 0xa2243(%rip), %rdi     # 0xe9c20
movl $0x3, %esi
callq 0x3a2e0
movq %rax, -0x48(%rbp)
movq -0x8(%rbp), %rdi
movq -0x48(%rbp), %rdx
xorl %esi, %esi
callq 0x38a50
movq -0x48(%rbp), %rdi
callq 0x3aaa0
movq -0x8(%rbp), %rdi
movq -0x40(%rbp), %rdx
movl $0x2, %esi
callq 0x38a50
addq $0x70, %rsp
popq %rbp
retq
nopl (%rax,%rax)