user: Please show me the C implementation that matches the assembly code listed below:

```asm
<main>:
  endbr64
  push   %r15
  push   %r14
  push   %r13
  push   %r12
  push   %rbp
  push   %rbx
  sub    $0x48,%rsp
  mov    %rsi,%r12
  mov    %fs:0x28,%rax
  mov    %rax,0x38(%rsp)
  xor    %eax,%eax
  cmp    $0x4,%edi
  jne    L349
L298:
  mov    0x10(%r12),%rdi
  call   <strlen@plt>
  mov    %eax,%edx
  cmp    $0xb,%eax
  je     L225
  cmp    $0xc,%eax
  je     L125
  cmp    $0xd,%eax
  jne    L34
  mov    0x10(%r12),%rax
  cmpb   $0x2b,(%rax)
  je     L67
L34:
  mov    0x10(%r12),%rsi
  lea    D57(%rip),%rdi
  mov    $0x0,%eax
  call   <printf@plt>
  mov    $0xffffffff,%edi
  call   <exit@plt>
L186:
  lea    0x2c(%rsp),%r15
  lea    0x38(%rsp),%rax
  mov    %rax,(%rsp)
  mov    %r15,%rbx
  lea    D97(%rip),%r13
  lea    D34(%rip),%rbp
  jmp    L123
L349:
  mov    (%rsi),%rsi
  lea    D132(%rip),%rdi
  call   <printf@plt>
  mov    $0xffffffff,%edi
  call   <exit@plt>
  jmp    L298
L225:
  mov    0x10(%r12),%rax
  cmpb   $0x30,(%rax)
  jne    L34
  movb   $0x34,0x2c(%rsp)
  movb   $0x34,0x2d(%rsp)
  lea    0x1(%rax),%rsi
  lea    0x2e(%rsp),%rdi
  mov    $0xa,%edx
  call   <memcpy@plt>
  jmp    L186
L125:
  mov    0x10(%r12),%rsi
  lea    0x2c(%rsp),%rdi
  call   <memcpy@plt>
  jmp    L186
L67:
  lea    0x1(%rax),%rsi
  lea    0x2c(%rsp),%rdi
  mov    $0xc,%edx
  call   <memcpy@plt>
  jmp    L186
L197:
  movsbl %sil,%esi
  mov    %r13,%rdi
  mov    $0x0,%eax
  call   <printf@plt>
L69:
  mov    $0xffffffff,%edi
  call   <exit@plt>
L379:
  add    $0x1,%rbx
  cmp    (%rsp),%rbx
  je     L299
L123:
  movzbl (%rbx),%esi
  lea    -0x30(%rsi),%eax
  cmp    $0x9,%al
  jbe    L379
  lea    -0x20(%rsi),%eax
  cmp    $0x5e,%al
  jbe    L197
  movzbl %sil,%esi
  mov    %rbp,%rdi
  mov    $0x0,%eax
  call   <printf@plt>
  jmp    L69
L299:
  mov    0x18(%r12),%rdi
  call   <strlen@plt>
  mov    %eax,0x18(%rsp)
  cmp    $0xa0,%eax
  jg     L162
  cmpl   $0x0,0x18(%rsp)
  jle    L59
L304:
  mov    0x18(%rsp),%eax
  lea    0x0(,%rax,8),%ecx
  sub    %eax,%ecx
  mov    %ecx,%eax
  mov    %ecx,0x1c(%rsp)
  test   $0x7,%cl
  je     L259
  mov    $0x8,%esi
  cltd
  idiv   %esi
  sub    %edx,%esi
  lea    (%rcx,%rsi,1),%eax
  mov    %eax,0x1c(%rsp)
L259:
  mov    0x1c(%rsp),%ecx
  lea    0x7(%rcx),%eax
  test   %ecx,%ecx
  cmovns %ecx,%eax
  sar    $0x3,%eax
  mov    %eax,0xc(%rsp)
  mov    %eax,%edi
  call   <malloc@plt>
  mov    %rax,%r13
  test   %rax,%rax
  je     L2
L268:
  mov    0xc(%rsp),%edx
  mov    $0x0,%esi
  mov    %r13,%rdi
  call   <memset@plt>
  mov    0x18(%rsp),%eax
  test   %eax,%eax
  jle    L394
  mov    %eax,%eax
  mov    %rax,0x10(%rsp)
  mov    $0x0,%ebp
  mov    $0x0,%r14d
  mov    $0x1,%ebx
  jmp    L393
L162:
  mov    $0xc,%esi
  lea    D107(%rip),%rdi
  mov    $0x0,%eax
  call   <printf@plt>
  mov    $0xffffffff,%edi
  call   <exit@plt>
  jmp    L304
L59:
  lea    D130(%rip),%rdi
  call   <puts@plt>
  mov    $0xffffffff,%edi
  call   <exit@plt>
  jmp    L304
L2:
  mov    0xc(%rsp),%esi
  lea    D3(%rip),%rdi
  mov    $0x0,%eax
  call   <printf@plt>
  mov    $0xffffffff,%edi
  call   <exit@plt>
  jmp    L268
L39:
  movzbl %sil,%esi
  lea    D160(%rip),%rdi
  mov    $0x0,%eax
  call   <printf@plt>
  mov    $0xffffffff,%edi
  call   <exit@plt>
  jmp    L364
L101:
  movb   $0x2,(%rax)
  jmp    L164
L292:
  add    %ebx,%ebx
  cmp    $0x100,%ebx
  je     L287
L283:
  add    $0x1,%eax
  cmp    $0x7,%eax
  je     L29
L264:
  mov    0x18(%r12),%rdx
  movzbl (%rdx,%rbp,1),%edx
  bt     %eax,%edx
  jae    L292
  movslq %r14d,%rdx
  or     %bl,0x0(%r13,%rdx,1)
  jmp    L292
L287:
  add    $0x1,%r14d
  mov    $0x1,%ebx
  jmp    L283
L29:
  add    $0x1,%rbp
  cmp    0x10(%rsp),%rbp
  je     L394
L393:
  mov    0x18(%r12),%rax
  movzbl (%rax,%rbp,1),%esi
  lea    -0x20(%rsi),%eax
  cmp    $0x5e,%al
  ja     L39
L364:
  mov    %rbp,%rax
  add    0x18(%r12),%rax
  cmpb   $0x24,(%rax)
  je     L101
L164:
  mov    $0x0,%eax
  jmp    L264
L394:
  mov    0x8(%r12),%rdi
  lea    D98(%rip),%rsi
  call   <fopen@plt>
  mov    %rax,%rbx
  test   %rax,%rax
  je     L229
L336:
  mov    %rbx,%rcx
  mov    $0xb,%edx
  mov    $0x1,%esi
  lea    D45(%rip),%rdi
  call   <fwrite@plt>
  mov    %rbx,%rdi
  call   <fflush@plt>
  mov    0xc(%rsp),%eax
  lea    0xe(%rax),%edx
  lea    D51(%rip),%rsi
  mov    %rbx,%rdi
  mov    $0x0,%eax
  call   <fprintf@plt>
  mov    %rbx,%rdi
  call   <fflush@plt>
  mov    %rbx,%rcx
  mov    $0xa,%edx
  mov    $0x1,%esi
  lea    D119(%rip),%rdi
  call   <fwrite@plt>
  lea    D10(%rip),%rbp
L382:
  movsbl (%r15),%ecx
  movsbl 0x1(%r15),%edx
  mov    %rbp,%rsi
  mov    %rbx,%rdi
  mov    $0x0,%eax
  call   <fprintf@plt>
  add    $0x2,%r15
  cmp    (%rsp),%r15
  jne    L382
  mov    %rbx,%rcx
  mov    $0x6,%edx
  mov    $0x1,%esi
  lea    D16(%rip),%rdi
  call   <fwrite@plt>
  mov    0x18(%rsp),%edx
  lea    D43(%rip),%rsi
  mov    %rbx,%rdi
  mov    $0x0,%eax
  call   <fprintf@plt>
  cmpl   $0x7,0x1c(%rsp)
  jle    L102
  mov    $0x0,%ebp
  lea    D43(%rip),%r12
L396:
  movzbl 0x0(%r13,%rbp,1),%edx
  mov    %r12,%rsi
  mov    %rbx,%rdi
  mov    $0x0,%eax
  call   <fprintf@plt>
  add    $0x1,%rbp
  cmp    %ebp,0xc(%rsp)
  jg     L396
L102:
  mov    %rbx,%rsi
  mov    $0x1a,%edi
  call   <fputc@plt>
  mov    %rbx,%rdi
  call   <fflush@plt>
  mov    %rbx,%rdi
  call   <fclose@plt>
  mov    %r13,%rdi
  call   <free@plt>
  mov    0x38(%rsp),%rax
  sub    %fs:0x28,%rax
  jne    L38
  mov    $0x0,%eax
  add    $0x48,%rsp
  pop    %rbx
  pop    %rbp
  pop    %r12
  pop    %r13
  pop    %r14
  pop    %r15
  ret
L229:
  lea    D93(%rip),%rdi
  call   <perror@plt>
  mov    $0xffffffff,%edi
  call   <exit@plt>
  jmp    L336
L38:
  call   <__stack_chk_fail@plt>
```

