// File: /workspace/github_c_makefile_star2_O0/ohkimur[P]the-c-programming-language-2nd-edition-solutions/chapter_4/exercise_4_06/variables.c
// Function: main
int main(void)
{
  int type;
  double op2;
  char s[MAXOP];

  int varindex = 0;
  double var_buff[VARNUM];

  while ((type = getop(s)) != EOF)
  {
    switch (type)
    {
    case NUMBER:
      push(atof(s));
      break;

    case '+':
      push(pop() + pop());
      break;

    case '-':
      op2 = pop();
      push(pop() - op2);
      break;

    case '*':
      push(pop() * pop());
      break;

    case '/':
      op2 = pop();

      if (op2 != 0.0)
      {
        push(pop() / op2);
      }
      else
      {
        printf("Error: zero divisor.\n");
      }

      break;

    case '%':
      op2 = pop();

      if (op2 != 0.0)
      {
        push((int)pop() % (int)op2);
      }
      else
      {
        printf("Error: zero divisor.\n");
      }
      break;

    case '^':
      op2 = pop();
      push(pow(pop(), op2));
      break;

    case '~':
      push(sin(pop()));
      break;

    case 'E':
      push(exp(pop()));
      break;

    case 'H':
      view_head();
      break;

    case 'D':
      duplicate();
      break;

    case 'S':
      swap();
      break;

    case 'C':
      clear();
      break;

    case VARSET:
      var_buff[varindex++] = pop();
      printf("variable %c: %.3f\n", 'a' + varindex - 1, var_buff[varindex - 1]);
      break;

    case VARGET:
      // Check if the variable has been assigned previously
      if (var - 'a' <= (varindex - 1))
      {
        push(var_buff[var - 'a']);
      }
      else
      {
        printf("Error: undefined variable.\n");
      }
      break;

    case '\n':
      if (!is_empty())
      {
        printf("result: %.8g\n", pop());
      }
      break;

    default:
      printf("Error: unknown command %s.\n", s);
      break;
    }
  }

  return 0;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x180, %rsp            # imm = 0x180
movl $0x0, -0x4(%rbp)
movl $0x0, -0x84(%rbp)
leaq -0x80(%rbp), %rdi
callq 0x1460
movl %eax, -0x8(%rbp)
cmpl $-0x1, %eax
je 0x144f
movl -0x8(%rbp), %eax
addl $-0xa, %eax
movl %eax, %ecx
movq %rcx, -0x168(%rbp)
subl $0x74, %eax
ja 0x1438
movq -0x168(%rbp), %rax
leaq 0xe0d(%rip), %rcx       # 0x2004
movslq (%rcx,%rax,4), %rax
addq %rcx, %rax
jmpq *%rax
leaq -0x80(%rbp), %rdi
callq 0x1030
callq 0x1660
jmp 0x144a
callq 0x16c0
movsd %xmm0, -0x170(%rbp)
callq 0x16c0
movaps %xmm0, %xmm1
movsd -0x170(%rbp), %xmm0
addsd %xmm1, %xmm0
callq 0x1660
jmp 0x144a
callq 0x16c0
movsd %xmm0, -0x10(%rbp)
callq 0x16c0
subsd -0x10(%rbp), %xmm0
callq 0x1660
jmp 0x144a
callq 0x16c0
movsd %xmm0, -0x178(%rbp)
callq 0x16c0
movaps %xmm0, %xmm1
movsd -0x178(%rbp), %xmm0
mulsd %xmm1, %xmm0
callq 0x1660
jmp 0x144a
callq 0x16c0
movsd %xmm0, -0x10(%rbp)
movsd -0x10(%rbp), %xmm0
xorps %xmm1, %xmm1
ucomisd %xmm1, %xmm0
jne 0x12a3
jp 0x12a3
jmp 0x12b4
callq 0x16c0
divsd -0x10(%rbp), %xmm0
callq 0x1660
jmp 0x12c2
leaq 0xf1d(%rip), %rdi       # 0x21d8
movb $0x0, %al
callq 0x1050
jmp 0x144a
callq 0x16c0
movsd %xmm0, -0x10(%rbp)
movsd -0x10(%rbp), %xmm0
xorps %xmm1, %xmm1
ucomisd %xmm1, %xmm0
jne 0x12e3
jp 0x12e3
jmp 0x12ff
callq 0x16c0
cvttsd2si %xmm0, %eax
cvttsd2si -0x10(%rbp), %ecx
cltd
idivl %ecx
cvtsi2sd %edx, %xmm0
callq 0x1660
jmp 0x130d
leaq 0xed2(%rip), %rdi       # 0x21d8
movb $0x0, %al
callq 0x1050
jmp 0x144a
callq 0x16c0
movsd %xmm0, -0x10(%rbp)
callq 0x16c0
movsd -0x10(%rbp), %xmm1
callq 0x1040
callq 0x1660
jmp 0x144a
callq 0x16c0
callq 0x1070
callq 0x1660
jmp 0x144a
callq 0x16c0
callq 0x1080
callq 0x1660
jmp 0x144a
callq 0x1720
jmp 0x144a
callq 0x1770
jmp 0x144a
callq 0x17a0
jmp 0x144a
callq 0x17e0
jmp 0x144a
callq 0x16c0
movl -0x84(%rbp), %eax
movl %eax, %ecx
addl $0x1, %ecx
movl %ecx, -0x84(%rbp)
cltq
movsd %xmm0, -0x160(%rbp,%rax,8)
movl -0x84(%rbp), %esi
addl $0x61, %esi
subl $0x1, %esi
movl -0x84(%rbp), %eax
subl $0x1, %eax
cltq
movsd -0x160(%rbp,%rax,8), %xmm0
leaq 0xe21(%rip), %rdi       # 0x21ee
movb $0x1, %al
callq 0x1050
jmp 0x144a
movsbl 0x2c83(%rip), %eax      # 0x4060
subl $0x61, %eax
movl -0x84(%rbp), %ecx
subl $0x1, %ecx
cmpl %ecx, %eax
jg 0x1409
movsbl 0x2c6c(%rip), %eax      # 0x4060
subl $0x61, %eax
cltq
movsd -0x160(%rbp,%rax,8), %xmm0
callq 0x1660
jmp 0x1417
leaq 0xdf1(%rip), %rdi       # 0x2201
movb $0x0, %al
callq 0x1050
jmp 0x144a
callq 0x1820
cmpl $0x0, %eax
jne 0x1436
callq 0x16c0
leaq 0xdee(%rip), %rdi       # 0x221d
movb $0x1, %al
callq 0x1050
jmp 0x144a
leaq -0x80(%rbp), %rsi
leaq 0xde8(%rip), %rdi       # 0x222b
movb $0x0, %al
callq 0x1050
jmp 0x11bc
xorl %eax, %eax
addq $0x180, %rsp            # imm = 0x180
popq %rbp
retq
nopw (%rax,%rax)