user: Converte this assembly snippet into its equivalent C code:

```asm
<memcpy>:
  endbr64
  mov    %rdi,%rax
  push   %r12
  mov    %rdi,%r12
  xor    %edi,%edi
  push   %rbp
  or     %rsi,%rax
  mov    %rdx,%rbp
  push   %rbx
  test   $0x3,%al
  mov    %rsi,%rbx
  mov    $0x1,%esi
  sete   %dil
  call   <__builtin_expect@plt>
  test   %rax,%rax
  jne    L67
  test   %rbp,%rbp
  je     L77
  lea    0x4(%rbx),%rdx
  mov    %r12,%rax
  lea    -0x1(%rbp),%rsi
  sub    %rdx,%rax
  cmp    $0x8,%rax
  jbe    L174
  cmp    $0x2,%rsi
  jbe    L174
  mov    %rbp,%rcx
  xor    %eax,%eax
  xor    %edx,%edx
  shr    $0x2,%rcx
  nopl   0x0(%rax)
L158:
  movdqu (%rbx,%rax,1),%xmm1
  add    $0x1,%rdx
  movups %xmm1,(%r12,%rax,1)
  add    $0x10,%rax
  cmp    %rdx,%rcx
  jne    L158
  mov    %rbp,%rdx
  and    $0xfffffffffffffffc,%rdx
  lea    0x0(,%rdx,4),%rax
  lea    (%r12,%rax,1),%rcx
  add    %rbx,%rax
  cmp    %rdx,%rbp
  je     L77
  mov    (%rax),%edi
  mov    %edi,(%rcx)
  sub    %rdx,%rsi
  je     L77
  mov    0x4(%rax),%edx
  mov    %edx,0x4(%rcx)
  cmp    $0x1,%rsi
  je     L77
  mov    0x8(%rax),%eax
  mov    %eax,0x8(%rcx)
L77:
  mov    %r12,%rax
  pop    %rbx
  pop    %rbp
  pop    %r12
  ret
  nopl   (%rax)
L67:
  mov    %rbp,%rdx
  shr    $0x2,%rdx
  je     L23
  lea    0x4(%rbx),%rcx
  mov    %r12,%rax
  lea    -0x1(%rdx),%rdi
  sub    %rcx,%rax
  cmp    $0x8,%rax
  jbe    L165
  cmp    $0x2,%rdi
  jbe    L165
  mov    %rbp,%rcx
  mov    %rbp,%rsi
  xor    %eax,%eax
  shr    $0x4,%rcx
  and    $0xfffffffffffffff0,%rsi
  nop
L92:
  movdqu (%rbx,%rax,1),%xmm0
  movups %xmm0,(%r12,%rax,1)
  add    $0x10,%rax
  cmp    %rsi,%rax
  jne    L92
  mov    %rcx,%rax
  lea    0x0(,%rcx,4),%rsi
  shl    $0x4,%rax
  lea    (%r12,%rax,1),%rcx
  add    %rbx,%rax
  cmp    %rsi,%rdx
  je     L98
  mov    (%rax),%r8d
  mov    %r8d,(%rcx)
  sub    %rsi,%rdi
  je     L98
  mov    0x4(%rax),%esi
  mov    %esi,0x4(%rcx)
  cmp    $0x1,%rdi
  je     L98
  mov    0x8(%rax),%eax
  mov    %eax,0x8(%rcx)
L98:
  shl    $0x2,%rdx
  add    %rdx,%rbx
  add    %r12,%rdx
L73:
  test   $0x2,%bpl
  je     L140
  mov    (%rbx),%eax
  add    $0x4,%rdx
  add    $0x4,%rbx
  mov    %eax,-0x4(%rdx)
L140:
  and    $0x1,%ebp
  je     L77
  mov    (%rbx),%eax
  mov    %eax,(%rdx)
  mov    %r12,%rax
  pop    %rbx
  pop    %rbp
  pop    %r12
  ret
  nopl   (%rax)
L23:
  mov    %r12,%rdx
  jmp    L73
  nopl   (%rax)
L174:
  xor    %eax,%eax
  nopw   0x0(%rax,%rax,1)
L87:
  mov    (%rbx,%rax,4),%edx
  mov    %edx,(%r12,%rax,4)
  add    $0x1,%rax
  cmp    %rax,%rbp
  jne    L87
  jmp    L77
  nopl   (%rax)
L165:
  lea    0x0(,%rdx,4),%rsi
  xor    %eax,%eax
  nopw   0x0(%rax,%rax,1)
L162:
  mov    (%rbx,%rax,1),%ecx
  mov    %ecx,(%r12,%rax,1)
  add    $0x4,%rax
  cmp    %rsi,%rax
  jne    L162
  jmp    L98
```

assistant: ```c
void *memcpy(void *dst, const void *src, size_t n) {
  if (__builtin_expect((!(((uint32_t)dst) & 3) && !(((uint32_t)src) & 3)), 1)) {
    uint32_t *d = dst;
    const uint32_t *s = src;
    for (size_t i = (n >> 2); i; i--) {
      *d++ = *s++;
    }
    if (n & 2) {
      *(uint16_t *)d = *(const uint16_t *)s;
      d = (uint32_t *)((uint16_t *)d + 1);
      s = (const uint32_t *)((const uint16_t *)s + 1);
    }
    if (n & 1) {
      *((uint8_t *)d) = *((const uint8_t *)s);
    }
  } else {
    uint8_t *d = dst;
    const uint8_t *s = src;
    for (; n; n--) {
      *d++ = *s++;
    }
  }
  return dst;
}
```