tool_calls: name: disassemble_data
arguments: tag: D57
type: string
name: disassemble_data
arguments: tag: D97
type: string
name: disassemble_data
arguments: tag: D34
type: string
name: disassemble_data
arguments: tag: D132
type: string
name: disassemble_data
arguments: tag: D107
type: string
name: disassemble_data
arguments: tag: D130
type: string
name: disassemble_data
arguments: tag: D3
type: string
name: disassemble_data
arguments: tag: D160
type: string
name: disassemble_data
arguments: tag: D98
type: string
name: disassemble_data
arguments: tag: D45
type: string
name: disassemble_data
arguments: tag: D51
type: string
name: disassemble_data
arguments: tag: D119
type: string
name: disassemble_data
arguments: tag: D10
type: string
name: disassemble_data
arguments: tag: D16
type: string
name: disassemble_data
arguments: tag: D43
type: string
name: disassemble_data
arguments: tag: D93
type: string

tool: D57: Invalid length for phone number '%s': %i


tool: D97: Invalid char in phone number: '%c'


tool: D34: Invalid char in phone number: 0x'%.2X'


tool: D132: usage: %s </dev/device> <phone-no> <sms text>


tool: D107: Text is too long at %i chars. Max is 160.


tool: D130: No text supplied for the SMS.

