Reactos
at master 221 lines 5.2 kB view raw
1/* 2 * PROJECT: ReactOS CRT library 3 * LICENSE: LGPL - See COPYING in the top level directory 4 * FILE: lib/sdk/crt/string/wcs.c 5 * PURPOSE: wcs* CRT functions 6 * PROGRAMMERS: Wine team 7 * Ported to ReactOS by Aleksey Bragin (aleksey@reactos.org) 8 */ 9 10/* 11 * msvcrt.dll wide-char functions 12 * 13 * Copyright 1999 Alexandre Julliard 14 * Copyright 2000 Jon Griffiths 15 * 16 * This library is free software; you can redistribute it and/or 17 * modify it under the terms of the GNU Lesser General Public 18 * License as published by the Free Software Foundation; either 19 * version 2.1 of the License, or (at your option) any later version. 20 * 21 * This library is distributed in the hope that it will be useful, 22 * but WITHOUT ANY WARRANTY; without even the implied warranty of 23 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 24 * Lesser General Public License for more details. 25 * 26 * You should have received a copy of the GNU Lesser General Public 27 * License along with this library; if not, write to the Free Software 28 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA 29 */ 30#include <precomp.h> 31#include <assert.h> 32#include "wine/unicode.h" 33 34/********************************************************************* 35 * _wcsnset (MSVCRT.@) 36 */ 37wchar_t* CDECL _wcsnset( wchar_t* str, wchar_t c, size_t n ) 38{ 39 wchar_t* ret = str; 40 while ((n-- > 0) && *str) *str++ = c; 41 return ret; 42} 43 44/********************************************************************* 45 * _wcsrev (MSVCRT.@) 46 */ 47wchar_t* CDECL _wcsrev( wchar_t* str ) 48{ 49 wchar_t* ret = str; 50 wchar_t* end = str + strlenW(str) - 1; 51 while (end > str) 52 { 53 wchar_t t = *end; 54 *end-- = *str; 55 *str++ = t; 56 } 57 return ret; 58} 59 60/********************************************************************* 61 * wcscoll (MSVCRT.@) 62 */ 63int CDECL wcscoll( const wchar_t* str1, const wchar_t* str2 ) 64{ 65 /* FIXME: handle collates */ 66 return strcmpW( str1, str2 ); 67} 68 69/********************************************************************* 70 * wcspbrk (MSVCRT.@) 71 */ 72wchar_t* CDECL wcspbrk( const wchar_t* str, const wchar_t* accept ) 73{ 74 const wchar_t* p; 75 while (*str) 76 { 77 for (p = accept; *p; p++) if (*p == *str) return (wchar_t*)str; 78 str++; 79 } 80 return NULL; 81} 82 83/********************************************************************* 84 * wcscpy_s (MSVCRT.@) 85 */ 86INT CDECL wcscpy_s( wchar_t* wcDest, size_t numElement, const wchar_t *wcSrc) 87{ 88 size_t size = 0; 89 90 if(!wcDest || !numElement) 91 return EINVAL; 92 93 wcDest[0] = 0; 94 95 if(!wcSrc) 96 { 97 return EINVAL; 98 } 99 100 size = strlenW(wcSrc) + 1; 101 102 if(size > numElement) 103 { 104 return ERANGE; 105 } 106 107 memcpy( wcDest, wcSrc, size*sizeof(WCHAR) ); 108 109 return 0; 110} 111 112/****************************************************************** 113 * wcsncpy_s (MSVCRT.@) 114 */ 115INT CDECL wcsncpy_s( wchar_t* wcDest, size_t numElement, const wchar_t *wcSrc, 116 size_t count ) 117{ 118 size_t size = 0; 119 120 if (!wcDest || !numElement) 121 return EINVAL; 122 123 wcDest[0] = 0; 124 125 if (!wcSrc) 126 { 127 return EINVAL; 128 } 129 130 size = min(strlenW(wcSrc), count); 131 132 if (size >= numElement) 133 { 134 return ERANGE; 135 } 136 137 memcpy( wcDest, wcSrc, size*sizeof(WCHAR) ); 138 wcDest[size] = '\0'; 139 140 return 0; 141} 142 143/****************************************************************** 144 * wcscat_s (MSVCRT.@) 145 * 146 */ 147INT CDECL wcscat_s(wchar_t* dst, size_t elem, const wchar_t* src) 148{ 149 wchar_t* ptr = dst; 150 151 if (!dst || elem == 0) return EINVAL; 152 if (!src) 153 { 154 dst[0] = '\0'; 155 return EINVAL; 156 } 157 158 /* seek to end of dst string (or elem if no end of string is found */ 159 while (ptr < dst + elem && *ptr != '\0') ptr++; 160 while (ptr < dst + elem) 161 { 162 if ((*ptr++ = *src++) == '\0') return 0; 163 } 164 /* not enough space */ 165 dst[0] = '\0'; 166 return ERANGE; 167} 168 169/********************************************************************* 170 * wcsncat_s (MSVCRT.@) 171 * 172 */ 173INT CDECL wcsncat_s(wchar_t *dst, size_t elem, 174 const wchar_t *src, size_t count) 175{ 176 size_t srclen; 177 wchar_t dststart; 178 INT ret = 0; 179 180 if (!MSVCRT_CHECK_PMT(dst != NULL) || !MSVCRT_CHECK_PMT(elem > 0)) 181 { 182 return EINVAL; 183 } 184 if (!MSVCRT_CHECK_PMT(src != NULL || count == 0)) 185 return EINVAL; 186 if (count == 0) 187 return 0; 188 189 for (dststart = 0; dststart < elem; dststart++) 190 { 191 if (dst[dststart] == '\0') 192 break; 193 } 194 if (dststart == elem) 195 { 196 MSVCRT_INVALID_PMT("dst[elem] is not NULL terminated\n", EINVAL); 197 return EINVAL; 198 } 199 200 if (count == _TRUNCATE) 201 { 202 srclen = strlenW(src); 203 if (srclen >= (elem - dststart)) 204 { 205 srclen = elem - dststart - 1; 206 ret = STRUNCATE; 207 } 208 } 209 else 210 srclen = min(strlenW(src), count); 211 if (srclen < (elem - dststart)) 212 { 213 memcpy(&dst[dststart], src, srclen*sizeof(wchar_t)); 214 dst[dststart+srclen] = '\0'; 215 return ret; 216 } 217 MSVCRT_INVALID_PMT("dst[elem] is too small", ERANGE); 218 dst[0] = '\0'; 219 return ERANGE; 220} 221