user: 请将这段汇编代码片段转换成等效的C代码：

```asm
<memmove>:
  endbr64
  mov    %rdi,%r8
  mov    %rsi,%rax
  mov    %rdx,%rcx
  cmp    %rsi,%rdi
  jbe    L129
  lea    (%rsi,%rdx,1),%rdx
  cmp    %rdx,%rdi
  jae    L129
  lea    -0x1(%rcx),%rdx
  test   %rcx,%rcx
  je     L20
  nopl   0x0(%rax,%rax,1)
L225:
  movzbl (%rax,%rdx,1),%ecx
  mov    %cl,(%r8,%rdx,1)
  sub    $0x1,%rdx
  jae    L225
  mov    %r8,%rax
  ret
  nopw   0x0(%rax,%rax,1)
L129:
  cmp    $0x1f,%rcx
  ja     L6
  mov    %r8,%r10
L164:
  lea    -0x1(%rcx),%r9
  test   %rcx,%rcx
  je     L20
  lea    0x1(%rax),%rsi
  mov    %r10,%rdx
  sub    %rsi,%rdx
  cmp    $0xe,%rdx
  jbe    L253
  cmp    $0x6,%r9
  jbe    L253
  cmp    $0xe,%r9
  jbe    L191
L304:
  lea    -0x10(%rcx),%rdx
  xor    %edi,%edi
  shr    $0x4,%rdx
  lea    0x1(%rdx),%rsi
  xor    %edx,%edx
  nopw   0x0(%rax,%rax,1)
L181:
  movdqu (%rax,%rdx,1),%xmm1
  add    $0x1,%rdi
  movups %xmm1,(%r10,%rdx,1)
  add    $0x10,%rdx
  cmp    %rdi,%rsi
  ja     L181
  shl    $0x4,%rsi
  mov    %rsi,%rdx
  lea    (%r10,%rsi,1),%rdi
  lea    (%rax,%rsi,1),%r11
  mov    %r9,%rsi
  sub    %rdx,%rsi
  cmp    %rcx,%rdx
  je     L20
  lea    0x1(%rsi),%rcx
  cmp    $0x6,%rsi
  jbe    L163
L230:
  mov    (%rax,%rdx,1),%rax
  mov    %rax,(%r10,%rdx,1)
  mov    %rcx,%rax
  and    $0xfffffffffffffff8,%rax
  add    %rax,%rdi
  add    %rax,%r11
  sub    %rax,%rsi
  cmp    %rax,%rcx
  je     L20
L163:
  movzbl (%r11),%eax
  mov    %al,(%rdi)
  test   %rsi,%rsi
  je     L20
  movzbl 0x1(%r11),%eax
  mov    %al,0x1(%rdi)
  cmp    $0x1,%rsi
  je     L20
  movzbl 0x2(%r11),%eax
  mov    %al,0x2(%rdi)
  cmp    $0x2,%rsi
  je     L20
  movzbl 0x3(%r11),%eax
  mov    %al,0x3(%rdi)
  cmp    $0x3,%rsi
  je     L20
  movzbl 0x4(%r11),%eax
  mov    %al,0x4(%rdi)
  cmp    $0x4,%rsi
  je     L20
  movzbl 0x5(%r11),%eax
  mov    %al,0x5(%rdi)
  cmp    $0x5,%rsi
  je     L20
  movzbl 0x6(%r11),%eax
  mov    %al,0x6(%rdi)
L20:
  mov    %r8,%rax
  ret
  nopl   0x0(%rax)
L6:
  mov    %r8,%rsi
  or     %rax,%rsi
  and    $0x7,%esi
  jne    L192
  lea    0x1f(%r8),%rdx
  lea    -0x20(%rcx),%r9
  sub    %rax,%rdx
  cmp    $0x3e,%rdx
  jbe    L120
  mov    %r9,%rdi
  xor    %edx,%edx
  shr    $0x5,%rdi
  add    $0x1,%rdi
  nopl   0x0(%rax)
L267:
  movdqu 0x10(%rax,%rdx,1),%xmm0
  movdqu (%rax,%rdx,1),%xmm2
  add    $0x1,%rsi
  movups %xmm2,(%r8,%rdx,1)
  movups %xmm0,0x10(%r8,%rdx,1)
  add    $0x20,%rdx
  cmp    %rdi,%rsi
  jb     L267
L114:
  and    $0xffffffffffffffe0,%r9
  mov    %rcx,%rsi
  lea    0x20(%r9),%r10
  and    $0x1f,%esi
  add    %r10,%rax
  add    %r8,%r10
  test   $0x18,%cl
  je     L96
  mov    (%rax),%rdx
  mov    %rdx,(%r10)
  lea    -0x8(%rsi),%rdx
  cmp    $0x7,%rdx
  jbe    L61
  mov    0x8(%rax),%rdi
  sub    $0x10,%rsi
  mov    %rdi,0x8(%r10)
  cmp    $0x7,%rsi
  jbe    L61
  mov    0x10(%rax),%rsi
  mov    %rsi,0x10(%r10)
L61:
  shr    $0x3,%rdx
  and    $0x7,%ecx
  lea    0x8(,%rdx,8),%rdx
  add    %rdx,%r10
  add    %rdx,%rax
  jmp    L164
  nopl   0x0(%rax)
L192:
  lea    0x1(%rax),%rsi
  mov    %r8,%rdx
  lea    -0x1(%rcx),%r9
  mov    %r8,%r10
  sub    %rsi,%rdx
  cmp    $0xe,%rdx
  ja     L304
L253:
  xor    %edx,%edx
  nopl   (%rax)
L19:
  movzbl (%rax,%rdx,1),%ecx
  mov    %cl,(%r10,%rdx,1)
  mov    %rdx,%rcx
  add    $0x1,%rdx
  cmp    %rcx,%r9
  jne    L19
  mov    %r8,%rax
  ret
L191:
  mov    %r9,%rsi
  mov    %rax,%r11
  mov    %r10,%rdi
  xor    %edx,%edx
  jmp    L230
L96:
  mov    %rsi,%rcx
  jmp    L164
L120:
  mov    %r9,%rdx
  mov    %rax,%rsi
  and    $0xffffffffffffffe0,%rdx
  lea    0x20(%r8,%rdx,1),%r10
  mov    %r8,%rdx
  nopw   0x0(%rax,%rax,1)
L175:
  mov    (%rsi),%rdi
  add    $0x20,%rsi
  add    $0x20,%rdx
  mov    %rdi,-0x20(%rdx)
  mov    -0x18(%rsi),%rdi
  mov    %rdi,-0x18(%rdx)
  mov    -0x10(%rsi),%rdi
  mov    %rdi,-0x10(%rdx)
  mov    -0x8(%rsi),%rdi
  mov    %rdi,-0x8(%rdx)
  cmp    %r10,%rdx
  jne    L175
  jmp    L114
```

assistant: ```c
void *memmove(void *dst_void, const void *src_void, size_t length) {
  char *dst = dst_void;
  const char *src = src_void;
  long *aligned_dst;
  const long *aligned_src;
  if (src < dst && dst < src + length) {
    src += length;
    dst += length;
    while (length--)
      *--dst = *--src;
  } else {
    if (!((length) < (sizeof(long) << 2)) && !(((long)src & (sizeof(long) - 1)) | ((long)dst & (sizeof(long) - 1)))) {
      aligned_dst = (long *)dst;
      aligned_src = (long *)src;
      while (length >= (sizeof(long) << 2)) {
        *aligned_dst++ = *aligned_src++;
        *aligned_dst++ = *aligned_src++;
        *aligned_dst++ = *aligned_src++;
        *aligned_dst++ = *aligned_src++;
        length -= (sizeof(long) << 2);
      }
      while (length >= (sizeof(long))) {
        *aligned_dst++ = *aligned_src++;
        length -= (sizeof(long));
      }
      dst = (char *)aligned_dst;
      src = (char *)aligned_src;
    }
    while (length--)
      *dst++ = *src++;
  }
  return dst_void;
}
```