tool: D3: Unable to malloc '%i' bytes for variable 'sms_string'


tool: D160: Invalid character in text input: 0x'%.2X'


tool: D98: wb

tool: D45: AT+CMGF=0


tool: D51: AT+CMGS=%i


tool: D119: 0011000C91

tool: D10: %c%c

tool: D16: 0000AA

tool: D43: %.2X

tool: D93: Unable to open output device

assistant: ```c
int main(int argc, char **argv) {
  FILE *output_device;
  char target_phone[12];
  unsigned char *sms_string;
  int i, l, m, n;
  int intext_length, sms_string_length;
  if (argc != 4) {
    printf("usage: %s </dev/device> <phone-no> <sms text>\n", argv[0]);
    exit(-1);
  }
  i = strlen((argv[2]));
  if (i == 11 && (argv[2])[0] == '0') {
    target_phone[0] = '4';
    target_phone[1] = '4';
    memcpy(target_phone + 2, (argv[2]) + 1, 10);
  } else if (i == 12) {
    memcpy(target_phone, (argv[2]), 12);
  } else if (i == 13 && (argv[2])[0] == '+') {
    memcpy(target_phone, (argv[2]) + 1, 12);
  } else {
    printf("Invalid length for phone number '%s': %i\n", (argv[2]), i);
    exit(-1);
  }
  for (i = 0; i < 12; i++) {
    if (target_phone[i] < '0' || target_phone[i] > '9') {
      if (((unsigned char)target_phone[i]) < 32 || ((unsigned char)target_phone[i]) > 126)
        printf("Invalid char in phone number: 0x'%.2X'\n", (unsigned char)target_phone[i]);
      else
        printf("Invalid char in phone number: '%c'\n", target_phone[i]);
      exit(-1);
    }
  }
  intext_length = strlen((argv[3]));
  if (intext_length > 160) {
    printf("Text is too long at %i chars. Max is 160.\n", i);
    exit(-1);
  }
  if (intext_length < 1) {
    printf("No text supplied for the SMS.\n");
    exit(-1);
  }
  i = intext_length * 7;
  m = i % 8;
  if (m != 0)
    i += (8 - m);
  sms_string_length = i / 8;
  sms_string = malloc(sms_string_length);
  if (sms_string == NULL) {
    printf("Unable to malloc '%i' bytes for variable 'sms_string'\n", sms_string_length);
    exit(-1);
  }
  memset(sms_string, 0, sms_string_length);
  l = 1;
  m = 0;
  for (i = 0; i < intext_length; i++) {
    if (((unsigned char)(argv[3])[i]) < 32 || ((unsigned char)(argv[3])[i]) > 126) {
      printf("Invalid character in text input: 0x'%.2X'\n", (unsigned char)(argv[3])[i]);
      exit(-1);
    }
    if ((argv[3])[i] == '$') {
      (argv[3])[i] = 0x02;
    }
    for (n = 0; n < 7; n++) {
      if (((unsigned char)(argv[3])[i]) & (1 << n)) {
        sms_string[m] |= l;
      }
      l = l << 1;
      if (l == 256) {
        l = 1;
        m++;
      }
    }
  }
  output_device = fopen((argv[1]), "wb");
  if (output_device == NULL) {
    perror("Unable to open output device");
    exit(-1);
  }
  fprintf(output_device, "AT+CMGF=0\r\n");
  fflush(output_device);
  fprintf(output_device, "AT+CMGS=%i\r\n", 14 + sms_string_length);
  fflush(output_device);
  fprintf(output_device, "0011000C91");
  for (i = 0; i < 12; i += 2) {
    fprintf(output_device, "%c%c", target_phone[i + 1], target_phone[i]);
  }
  fprintf(output_device, "0000AA");
  fprintf(output_device, "%.2X", intext_length);
  for (i = 0; i < sms_string_length; i++)
    fprintf(output_device, "%.2X", sms_string[i]);
  fprintf(output_device, "%c", 0x1a);
  fflush(output_device);
  fclose(output_device);
  free(sms_string);
  return 0;
}
```