A modern Music Player Daemon based on Rockbox open source high quality audio player
libadwaita audio rust zig deno mpris rockbox mpd
at master 117 lines 2.9 kB view raw
1/* 2FUNCTION 3 <<memcpy>>---copy memory regions 4 5ANSI_SYNOPSIS 6 #include <string.h> 7 void* memcpy(void *<[out]>, const void *<[in]>, size_t <[n]>); 8 9TRAD_SYNOPSIS 10 void *memcpy(<[out]>, <[in]>, <[n]> 11 void *<[out]>; 12 void *<[in]>; 13 size_t <[n]>; 14 15DESCRIPTION 16 This function copies <[n]> bytes from the memory region 17 pointed to by <[in]> to the memory region pointed to by 18 <[out]>. 19 20 If the regions overlap, the behavior is undefined. 21 22RETURNS 23 <<memcpy>> returns a pointer to the first byte of the <[out]> 24 region. 25 26PORTABILITY 27<<memcpy>> is ANSI C. 28 29<<memcpy>> requires no supporting OS subroutines. 30 31QUICKREF 32 memcpy ansi pure 33 */ 34 35#include "config.h" 36#include "_ansi.h" /* for _DEFUN */ 37#include <string.h> 38 39/* Nonzero if either X or Y is not aligned on a "long" boundary. */ 40#define ROCKBOX_UNALIGNED(X, Y) \ 41 (((long)X & (sizeof (long) - 1)) | ((long)Y & (sizeof (long) - 1))) 42 43/* How many bytes are copied each iteration of the 4X unrolled loop. */ 44#define BIGBLOCKSIZE (sizeof (long) << 2) 45 46/* How many bytes are copied each iteration of the word copy loop. */ 47#define LITTLEBLOCKSIZE (sizeof (long)) 48 49/* Threshold for punting to the byte copier. */ 50#define TOO_SMALL(LEN) ((LEN) < BIGBLOCKSIZE) 51 52_PTR 53_DEFUN (memcpy, (dst0, src0, len0), 54 _PTR dst0 _AND 55 _CONST _PTR src0 _AND 56 size_t len0) ICODE_ATTR; 57 58_PTR 59_DEFUN (memcpy, (dst0, src0, len0), 60 _PTR dst0 _AND 61 _CONST _PTR src0 _AND 62 size_t len0) 63{ 64#if defined(PREFER_SIZE_OVER_SPEED) || defined(__OPTIMIZE_SIZE__) 65 char *dst = (char *) dst0; 66 char *src = (char *) src0; 67 68 _PTR save = dst0; 69 70 while (len0--) 71 { 72 *dst++ = *src++; 73 } 74 75 return save; 76#else 77 char *dst = dst0; 78 _CONST char *src = src0; 79 long *aligned_dst; 80 _CONST long *aligned_src; 81 unsigned int len = len0; 82 83 /* If the size is small, or either SRC or DST is unaligned, 84 then punt into the byte copy loop. This should be rare. */ 85 if (!TOO_SMALL(len) && !ROCKBOX_UNALIGNED (src, dst)) 86 { 87 aligned_dst = (long*)dst; 88 aligned_src = (long*)src; 89 90 /* Copy 4X long words at a time if possible. */ 91 while (len >= BIGBLOCKSIZE) 92 { 93 *aligned_dst++ = *aligned_src++; 94 *aligned_dst++ = *aligned_src++; 95 *aligned_dst++ = *aligned_src++; 96 *aligned_dst++ = *aligned_src++; 97 len -= (unsigned int)BIGBLOCKSIZE; 98 } 99 100 /* Copy one long word at a time if possible. */ 101 while (len >= LITTLEBLOCKSIZE) 102 { 103 *aligned_dst++ = *aligned_src++; 104 len -= LITTLEBLOCKSIZE; 105 } 106 107 /* Pick up any residual with a byte copier. */ 108 dst = (char*)aligned_dst; 109 src = (char*)aligned_src; 110 } 111 112 while (len--) 113 *dst++ = *src++; 114 115 return dst0; 116#endif /* not PREFER_SIZE_OVER_SPEED */ 117}