// File: /workspace/github_c_makefile_star2_O2/pocari[P]compilerbook-9cc/parser.c
// Function: assign
static Node *assign() {
  Node *node = ternary();
  Token *tk;

  // chibicc だと "=" 以外の +=, -=... 計の演算子は別途 ND_ADD_EQ のような専用のNode種別をつくって処理している
  // https://github.com/rui314/chibicc/commit/05e907d2b8a94103d60148ce90e27ca191ad5446
  // 難しかったので、簡単そうな i += x を構文木上 i = i + x に読み替える方式にしてみる。
  // ただそのせいで、左辺のnodeが複数のnodeで共有されてしまってfree_nodesのときに複数回freeしてしまってエラーになったので、
  // chibccに合わせて今回からastのfreeはやめる
  if (tk = consume("=")) {
    return new_bin_node(ND_ASSIGN, node, assign(), tk);
  } else if (tk = consume("+=")) {
    Node *n = new_add_node(node, assign(), tk);
    return new_bin_node(ND_ASSIGN, node, n, tk);
  } else if (tk = consume("-=")) {
    Node *n = new_sub_node(node, assign(), tk);
    return new_bin_node(ND_ASSIGN, node, n, tk);
  } else if (tk = consume("*=")) {
    Node *n = new_bin_node(ND_MUL, node, assign(), tk);
    return new_bin_node(ND_ASSIGN, node, n, tk);
  } else if (tk = consume("/=")) {
    Node *n = new_bin_node(ND_DIV, node, assign(), tk);
    return new_bin_node(ND_ASSIGN, node, n, tk);
  } else if (tk = consume("<<=")) {
    Node *n = new_bin_node(ND_A_LSHIFT, node, assign(), tk);
    return new_bin_node(ND_ASSIGN, node, n, tk);
  } else if (tk = consume(">>=")) {
    Node *n = new_bin_node(ND_A_RSHIFT, node, assign(), tk);
    return new_bin_node(ND_ASSIGN, node, n, tk);
  } else if (tk = consume("|=")) {
    Node *n = new_bin_node(ND_BIT_OR, node, assign(), tk);
    return new_bin_node(ND_ASSIGN, node, n, tk);
  } else if (tk = consume("&=")) {
    Node *n = new_bin_node(ND_BIT_AND, node, assign(), tk);
    return new_bin_node(ND_ASSIGN, node, n, tk);
  } else if (tk = consume("^=")) {
    Node *n = new_bin_node(ND_BIT_XOR, node, assign(), tk);
    return new_bin_node(ND_ASSIGN, node, n, tk);
  }
  return node;
}

// Assembly:
pushq %r14
pushq %rbx
pushq %rax
callq 0x5a45
movq %rax, %rbx
leaq 0x3a11(%rip), %rdi      # 0xa901
callq 0x498f
testq %rax, %rax
je 0x6f07
movq %rax, %r14
callq 0x6edd
jmp 0x703d
leaq 0x3aa9(%rip), %rdi      # 0xa9b7
callq 0x498f
testq %rax, %rax
je 0x6f33
movq %rax, %r14
callq 0x6edd
movq %rbx, %rdi
movq %rax, %rsi
movq %r14, %rdx
callq 0x5e8a
jmp 0x703d
leaq 0x3a80(%rip), %rdi      # 0xa9ba
callq 0x498f
testq %rax, %rax
je 0x6f5f
movq %rax, %r14
callq 0x6edd
movq %rbx, %rdi
movq %rax, %rsi
movq %r14, %rdx
callq 0x5f34
jmp 0x703d
leaq 0x3a57(%rip), %rdi      # 0xa9bd
callq 0x498f
testq %rax, %rax
je 0x6f7f
movq %rax, %r14
callq 0x6edd
pushq $0x6
jmp 0x702e
leaq 0x3a3a(%rip), %rdi      # 0xa9c0
callq 0x498f
testq %rax, %rax
je 0x6f9f
movq %rax, %r14
callq 0x6edd
pushq $0x7
jmp 0x702e
leaq 0x3a1d(%rip), %rdi      # 0xa9c3
callq 0x498f
testq %rax, %rax
je 0x6fbc
movq %rax, %r14
callq 0x6edd
pushq $0xf
jmp 0x702e
leaq 0x3a04(%rip), %rdi      # 0xa9c7
callq 0x498f
testq %rax, %rax
je 0x6fd9
movq %rax, %r14
callq 0x6edd
pushq $0x10
jmp 0x702e
leaq 0x39eb(%rip), %rdi      # 0xa9cb
callq 0x498f
testq %rax, %rax
je 0x6ff6
movq %rax, %r14
callq 0x6edd
pushq $0xd
jmp 0x702e
leaq 0x39d1(%rip), %rdi      # 0xa9ce
callq 0x498f
testq %rax, %rax
je 0x7013
movq %rax, %r14
callq 0x6edd
pushq $0xe
jmp 0x702e
leaq 0x39b7(%rip), %rdi      # 0xa9d1
callq 0x498f
testq %rax, %rax
je 0x7055
movq %rax, %r14
callq 0x6edd
pushq $0x11
popq %rdi
movq %rbx, %rsi
movq %rax, %rdx
movq %r14, %rcx
callq 0x5adf
pushq $0x16
popq %rdi
movq %rbx, %rsi
movq %rax, %rdx
movq %r14, %rcx
addq $0x8, %rsp
popq %rbx
popq %r14
jmp 0x5adf
movq %rbx, %rax
addq $0x8, %rsp
popq %rbx
popq %r14
retq