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

```asm
<mbrtowc>:
  endbr64
  test   %rdx,%rdx
  je     L29
  test   %rsi,%rsi
  je     L29
  movzbl (%rsi),%ecx
  test   %cl,%cl
  je     L29
  jns    L180
  test   $0x40,%cl
  je     L15
  test   $0x20,%cl
  jne    L150
  and    $0x1f,%ecx
  mov    $0x1,%r9d
L65:
  lea    0x1(%rsi),%rax
  cmp    %rdx,%r9
  jb     L13
  add    %rdx,%rsi
L9:
  cmp    %rsi,%rax
  je     L22
  add    $0x1,%rax
  movsbl -0x1(%rax),%edx
  and    $0xc0,%edx
  cmp    $0x80,%edx
  je     L9
  mov    D81(%rip),%rax
  mov    (%rax),%rdx
  mov    D41(%rip),%rax
  mov    %rdx,(%rax)
  mov    $0xffffffffffffffff,%rax
  ret
L29:
  mov    $0x0,%eax
  test   %rdi,%rdi
  je     L220
  movl   $0x0,(%rdi)
  ret
L180:
  mov    $0x1,%eax
  test   %rdi,%rdi
  je     L220
  movsbl %cl,%ecx
  mov    %ecx,(%rdi)
  ret
L15:
  mov    D81(%rip),%rax
  mov    (%rax),%rdx
  mov    D41(%rip),%rax
  mov    %rdx,(%rax)
  mov    $0xffffffffffffffff,%rax
  ret
L150:
  test   $0x10,%cl
  jne    L5
  and    $0xf,%ecx
  mov    $0x2,%r9d
  jmp    L65
L5:
  test   $0x8,%cl
  jne    L39
  and    $0x7,%ecx
  mov    $0x3,%r9d
  jmp    L65
L39:
  test   $0x4,%cl
  jne    L157
  and    $0x3,%ecx
  mov    $0x4,%r9d
  jmp    L65
L157:
  test   $0x2,%cl
  jne    L66
  and    $0x1,%ecx
  mov    $0x5,%r9d
  jmp    L65
L66:
  test   $0x1,%cl
  jne    L43
  mov    D81(%rip),%rax
  mov    (%rax),%rdx
  mov    D41(%rip),%rax
  mov    %rdx,(%rax)
  mov    $0xffffffffffffffff,%rax
  ret
L43:
  mov    D81(%rip),%rax
  mov    (%rax),%rdx
  mov    D41(%rip),%rax
  mov    %rdx,(%rax)
  mov    $0xffffffffffffffff,%rax
  ret
L22:
  mov    $0xfffffffffffffffe,%rax
  ret
L13:
  add    %rax,%r9
L184:
  add    $0x1,%rax
  movzbl -0x1(%rax),%edx
  mov    %edx,%r8d
  and    $0xc0,%r8d
  cmp    $0x80,%r8d
  jne    L153
  shl    $0x6,%ecx
  and    $0x3f,%edx
  or     %edx,%ecx
  cmp    %rax,%r9
  jne    L184
  test   %rdi,%rdi
  je     L202
  mov    %ecx,(%rdi)
L202:
  sub    %rsi,%rax
L220:
  ret
L153:
  mov    D81(%rip),%rax
  mov    (%rax),%rdx
  mov    D41(%rip),%rax
  mov    %rdx,(%rax)
  mov    $0xffffffffffffffff,%rax
  ret
```

assistant: ```c
size_t mbrtowc(wchar_t *restrict pwc, char const *restrict s, size_t n, mbstate_t *restrict ps) {
  if (!n || !s || !*s) {
    if (pwc)
      *pwc = 0;
    return 0;
  }
  wchar_t c = *s;
  size_t len;
  if (!(c & 0x80)) {
    if (pwc)
      *pwc = c;
    return 1;
  } else if (!(c & 0x40))
    return errno = EILSEQ, (size_t)-1;
  else if (!(c & 0x20))
    c = c & 0x1F, len = 1;
  else if (!(c & 0x10))
    c = c & 0x0F, len = 2;
  else if (!(c & 0x08))
    c = c & 0x07, len = 3;
  else if (!(c & 0x04))
    c = c & 0x03, len = 4;
  else if (!(c & 0x02))
    c = c & 0x01, len = 5;
  else if (!(c & 0x01))
    return errno = EILSEQ, (size_t)-1;
  else
    return errno = EILSEQ, (size_t)-1;
  char const *itr = s + 1;
  if (n <= len) {
    char const *end = s + n;
    while (itr != end) {
      if ((*itr++ & 0xC0) != 0x80)
        return errno = EILSEQ, (size_t)-1;
    }
    return (size_t)-2;
  }
  char const *end = itr + len;
  while (itr != end) {
    wchar_t i = *itr++;
    if ((i & 0xC0) != 0x80)
      return errno = EILSEQ, (size_t)-1;
    c = (c << 6) | (i & 0x3F);
  }
  if (pwc)
    *pwc = c;
  return itr - s;
}
```