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

```asm
<get_library_address>:
  endbr64
  push   %rbp
  mov    %rsp,%rbp
  sub    $0x260,%rsp
  mov    %rdi,-0x258(%rbp)
  mov    %fs:0x28,%rax
  mov    %rax,-0x8(%rbp)
  xor    %eax,%eax
  mov    -0x258(%rbp),%rax
  mov    %rax,%rdi
  call   <strlen@plt>
  mov    %eax,-0x244(%rbp)
  movq   $0x0,-0x228(%rbp)
  mov    $0x0,%eax
  call   <getpid@plt>
  mov    %eax,%edx
  lea    -0x210(%rbp),%rax
  mov    %edx,%ecx
  lea    D27(%rip),%rdx
  mov    $0x100,%esi
  mov    %rax,%rdi
  call   <snprintf@plt>
  lea    -0x210(%rbp),%rax
  lea    D20(%rip),%rdx
  mov    %rdx,%rsi
  mov    %rax,%rdi
  call   <fopen@plt>
  mov    %rax,-0x220(%rbp)
  cmpq   $0x0,-0x220(%rbp)
  jne    L101
  mov    $0x0,%eax
  jmp    L100
L103:
  lea    -0x110(%rbp),%rax
  mov    %rax,%rdi
  call   <strlen@plt>
  mov    %eax,-0x248(%rbp)
  cmpl   $0x0,-0x248(%rbp)
  jle    L129
  mov    -0x248(%rbp),%eax
  sub    $0x1,%eax
  cltq
  movzbl -0x110(%rbp,%rax,1),%eax
  cmp    $0xa,%al
  jne    L129
  subl   $0x1,-0x248(%rbp)
  mov    -0x248(%rbp),%eax
  cltq
  movb   $0x0,-0x110(%rbp,%rax,1)
L129:
  mov    -0x248(%rbp),%eax
  cmp    -0x244(%rbp),%eax
  jle    L115
  mov    -0x248(%rbp),%eax
  cltq
  mov    -0x244(%rbp),%edx
  movslq %edx,%rdx
  sub    %rdx,%rax
  mov    %rax,%rcx
  lea    -0x110(%rbp),%rax
  add    %rax,%rcx
  mov    -0x244(%rbp),%edx
  mov    -0x258(%rbp),%rax
  mov    %rax,%rsi
  mov    %rcx,%rdi
  call   <memcmp@plt>
  test   %rax,%rax
  jne    L115
  lea    -0x214(%rbp),%rax
  lea    0x1(%rax),%r8
  lea    -0x214(%rbp),%rdi
  lea    -0x238(%rbp),%rcx
  lea    -0x240(%rbp),%rdx
  lea    -0x110(%rbp),%rax
  sub    $0x8,%rsp
  lea    -0x230(%rbp),%rsi
  push   %rsi
  lea    -0x214(%rbp),%rsi
  add    $0x3,%rsi
  push   %rsi
  lea    -0x214(%rbp),%rsi
  add    $0x2,%rsi
  push   %rsi
  mov    %r8,%r9
  mov    %rdi,%r8
  lea    D2(%rip),%rsi
  mov    %rax,%rdi
  call   <sscanf@plt>
  add    $0x20,%rsp
  cmp    $0x7,%eax
  jne    L11
  movzbl -0x214(%rbp),%eax
  cmp    $0x72,%al
  jne    L79
  movzbl -0x212(%rbp),%eax
  cmp    $0x78,%al
  jne    L79
  mov    -0x240(%rbp),%rax
  mov    -0x230(%rbp),%rdx
  sub    %rdx,%rax
  mov    %rax,-0x228(%rbp)
  jmp    L133
L115:
  nop
  jmp    L101
L11:
  nop
  jmp    L101
L79:
  nop
L101:
  mov    -0x220(%rbp),%rdx
  lea    -0x110(%rbp),%rax
  mov    $0x100,%esi
  mov    %rax,%rdi
  call   <fgets@plt>
  test   %rax,%rax
  jne    L103
L133:
  mov    -0x220(%rbp),%rax
  mov    %rax,%rdi
  call   <fclose@plt>
  mov    -0x228(%rbp),%rax
L100:
  mov    -0x8(%rbp),%rdx
  sub    %fs:0x28,%rdx
  je     L56
  call   <__stack_chk_fail@plt>
L56:
  leave
  ret
```

tool_calls: name: parse_data
arguments: label: D27
data_type: string
name: parse_data
arguments: label: D20
data_type: string
name: parse_data
arguments: label: D2
data_type: string

tool: D27: /proc/%d/smaps

tool: D20: rt

tool: D2: %zx-%zx %c%c%c%c %zx

assistant: ```c
size_t get_library_address(const char *libname) {
  char path[256];
  char buff[256];
  int len_libname = strlen(libname);
  FILE *file;
  size_t addr = 0;
  snprintf(path, sizeof path, "/proc/%d/smaps", getpid());
  file = fopen(path, "rt");
  if (file == NULL)
    return 0;
  while (fgets(buff, sizeof buff, file) != NULL) {
    int len = strlen(buff);
    if (len > 0 && buff[len - 1] == '\n') {
      buff[--len] = '\0';
    }
    if (len <= len_libname || memcmp(buff + len - len_libname, libname, len_libname))
      continue;
    size_t start, end, offset;
    char flags[4];
    if (sscanf(buff, "%zx-%zx %c%c%c%c %zx", &start, &end, &flags[0], &flags[1], &flags[2], &flags[3], &offset) != 7)
      continue;
    if (flags[0] != 'r' || flags[2] != 'x') {
      continue;
    }
    addr = start - offset;
    break;
  }
  fclose(file);
  return addr;
}
```