user: 请从给定的汇编指令推导出C源代码：

```asm
<tv_standard>:
  endbr64
  push   %r12
  mov    %rdi,%r12
  push   %rbp
  sub    $0x28,%rsp
  mov    %fs:0x28,%rax
  mov    %rax,0x18(%rsp)
  xor    %eax,%eax
  lea    0x8(%rsp),%rbp
  mov    %rbp,%rdi
  call   <FS460_get_tv_standard@plt>
  test   %eax,%eax
  jne    L68
  lea    0x10(%rsp),%rdi
  call   <FS460_get_available_tv_standards@plt>
  test   %eax,%eax
  jne    L88
  cmpq   $0x0,0x10(%rsp)
  jne    L60
L81:
  mov    0x18(%rsp),%rax
  sub    %fs:0x28,%rax
  jne    L73
  add    $0x28,%rsp
  pop    %rbp
  pop    %r12
  ret
  nopl   (%rax)
L68:
  mov    %eax,%esi
  lea    D51(%rip),%rdi
  xor    %eax,%eax
  call   <printf@plt>
  jmp    L81
  nopw   0x0(%rax,%rax,1)
L60:
  lea    D34(%rip),%rsi
  mov    %r12,%rdi
  call   <strcmp@plt>
  test   %rax,%rax
  jne    L69
  mov    0x8(%rsp),%rdi
  mov    0x10(%rsp),%rdx
  nopw   0x0(%rax,%rax,1)
L171:
  add    %rdi,%rdi
  mov    $0x1,%eax
  cmove  %rax,%rdi
  test   %rdi,%rdx
  je     L171
L57:
  mov    %rdi,0x8(%rsp)
L104:
  call   <FS460_set_tv_standard@plt>
  mov    %eax,%esi
  test   %eax,%eax
  je     L25
  lea    D76(%rip),%rdi
  xor    %eax,%eax
  call   <printf@plt>
  jmp    L81
  nopl   0x0(%rax)
L88:
  mov    %eax,%esi
  lea    D56(%rip),%rdi
  xor    %eax,%eax
  call   <printf@plt>
  jmp    L81
  nopl   (%rax)
L25:
  mov    %rbp,%rdi
  call   <FS460_get_tv_standard@plt>
  mov    %eax,%esi
  test   %eax,%eax
  je     L31
  lea    D12(%rip),%rdi
  xor    %eax,%eax
  call   <printf@plt>
  jmp    L81
  nopl   0x0(%rax)
L69:
  lea    D14(%rip),%rsi
  mov    %r12,%rdi
  call   <strcmp@plt>
  test   %rax,%rax
  jne    L76
  mov    0x8(%rsp),%rdi
  mov    0x10(%rsp),%rdx
  mov    $0x80000000,%eax
  nopl   0x0(%rax,%rax,1)
L106:
  shr    %rdi
  cmove  %rax,%rdi
  test   %rdi,%rdx
  je     L106
  jmp    L57
  nopl   0x0(%rax)
L31:
  mov    0x8(%rsp),%rdi
  call   <str_TVStandard@plt>
  lea    D42(%rip),%rdi
  mov    %rax,%rsi
  xor    %eax,%eax
  call   <printf@plt>
  jmp    L81
L76:
  lea    D40(%rip),%rsi
  mov    %r12,%rdi
  call   <strcmp@plt>
  test   %rax,%rax
  jne    L70
  mov    0x8(%rsp),%rdi
  jmp    L104
L70:
  lea    D82(%rip),%rdi
  call   <puts@plt>
  jmp    L81
L73:
  call   <__stack_chk_fail@plt>
```

tool_calls: name: unpack_data
arguments: data_tag: D51
type_guessed: string
name: unpack_data
arguments: data_tag: D34
type_guessed: string
name: unpack_data
arguments: data_tag: D76
type_guessed: string
name: unpack_data
arguments: data_tag: D56
type_guessed: string
name: unpack_data
arguments: data_tag: D12
type_guessed: string
name: unpack_data
arguments: data_tag: D14
type_guessed: string
name: unpack_data
arguments: data_tag: D42
type_guessed: string
name: unpack_data
arguments: data_tag: D40
type_guessed: string
name: unpack_data
arguments: data_tag: D82
type_guessed: string

tool: D51: error %u getting tv standard.


tool: D34: +

tool: D76: error %u setting TV standard.


tool: D56: error %u getting available tv standards.


tool: D12: error %u getting TV standard after set.


tool: D14: -

tool: D42:   TV Standard=%s


tool: 

tool: D82: Invalid command.

assistant: ```c
void tv_standard(char *mod) {
  int err;
  unsigned long tv_standard, available_tv_standards;
  err = FS460_get_tv_standard(&tv_standard);
  if (err) {
    printf("error %u getting tv standard.\n", err);
    return;
  }
  err = FS460_get_available_tv_standards(&available_tv_standards);
  if (err) {
    printf("error %u getting available tv standards.\n", err);
    return;
  }
  if (available_tv_standards) {
    if (0 == strcmp(mod, "+")) {
      do {
        tv_standard <<= 1;
        if (!tv_standard)
          tv_standard = 1;
      } while (!(tv_standard & available_tv_standards));
    } else if (0 == strcmp(mod, "-")) {
      do {
        tv_standard >>= 1;
        if (!tv_standard)
          tv_standard = 0x80000000;
      } while (!(tv_standard & available_tv_standards));
    } else if (0 != strcmp(mod, "")) {
      printf("Invalid command.\n");
      return;
    }
    err = FS460_set_tv_standard(tv_standard);
    if (err)
      printf("error %u setting TV standard.\n", err);
    else {
      err = FS460_get_tv_standard(&tv_standard);
      if (err)
        printf("error %u getting TV standard after set.\n", err);
      else
        printf("  TV Standard=%s\n", str_TVStandard(tv_standard));
    }
  }
}
```