Home | History | Annotate | Download | only in String
      1 /** @file
      2     Copying Functions for <string.h>.
      3 
      4     Copyright (c) 2010 - 2011, Intel Corporation. All rights reserved.<BR>
      5     This program and the accompanying materials are licensed and made available under
      6     the terms and conditions of the BSD License that accompanies this distribution.
      7     The full text of the license may be found at
      8     http://opensource.org/licenses/bsd-license.php.
      9 
     10     THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
     11     WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
     12 **/
     13 #include  <Uefi.h>
     14 #include  <Library/BaseLib.h>
     15 #include  <Library/BaseMemoryLib.h>
     16 
     17 #include  <LibConfig.h>
     18 
     19 #include  <stdlib.h>
     20 #include  <string.h>
     21 
     22 /** Do not define memcpy for IPF+GCC or ARM/AARCH64+GCC builds.
     23     For IPF, using a GCC compiler, the memcpy function is converted to
     24     CopyMem by objcpy during build.
     25     For ARM/AARCH64, the memcpy function is provided by the CompilerIntrinsics library.
     26 **/
     27 #if !((defined(MDE_CPU_IPF) || defined(MDE_CPU_ARM) || defined(MDE_CPU_AARCH64)) && defined(__GNUC__))
     28 /** The memcpy function copies n characters from the object pointed to by s2
     29     into the object pointed to by s1.
     30 
     31     The implementation is reentrant and handles the case where s2 overlaps s1.
     32 
     33     @return   The memcpy function returns the value of s1.
     34 **/
     35 void *
     36 memcpy(void * __restrict s1, const void * __restrict s2, size_t n)
     37 {
     38   return CopyMem( s1, s2, n);
     39 }
     40 #endif  /* !(defined(MDE_CPU_IPF) && defined(__GCC)) */
     41 
     42 #if !(defined(MDE_CPU_ARM) && defined(__GNUC__))
     43 /** The memmove function copies n characters from the object pointed to by s2
     44     into the object pointed to by s1. Copying takes place as if the n
     45     characters from the object pointed to by s2 are first copied into a
     46     temporary array of n characters that does not overlap the objects pointed
     47     to by s1 and s2, and then the n characters from the temporary array are
     48     copied into the object pointed to by s1.
     49 
     50     This is a version of memcpy that is guaranteed to work when s1 and s2
     51     overlap.  Since our implementation of memcpy already handles overlap,
     52     memmove can be identical to memcpy.
     53 
     54     @return   The memmove function returns the value of s1.
     55 **/
     56 void *
     57 memmove(void *s1, const void *s2, size_t n)
     58 {
     59   return CopyMem( s1, s2, n);
     60 }
     61 #endif
     62 
     63 /** The strcpy function copies the string pointed to by s2 (including the
     64     terminating null character) into the array pointed to by s1. If copying
     65     takes place between objects that overlap, the behavior is undefined.
     66 
     67     @return   The strcpy function returns the value of s1.
     68 **/
     69 char *
     70 strcpy(char * __restrict s1, const char * __restrict s2)
     71 {
     72   //char *s1ret = s1;
     73 
     74   //while ( *s1++ = *s2++)  /* Empty Body */;
     75   //return(s1ret);
     76   return AsciiStrCpy( s1, s2);
     77 }
     78 
     79 /** The strncpy function copies not more than n characters (characters that
     80     follow a null character are not copied) from the array pointed to by s2 to
     81     the array pointed to by s1. If copying takes place between objects that
     82     overlap, the behavior is undefined.
     83 
     84     If the array pointed to by s2 is a string that is shorter than n
     85     characters, null characters are appended to the copy in the array pointed
     86     to by s1, until n characters in all have been written.
     87 
     88     @return   The strncpy function returns the value of s1.
     89 **/
     90 char     *strncpy(char * __restrict s1, const char * __restrict s2, size_t n)
     91 {
     92   return AsciiStrnCpy( s1, s2, n);
     93   //char *dest = s1;
     94 
     95   //while(n != 0) {
     96   //  --n;
     97   //  if((*dest++ = *s2++) == '\0')  break;
     98   //}
     99   //while(n != 0) {
    100   //  *dest++ = '\0';
    101   //  --n;
    102   //}
    103   //return (s1);
    104 }
    105 
    106 /** The strncpyX function copies not more than n-1 characters (characters that
    107     follow a null character are not copied) from the array pointed to by s2 to
    108     the array pointed to by s1. Array s1 is guaranteed to be NULL terminated.
    109     If copying takes place between objects that overlap,
    110     the behavior is undefined.
    111 
    112     strncpyX exists because normal strncpy does not indicate if the copy was
    113     terminated because of exhausting the buffer or reaching the end of s2.
    114 
    115     @return   The strncpyX function returns 0 if the copy operation was
    116               terminated because it reached the end of s1.  Otherwise,
    117               a non-zero value is returned indicating how many characters
    118               remain in s1.
    119 **/
    120 int strncpyX(char * __restrict s1, const char * __restrict s2, size_t n)
    121 {
    122   int NumLeft;
    123 
    124   for( ; n != 0; --n) {
    125     if((*s1++ = *s2++) == '\0')  break;
    126   }
    127   NumLeft = (int)n;
    128 
    129   for( --s1; n != 0; --n) {
    130     *s1++ = '\0';
    131   }
    132 
    133   return NumLeft;   // Zero if we ran out of buffer ( strlen(s1) < strlen(s2) )
    134 }
    135 
    136 /** NetBSD Compatibility Function strdup creates a duplicate copy of a string. **/
    137 char *
    138 strdup(const char *str)
    139 {
    140   size_t len;
    141   char *copy;
    142 
    143   len = strlen(str) + 1;
    144   if ((copy = malloc(len)) == NULL)
    145     return (NULL);
    146   memcpy(copy, str, len);
    147   return (copy);
    148 }
    149