vg_replace_strmem.c revision 8eb8bab992e3998c33770b0cdb16059a8b918a06
19c7779b64eacf264ee427b97ae0df8596b1960ccbart 29c7779b64eacf264ee427b97ae0df8596b1960ccbart/*--------------------------------------------------------------------*/ 39c7779b64eacf264ee427b97ae0df8596b1960ccbart/*--- Replacements for strcpy(), memcpy() et al, which run on the ---*/ 49c7779b64eacf264ee427b97ae0df8596b1960ccbart/*--- simulated CPU. ---*/ 5f2a68aa6deb788304b9c100ecd4dec41f5064b8cphilippe/*--- vg_replace_strmem.c ---*/ 69c7779b64eacf264ee427b97ae0df8596b1960ccbart/*--------------------------------------------------------------------*/ 79c7779b64eacf264ee427b97ae0df8596b1960ccbart 89c7779b64eacf264ee427b97ae0df8596b1960ccbart/* 99c7779b64eacf264ee427b97ae0df8596b1960ccbart This file is part of Valgrind. 109c7779b64eacf264ee427b97ae0df8596b1960ccbart 119c7779b64eacf264ee427b97ae0df8596b1960ccbart Copyright (C) 2000-2013 Julian Seward 129c7779b64eacf264ee427b97ae0df8596b1960ccbart jseward@acm.org 139c7779b64eacf264ee427b97ae0df8596b1960ccbart 149c7779b64eacf264ee427b97ae0df8596b1960ccbart This program is free software; you can redistribute it and/or 159c7779b64eacf264ee427b97ae0df8596b1960ccbart modify it under the terms of the GNU General Public License as 169c7779b64eacf264ee427b97ae0df8596b1960ccbart published by the Free Software Foundation; either version 2 of the 179c7779b64eacf264ee427b97ae0df8596b1960ccbart License, or (at your option) any later version. 189c7779b64eacf264ee427b97ae0df8596b1960ccbart 199c7779b64eacf264ee427b97ae0df8596b1960ccbart This program is distributed in the hope that it will be useful, but 209c7779b64eacf264ee427b97ae0df8596b1960ccbart WITHOUT ANY WARRANTY; without even the implied warranty of 219c7779b64eacf264ee427b97ae0df8596b1960ccbart MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 229c7779b64eacf264ee427b97ae0df8596b1960ccbart General Public License for more details. 239c7779b64eacf264ee427b97ae0df8596b1960ccbart 249c7779b64eacf264ee427b97ae0df8596b1960ccbart You should have received a copy of the GNU General Public License 259c7779b64eacf264ee427b97ae0df8596b1960ccbart along with this program; if not, write to the Free Software 269c7779b64eacf264ee427b97ae0df8596b1960ccbart Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 279c7779b64eacf264ee427b97ae0df8596b1960ccbart 02111-1307, USA. 289c7779b64eacf264ee427b97ae0df8596b1960ccbart 299c7779b64eacf264ee427b97ae0df8596b1960ccbart The GNU General Public License is contained in the file COPYING. 309c7779b64eacf264ee427b97ae0df8596b1960ccbart*/ 319c7779b64eacf264ee427b97ae0df8596b1960ccbart 329c7779b64eacf264ee427b97ae0df8596b1960ccbart#include "pub_tool_basics.h" 339c7779b64eacf264ee427b97ae0df8596b1960ccbart#include "pub_tool_poolalloc.h" 349c7779b64eacf264ee427b97ae0df8596b1960ccbart#include "pub_tool_hashtable.h" 359c7779b64eacf264ee427b97ae0df8596b1960ccbart#include "pub_tool_redir.h" 369c7779b64eacf264ee427b97ae0df8596b1960ccbart#include "pub_tool_tooliface.h" 379c7779b64eacf264ee427b97ae0df8596b1960ccbart#include "pub_tool_clreq.h" 389c7779b64eacf264ee427b97ae0df8596b1960ccbart 399c7779b64eacf264ee427b97ae0df8596b1960ccbart/* --------------------------------------------------------------------- 409c7779b64eacf264ee427b97ae0df8596b1960ccbart We have our own versions of these functions for two reasons: 419c7779b64eacf264ee427b97ae0df8596b1960ccbart (a) it allows us to do overlap checking 429c7779b64eacf264ee427b97ae0df8596b1960ccbart (b) some of the normal versions are hyper-optimised, which fools 439c7779b64eacf264ee427b97ae0df8596b1960ccbart Memcheck and cause spurious value warnings. Our versions are 449c7779b64eacf264ee427b97ae0df8596b1960ccbart simpler. 459c7779b64eacf264ee427b97ae0df8596b1960ccbart (c) the glibc SSE-variants can read past the end of the input data 469c7779b64eacf264ee427b97ae0df8596b1960ccbart ranges. This can cause false-positive Memcheck / Helgrind / DRD 479c7779b64eacf264ee427b97ae0df8596b1960ccbart reports. 489c7779b64eacf264ee427b97ae0df8596b1960ccbart 499c7779b64eacf264ee427b97ae0df8596b1960ccbart Note that overenthusiastic use of PLT bypassing by the glibc people also 509c7779b64eacf264ee427b97ae0df8596b1960ccbart means that we need to patch multiple versions of some of the functions to 519c7779b64eacf264ee427b97ae0df8596b1960ccbart our own implementations. 529c7779b64eacf264ee427b97ae0df8596b1960ccbart 539c7779b64eacf264ee427b97ae0df8596b1960ccbart THEY RUN ON THE SIMD CPU! 549c7779b64eacf264ee427b97ae0df8596b1960ccbart ------------------------------------------------------------------ */ 559c7779b64eacf264ee427b97ae0df8596b1960ccbart 569c7779b64eacf264ee427b97ae0df8596b1960ccbart/* Assignment of behavioural equivalence class tags: 2NNNP is intended 579c7779b64eacf264ee427b97ae0df8596b1960ccbart to be reserved for str/mem intercepts. Current usage: 589c7779b64eacf264ee427b97ae0df8596b1960ccbart 599c7779b64eacf264ee427b97ae0df8596b1960ccbart 20010 STRRCHR 609c7779b64eacf264ee427b97ae0df8596b1960ccbart 20020 STRCHR 619c7779b64eacf264ee427b97ae0df8596b1960ccbart 20030 STRCAT 629c7779b64eacf264ee427b97ae0df8596b1960ccbart 20040 STRNCAT 639c7779b64eacf264ee427b97ae0df8596b1960ccbart 20050 STRLCAT 649c7779b64eacf264ee427b97ae0df8596b1960ccbart 20060 STRNLEN 659c7779b64eacf264ee427b97ae0df8596b1960ccbart 20070 STRLEN 669c7779b64eacf264ee427b97ae0df8596b1960ccbart 20080 STRCPY 679c7779b64eacf264ee427b97ae0df8596b1960ccbart 20090 STRNCPY 689c7779b64eacf264ee427b97ae0df8596b1960ccbart 20100 STRLCPY 699c7779b64eacf264ee427b97ae0df8596b1960ccbart 20110 STRNCMP 709c7779b64eacf264ee427b97ae0df8596b1960ccbart 20120 STRCASECMP 719c7779b64eacf264ee427b97ae0df8596b1960ccbart 20130 STRNCASECMP 729c7779b64eacf264ee427b97ae0df8596b1960ccbart 20140 STRCASECMP_L 739c7779b64eacf264ee427b97ae0df8596b1960ccbart 20150 STRNCASECMP_L 749c7779b64eacf264ee427b97ae0df8596b1960ccbart 20160 STRCMP 759c7779b64eacf264ee427b97ae0df8596b1960ccbart 20170 MEMCHR 769c7779b64eacf264ee427b97ae0df8596b1960ccbart 779c7779b64eacf264ee427b97ae0df8596b1960ccbart 20180 MEMCPY if there's a conflict between memcpy and 789c7779b64eacf264ee427b97ae0df8596b1960ccbart 20181 MEMMOVE memmove, prefer memmove 799c7779b64eacf264ee427b97ae0df8596b1960ccbart 809c7779b64eacf264ee427b97ae0df8596b1960ccbart 20190 MEMCMP 819c7779b64eacf264ee427b97ae0df8596b1960ccbart 20200 STPCPY 829c7779b64eacf264ee427b97ae0df8596b1960ccbart 20210 MEMSET 839c7779b64eacf264ee427b97ae0df8596b1960ccbart 2022P unused (was previously MEMMOVE) 849c7779b64eacf264ee427b97ae0df8596b1960ccbart 20230 BCOPY 859c7779b64eacf264ee427b97ae0df8596b1960ccbart 20240 GLIBC25___MEMMOVE_CHK 869c7779b64eacf264ee427b97ae0df8596b1960ccbart 20250 GLIBC232_STRCHRNUL 879c7779b64eacf264ee427b97ae0df8596b1960ccbart 20260 GLIBC232_RAWMEMCHR 889c7779b64eacf264ee427b97ae0df8596b1960ccbart 20270 GLIBC25___STRCPY_CHK 899c7779b64eacf264ee427b97ae0df8596b1960ccbart 20280 GLIBC25___STPCPY_CHK 909c7779b64eacf264ee427b97ae0df8596b1960ccbart 20290 GLIBC25_MEMPCPY 919c7779b64eacf264ee427b97ae0df8596b1960ccbart 20300 GLIBC26___MEMCPY_CHK 929c7779b64eacf264ee427b97ae0df8596b1960ccbart 20310 STRSTR 939c7779b64eacf264ee427b97ae0df8596b1960ccbart 20320 STRPBRK 949c7779b64eacf264ee427b97ae0df8596b1960ccbart 20330 STRCSPN 959c7779b64eacf264ee427b97ae0df8596b1960ccbart 20340 STRSPN 969c7779b64eacf264ee427b97ae0df8596b1960ccbart 20350 STRCASESTR 979c7779b64eacf264ee427b97ae0df8596b1960ccbart 20360 MEMRCHR 989c7779b64eacf264ee427b97ae0df8596b1960ccbart 20370 WCSLEN 999c7779b64eacf264ee427b97ae0df8596b1960ccbart 20380 WCSCMP 1009c7779b64eacf264ee427b97ae0df8596b1960ccbart 20390 WCSCPY 1019c7779b64eacf264ee427b97ae0df8596b1960ccbart 20400 WCSCHR 1029c7779b64eacf264ee427b97ae0df8596b1960ccbart 20410 WCSRCHR 1039c7779b64eacf264ee427b97ae0df8596b1960ccbart 20420 STPNCPY 1049c7779b64eacf264ee427b97ae0df8596b1960ccbart*/ 1059c7779b64eacf264ee427b97ae0df8596b1960ccbart 1068eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#if defined(VGO_solaris) 1078eb8bab992e3998c33770b0cdb16059a8b918a06sewardj/* 1088eb8bab992e3998c33770b0cdb16059a8b918a06sewardj Detour functions in the libc and the runtime linker. If a function isn't 1098eb8bab992e3998c33770b0cdb16059a8b918a06sewardj much optimized (and no overlap checking is necessary) then redir the 1108eb8bab992e3998c33770b0cdb16059a8b918a06sewardj function only in the libc. This way we can keep stacktraces in the tests 1118eb8bab992e3998c33770b0cdb16059a8b918a06sewardj consistent. 1128eb8bab992e3998c33770b0cdb16059a8b918a06sewardj*/ 1138eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#endif 1148eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 1159c7779b64eacf264ee427b97ae0df8596b1960ccbart 1169c7779b64eacf264ee427b97ae0df8596b1960ccbart/* Figure out if [dst .. dst+dstlen-1] overlaps with 1179c7779b64eacf264ee427b97ae0df8596b1960ccbart [src .. src+srclen-1]. 1189c7779b64eacf264ee427b97ae0df8596b1960ccbart We assume that the address ranges do not wrap around 1199c7779b64eacf264ee427b97ae0df8596b1960ccbart (which is safe since on Linux addresses >= 0xC0000000 1209c7779b64eacf264ee427b97ae0df8596b1960ccbart are not accessible and the program will segfault in this 1219c7779b64eacf264ee427b97ae0df8596b1960ccbart circumstance, presumably). 1229c7779b64eacf264ee427b97ae0df8596b1960ccbart*/ 1239c7779b64eacf264ee427b97ae0df8596b1960ccbartstatic inline 1249c7779b64eacf264ee427b97ae0df8596b1960ccbartBool is_overlap ( void* dst, const void* src, SizeT dstlen, SizeT srclen ) 1259c7779b64eacf264ee427b97ae0df8596b1960ccbart{ 1269c7779b64eacf264ee427b97ae0df8596b1960ccbart Addr loS, hiS, loD, hiD; 1279c7779b64eacf264ee427b97ae0df8596b1960ccbart 1289c7779b64eacf264ee427b97ae0df8596b1960ccbart if (dstlen == 0 || srclen == 0) 1299c7779b64eacf264ee427b97ae0df8596b1960ccbart return False; 1309c7779b64eacf264ee427b97ae0df8596b1960ccbart 1319c7779b64eacf264ee427b97ae0df8596b1960ccbart loS = (Addr)src; 1329c7779b64eacf264ee427b97ae0df8596b1960ccbart loD = (Addr)dst; 1339c7779b64eacf264ee427b97ae0df8596b1960ccbart hiS = loS + srclen - 1; 1349c7779b64eacf264ee427b97ae0df8596b1960ccbart hiD = loD + dstlen - 1; 1359c7779b64eacf264ee427b97ae0df8596b1960ccbart 1369c7779b64eacf264ee427b97ae0df8596b1960ccbart /* So figure out if [loS .. hiS] overlaps with [loD .. hiD]. */ 1379c7779b64eacf264ee427b97ae0df8596b1960ccbart if (loS < loD) { 1389c7779b64eacf264ee427b97ae0df8596b1960ccbart return !(hiS < loD); 1399c7779b64eacf264ee427b97ae0df8596b1960ccbart } 1409c7779b64eacf264ee427b97ae0df8596b1960ccbart else if (loD < loS) { 1419c7779b64eacf264ee427b97ae0df8596b1960ccbart return !(hiD < loS); 1429c7779b64eacf264ee427b97ae0df8596b1960ccbart } 1439c7779b64eacf264ee427b97ae0df8596b1960ccbart else { 1449c7779b64eacf264ee427b97ae0df8596b1960ccbart /* They start at same place. Since we know neither of them has 1459c7779b64eacf264ee427b97ae0df8596b1960ccbart zero length, they must overlap. */ 1469c7779b64eacf264ee427b97ae0df8596b1960ccbart return True; 1479c7779b64eacf264ee427b97ae0df8596b1960ccbart } 1489c7779b64eacf264ee427b97ae0df8596b1960ccbart} 1499c7779b64eacf264ee427b97ae0df8596b1960ccbart 1509c7779b64eacf264ee427b97ae0df8596b1960ccbart 1519c7779b64eacf264ee427b97ae0df8596b1960ccbart/* Call here to exit if we can't continue. On Android we can't call 1529c7779b64eacf264ee427b97ae0df8596b1960ccbart _exit for some reason, so we have to blunt-instrument it. */ 1539c7779b64eacf264ee427b97ae0df8596b1960ccbart__attribute__ ((__noreturn__)) 1549c7779b64eacf264ee427b97ae0df8596b1960ccbartstatic inline void my_exit ( int x ) 1559c7779b64eacf264ee427b97ae0df8596b1960ccbart{ 1569c6b05db45362b1afb981aa8298ab12ab4027b1adejanj# if defined(VGPV_arm_linux_android) || defined(VGPV_mips32_linux_android) \ 15726ed419d60369d0545510eba0832566e24452e1esewardj || defined(VGPV_arm64_linux_android) 1589c7779b64eacf264ee427b97ae0df8596b1960ccbart __asm__ __volatile__(".word 0xFFFFFFFF"); 1599c7779b64eacf264ee427b97ae0df8596b1960ccbart while (1) {} 1609c7779b64eacf264ee427b97ae0df8596b1960ccbart# elif defined(VGPV_x86_linux_android) 1619c7779b64eacf264ee427b97ae0df8596b1960ccbart __asm__ __volatile__("ud2"); 1629c7779b64eacf264ee427b97ae0df8596b1960ccbart while (1) {} 1639c7779b64eacf264ee427b97ae0df8596b1960ccbart# else 1649c7779b64eacf264ee427b97ae0df8596b1960ccbart extern __attribute__ ((__noreturn__)) void _exit(int status); 1659c7779b64eacf264ee427b97ae0df8596b1960ccbart _exit(x); 1669c7779b64eacf264ee427b97ae0df8596b1960ccbart# endif 1679c7779b64eacf264ee427b97ae0df8596b1960ccbart} 1689c7779b64eacf264ee427b97ae0df8596b1960ccbart 1699c7779b64eacf264ee427b97ae0df8596b1960ccbart 1709c7779b64eacf264ee427b97ae0df8596b1960ccbart// This is a macro rather than a function because we don't want to have an 1719c7779b64eacf264ee427b97ae0df8596b1960ccbart// extra function in the stack trace. 1729c7779b64eacf264ee427b97ae0df8596b1960ccbart#ifndef RECORD_OVERLAP_ERROR 1739c7779b64eacf264ee427b97ae0df8596b1960ccbart#define RECORD_OVERLAP_ERROR(s, src, dst, len) do { } while (0) 1749c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 1759c7779b64eacf264ee427b97ae0df8596b1960ccbart#ifndef VALGRIND_CHECK_VALUE_IS_DEFINED 1769c7779b64eacf264ee427b97ae0df8596b1960ccbart#define VALGRIND_CHECK_VALUE_IS_DEFINED(__lvalue) 1 1779c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 1789c7779b64eacf264ee427b97ae0df8596b1960ccbart 1799c7779b64eacf264ee427b97ae0df8596b1960ccbart 1809c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strrchr ----------------------*/ 1819c7779b64eacf264ee427b97ae0df8596b1960ccbart 1829c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRRCHR(soname, fnname) \ 1839c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20010,soname,fnname)( const char* s, int c ); \ 1849c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20010,soname,fnname)( const char* s, int c ) \ 1859c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 1869c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar ch = (HChar)c; \ 1879c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* p = s; \ 1889c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* last = NULL; \ 1899c7779b64eacf264ee427b97ae0df8596b1960ccbart while (True) { \ 1909c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*p == ch) last = p; \ 19170a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian if (*p == 0) return CONST_CAST(HChar *,last); \ 1929c7779b64eacf264ee427b97ae0df8596b1960ccbart p++; \ 1939c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 1949c7779b64eacf264ee427b97ae0df8596b1960ccbart } 1959c7779b64eacf264ee427b97ae0df8596b1960ccbart 1969c7779b64eacf264ee427b97ae0df8596b1960ccbart// Apparently rindex() is the same thing as strrchr() 1979c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 1989c7779b64eacf264ee427b97ae0df8596b1960ccbart STRRCHR(VG_Z_LIBC_SONAME, strrchr) 1999c7779b64eacf264ee427b97ae0df8596b1960ccbart STRRCHR(VG_Z_LIBC_SONAME, rindex) 2009c7779b64eacf264ee427b97ae0df8596b1960ccbart STRRCHR(VG_Z_LIBC_SONAME, __GI_strrchr) 2019c7779b64eacf264ee427b97ae0df8596b1960ccbart STRRCHR(VG_Z_LIBC_SONAME, __strrchr_sse2) 2029c7779b64eacf264ee427b97ae0df8596b1960ccbart STRRCHR(VG_Z_LIBC_SONAME, __strrchr_sse2_no_bsf) 2039c7779b64eacf264ee427b97ae0df8596b1960ccbart STRRCHR(VG_Z_LIBC_SONAME, __strrchr_sse42) 2049c7779b64eacf264ee427b97ae0df8596b1960ccbart STRRCHR(VG_Z_LD_LINUX_SO_2, rindex) 2059c6b05db45362b1afb981aa8298ab12ab4027b1adejanj#if defined(VGPV_arm_linux_android) || defined(VGPV_x86_linux_android) \ 2069c6b05db45362b1afb981aa8298ab12ab4027b1adejanj || defined(VGPV_mips32_linux_android) 2079c7779b64eacf264ee427b97ae0df8596b1960ccbart STRRCHR(NONE, __dl_strrchr); /* in /system/bin/linker */ 2089c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 2099c7779b64eacf264ee427b97ae0df8596b1960ccbart 2109c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 2119c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRRCHR(VG_Z_LIBC_SONAME, strrchr) 2129c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRRCHR(VG_Z_LIBC_SONAME, rindex) 2139c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRRCHR(VG_Z_DYLD, strrchr) 2149c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRRCHR(VG_Z_DYLD, rindex) 2159c7779b64eacf264ee427b97ae0df8596b1960ccbart STRRCHR(VG_Z_LIBC_SONAME, strrchr) 2169090d2f691fd59c3a67c55e74f3c66c9c5671b01rhyskidd# if DARWIN_VERS >= DARWIN_10_9 217eb86ddab35602995b31767f72a2babb6a692c3f3sewardj STRRCHR(libsystemZucZddylib, strrchr) 218eb86ddab35602995b31767f72a2babb6a692c3f3sewardj# endif 2199c7779b64eacf264ee427b97ae0df8596b1960ccbart 2208eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 2218eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRRCHR(VG_Z_LIBC_SONAME, strrchr) 2228eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRRCHR(VG_Z_LIBC_SONAME, rindex) 2238eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRRCHR(VG_Z_LD_SO_1, strrchr) 2248eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 2259c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 2269c7779b64eacf264ee427b97ae0df8596b1960ccbart 2279c7779b64eacf264ee427b97ae0df8596b1960ccbart 2289c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strchr ----------------------*/ 2299c7779b64eacf264ee427b97ae0df8596b1960ccbart 2309c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRCHR(soname, fnname) \ 2319c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20020,soname,fnname) ( const char* s, int c ); \ 2329c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20020,soname,fnname) ( const char* s, int c ) \ 2339c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 2349c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar ch = (HChar)c ; \ 2359c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* p = s; \ 2369c7779b64eacf264ee427b97ae0df8596b1960ccbart while (True) { \ 23770a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian if (*p == ch) return CONST_CAST(HChar *,p); \ 2389c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*p == 0) return NULL; \ 2399c7779b64eacf264ee427b97ae0df8596b1960ccbart p++; \ 2409c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 2419c7779b64eacf264ee427b97ae0df8596b1960ccbart } 2429c7779b64eacf264ee427b97ae0df8596b1960ccbart 2439c7779b64eacf264ee427b97ae0df8596b1960ccbart// Apparently index() is the same thing as strchr() 2449c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 2459c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCHR(VG_Z_LIBC_SONAME, strchr) 2469c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCHR(VG_Z_LIBC_SONAME, __GI_strchr) 2479c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCHR(VG_Z_LIBC_SONAME, __strchr_sse2) 2489c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCHR(VG_Z_LIBC_SONAME, __strchr_sse2_no_bsf) 2499c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCHR(VG_Z_LIBC_SONAME, index) 2509c7779b64eacf264ee427b97ae0df8596b1960ccbart# if !defined(VGP_x86_linux) 2519c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCHR(VG_Z_LD_LINUX_SO_2, strchr) 2529c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCHR(VG_Z_LD_LINUX_SO_2, index) 2539c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCHR(VG_Z_LD_LINUX_X86_64_SO_2, strchr) 2549c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCHR(VG_Z_LD_LINUX_X86_64_SO_2, index) 2559c7779b64eacf264ee427b97ae0df8596b1960ccbart# endif 2569c7779b64eacf264ee427b97ae0df8596b1960ccbart 2579c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 2589c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCHR(VG_Z_LIBC_SONAME, strchr) 259c3e09f66fa315ff9b207db6925a80bc5693ce838sewardj# if DARWIN_VERS == DARWIN_10_9 260c3e09f66fa315ff9b207db6925a80bc5693ce838sewardj STRCHR(libsystemZuplatformZddylib, _platform_strchr) 261c3e09f66fa315ff9b207db6925a80bc5693ce838sewardj# endif 2629090d2f691fd59c3a67c55e74f3c66c9c5671b01rhyskidd# if DARWIN_VERS >= DARWIN_10_10 2639951323b382138ba9ffbb33901af85bc0ad5dc3frhyskidd /* _platform_strchr$VARIANT$Generic */ 2649951323b382138ba9ffbb33901af85bc0ad5dc3frhyskidd STRCHR(libsystemZuplatformZddylib, _platform_strchr$VARIANT$Generic) 265366cefb68a2b15558ed1ddcda74c675d3ac39948rhyskidd STRCHR(libsystemZuplatformZddylib, _platform_strchr$VARIANT$Haswell) 2669951323b382138ba9ffbb33901af85bc0ad5dc3frhyskidd# endif 2678eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 2688eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 2698eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRCHR(VG_Z_LIBC_SONAME, strchr) 2708eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRCHR(VG_Z_LIBC_SONAME, index) 2718eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRCHR(VG_Z_LD_SO_1, strchr) 2728eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 2739c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 2749c7779b64eacf264ee427b97ae0df8596b1960ccbart 2759c7779b64eacf264ee427b97ae0df8596b1960ccbart 2769c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strcat ----------------------*/ 2779c7779b64eacf264ee427b97ae0df8596b1960ccbart 2789c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRCAT(soname, fnname) \ 2799c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20030,soname,fnname) \ 2809c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src ); \ 2819c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20030,soname,fnname) \ 2829c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src ) \ 2839c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 2849c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* src_orig = src; \ 2859c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar* dst_orig = dst; \ 2869c7779b64eacf264ee427b97ae0df8596b1960ccbart while (*dst) dst++; \ 2879c7779b64eacf264ee427b97ae0df8596b1960ccbart while (*src) *dst++ = *src++; \ 2889c7779b64eacf264ee427b97ae0df8596b1960ccbart *dst = 0; \ 2899c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 2909c7779b64eacf264ee427b97ae0df8596b1960ccbart /* This is a bit redundant, I think; any overlap and the strcat will */ \ 2919c7779b64eacf264ee427b97ae0df8596b1960ccbart /* go forever... or until a seg fault occurs. */ \ 2929c7779b64eacf264ee427b97ae0df8596b1960ccbart if (is_overlap(dst_orig, \ 2939c7779b64eacf264ee427b97ae0df8596b1960ccbart src_orig, \ 2949c7779b64eacf264ee427b97ae0df8596b1960ccbart (Addr)dst-(Addr)dst_orig+1, \ 2959c7779b64eacf264ee427b97ae0df8596b1960ccbart (Addr)src-(Addr)src_orig+1)) \ 2969c7779b64eacf264ee427b97ae0df8596b1960ccbart RECORD_OVERLAP_ERROR("strcat", dst_orig, src_orig, 0); \ 2979c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 2989c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst_orig; \ 2999c7779b64eacf264ee427b97ae0df8596b1960ccbart } 3009c7779b64eacf264ee427b97ae0df8596b1960ccbart 3019c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 3029c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCAT(VG_Z_LIBC_SONAME, strcat) 3039c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCAT(VG_Z_LIBC_SONAME, __GI_strcat) 3049c7779b64eacf264ee427b97ae0df8596b1960ccbart 3059c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 3069c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRCAT(VG_Z_LIBC_SONAME, strcat) 3079c7779b64eacf264ee427b97ae0df8596b1960ccbart 3088eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 3098eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRCAT(VG_Z_LIBC_SONAME, strcat) 3108eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRCAT(VG_Z_LD_SO_1, strcat) 3118eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 3129c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 3139c7779b64eacf264ee427b97ae0df8596b1960ccbart 3149c7779b64eacf264ee427b97ae0df8596b1960ccbart 3159c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strncat ----------------------*/ 3169c7779b64eacf264ee427b97ae0df8596b1960ccbart 3179c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRNCAT(soname, fnname) \ 3189c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20040,soname,fnname) \ 3199c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src, SizeT n ); \ 3209c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20040,soname,fnname) \ 3219c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src, SizeT n ) \ 3229c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 3239c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* src_orig = src; \ 3249c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar* dst_orig = dst; \ 3259c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT m = 0; \ 3269c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 3279c7779b64eacf264ee427b97ae0df8596b1960ccbart while (*dst) dst++; \ 3289c7779b64eacf264ee427b97ae0df8596b1960ccbart while (m < n && *src) { m++; *dst++ = *src++; } /* concat <= n chars */ \ 3299c7779b64eacf264ee427b97ae0df8596b1960ccbart *dst = 0; /* always add null */ \ 3309c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 3319c7779b64eacf264ee427b97ae0df8596b1960ccbart /* This checks for overlap after copying, unavoidable without */ \ 3329c7779b64eacf264ee427b97ae0df8596b1960ccbart /* pre-counting lengths... should be ok */ \ 3339c7779b64eacf264ee427b97ae0df8596b1960ccbart if (is_overlap(dst_orig, \ 3349c7779b64eacf264ee427b97ae0df8596b1960ccbart src_orig, \ 3359c7779b64eacf264ee427b97ae0df8596b1960ccbart (Addr)dst-(Addr)dst_orig+1, \ 3369c7779b64eacf264ee427b97ae0df8596b1960ccbart (Addr)src-(Addr)src_orig+1)) \ 3379c7779b64eacf264ee427b97ae0df8596b1960ccbart RECORD_OVERLAP_ERROR("strncat", dst_orig, src_orig, n); \ 3389c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 3399c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst_orig; \ 3409c7779b64eacf264ee427b97ae0df8596b1960ccbart } 3419c7779b64eacf264ee427b97ae0df8596b1960ccbart 3429c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 3439c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCAT(VG_Z_LIBC_SONAME, strncat) 3449c7779b64eacf264ee427b97ae0df8596b1960ccbart 3459c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 3469c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRNCAT(VG_Z_LIBC_SONAME, strncat) 3479c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRNCAT(VG_Z_DYLD, strncat) 3489c7779b64eacf264ee427b97ae0df8596b1960ccbart 3498eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 3508eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRNCAT(VG_Z_LIBC_SONAME, strncat) 3518eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 3529c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 3539c7779b64eacf264ee427b97ae0df8596b1960ccbart 3549c7779b64eacf264ee427b97ae0df8596b1960ccbart 3559c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strlcat ----------------------*/ 3569c7779b64eacf264ee427b97ae0df8596b1960ccbart 3579c7779b64eacf264ee427b97ae0df8596b1960ccbart/* Append src to dst. n is the size of dst's buffer. dst is guaranteed 3589c7779b64eacf264ee427b97ae0df8596b1960ccbart to be nul-terminated after the copy, unless n <= strlen(dst_orig). 3599c7779b64eacf264ee427b97ae0df8596b1960ccbart Returns min(n, strlen(dst_orig)) + strlen(src_orig). 3609c7779b64eacf264ee427b97ae0df8596b1960ccbart Truncation occurred if retval >= n. 3619c7779b64eacf264ee427b97ae0df8596b1960ccbart*/ 3629c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRLCAT(soname, fnname) \ 3639c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20050,soname,fnname) \ 3649c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src, SizeT n ); \ 3659c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20050,soname,fnname) \ 3669c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src, SizeT n ) \ 3679c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 3689c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* src_orig = src; \ 3699c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar* dst_orig = dst; \ 3709c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT m = 0; \ 3719c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 3729c7779b64eacf264ee427b97ae0df8596b1960ccbart while (m < n && *dst) { m++; dst++; } \ 3739c7779b64eacf264ee427b97ae0df8596b1960ccbart if (m < n) { \ 3749c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Fill as far as dst_orig[n-2], then nul-terminate. */ \ 3759c7779b64eacf264ee427b97ae0df8596b1960ccbart while (m < n-1 && *src) { m++; *dst++ = *src++; } \ 3769c7779b64eacf264ee427b97ae0df8596b1960ccbart *dst = 0; \ 3779c7779b64eacf264ee427b97ae0df8596b1960ccbart } else { \ 3789c7779b64eacf264ee427b97ae0df8596b1960ccbart /* No space to copy anything to dst. m == n */ \ 3799c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 3809c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Finish counting min(n, strlen(dst_orig)) + strlen(src_orig) */ \ 3819c7779b64eacf264ee427b97ae0df8596b1960ccbart while (*src) { m++; src++; } \ 3829c7779b64eacf264ee427b97ae0df8596b1960ccbart /* This checks for overlap after copying, unavoidable without */ \ 3839c7779b64eacf264ee427b97ae0df8596b1960ccbart /* pre-counting lengths... should be ok */ \ 3849c7779b64eacf264ee427b97ae0df8596b1960ccbart if (is_overlap(dst_orig, \ 3859c7779b64eacf264ee427b97ae0df8596b1960ccbart src_orig, \ 3869c7779b64eacf264ee427b97ae0df8596b1960ccbart (Addr)dst-(Addr)dst_orig+1, \ 3879c7779b64eacf264ee427b97ae0df8596b1960ccbart (Addr)src-(Addr)src_orig+1)) \ 3889c7779b64eacf264ee427b97ae0df8596b1960ccbart RECORD_OVERLAP_ERROR("strlcat", dst_orig, src_orig, n); \ 3899c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 3909c7779b64eacf264ee427b97ae0df8596b1960ccbart return m; \ 3919c7779b64eacf264ee427b97ae0df8596b1960ccbart } 3929c7779b64eacf264ee427b97ae0df8596b1960ccbart 3939c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 3949c7779b64eacf264ee427b97ae0df8596b1960ccbart 3959c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 3969c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRLCAT(VG_Z_LIBC_SONAME, strlcat) 3979c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRLCAT(VG_Z_DYLD, strlcat) 3989c7779b64eacf264ee427b97ae0df8596b1960ccbart STRLCAT(VG_Z_LIBC_SONAME, strlcat) 3999c7779b64eacf264ee427b97ae0df8596b1960ccbart 4008eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 4018eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRLCAT(VG_Z_LIBC_SONAME, strlcat) 4028eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 4039c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 4049c7779b64eacf264ee427b97ae0df8596b1960ccbart 4059c7779b64eacf264ee427b97ae0df8596b1960ccbart 4069c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strnlen ----------------------*/ 4079c7779b64eacf264ee427b97ae0df8596b1960ccbart 4089c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRNLEN(soname, fnname) \ 4099c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20060,soname,fnname) \ 4109c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* str, SizeT n ); \ 4119c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20060,soname,fnname) \ 4129c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* str, SizeT n ) \ 4139c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 4149c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT i = 0; \ 4159c7779b64eacf264ee427b97ae0df8596b1960ccbart while (i < n && str[i] != 0) i++; \ 4169c7779b64eacf264ee427b97ae0df8596b1960ccbart return i; \ 4179c7779b64eacf264ee427b97ae0df8596b1960ccbart } 4189c7779b64eacf264ee427b97ae0df8596b1960ccbart 4199c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 4209c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNLEN(VG_Z_LIBC_SONAME, strnlen) 4219c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNLEN(VG_Z_LIBC_SONAME, __GI_strnlen) 4229c7779b64eacf264ee427b97ae0df8596b1960ccbart 4239c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 424aec49a463fd7c90ef190ff72318e50224e463e90sewardj# if DARWIN_VERS == DARWIN_10_9 425aec49a463fd7c90ef190ff72318e50224e463e90sewardj STRNLEN(libsystemZucZddylib, strnlen) 426aec49a463fd7c90ef190ff72318e50224e463e90sewardj# endif 4279c7779b64eacf264ee427b97ae0df8596b1960ccbart 4288eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 4298eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRNLEN(VG_Z_LIBC_SONAME, strnlen) 4308eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 4319c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 4329c7779b64eacf264ee427b97ae0df8596b1960ccbart 4339c7779b64eacf264ee427b97ae0df8596b1960ccbart 4349c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strlen ----------------------*/ 4359c7779b64eacf264ee427b97ae0df8596b1960ccbart 4369c7779b64eacf264ee427b97ae0df8596b1960ccbart// Note that this replacement often doesn't get used because gcc inlines 4379c7779b64eacf264ee427b97ae0df8596b1960ccbart// calls to strlen() with its own built-in version. This can be very 4389c7779b64eacf264ee427b97ae0df8596b1960ccbart// confusing if you aren't expecting it. Other small functions in 4399c7779b64eacf264ee427b97ae0df8596b1960ccbart// this file may also be inline by gcc. 4409c7779b64eacf264ee427b97ae0df8596b1960ccbart 4419c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRLEN(soname, fnname) \ 4429c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20070,soname,fnname) \ 4439c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* str ); \ 4449c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20070,soname,fnname) \ 4459c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* str ) \ 4469c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 4479c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT i = 0; \ 4489c7779b64eacf264ee427b97ae0df8596b1960ccbart while (str[i] != 0) i++; \ 4499c7779b64eacf264ee427b97ae0df8596b1960ccbart return i; \ 4509c7779b64eacf264ee427b97ae0df8596b1960ccbart } 4519c7779b64eacf264ee427b97ae0df8596b1960ccbart 4529c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 4539c7779b64eacf264ee427b97ae0df8596b1960ccbart STRLEN(VG_Z_LIBC_SONAME, strlen) 4549c7779b64eacf264ee427b97ae0df8596b1960ccbart STRLEN(VG_Z_LIBC_SONAME, __GI_strlen) 4559c7779b64eacf264ee427b97ae0df8596b1960ccbart STRLEN(VG_Z_LIBC_SONAME, __strlen_sse2) 4569c7779b64eacf264ee427b97ae0df8596b1960ccbart STRLEN(VG_Z_LIBC_SONAME, __strlen_sse2_no_bsf) 4579c7779b64eacf264ee427b97ae0df8596b1960ccbart STRLEN(VG_Z_LIBC_SONAME, __strlen_sse42) 4589c7779b64eacf264ee427b97ae0df8596b1960ccbart STRLEN(VG_Z_LD_LINUX_SO_2, strlen) 4599c7779b64eacf264ee427b97ae0df8596b1960ccbart STRLEN(VG_Z_LD_LINUX_X86_64_SO_2, strlen) 46026ed419d60369d0545510eba0832566e24452e1esewardj# if defined(VGPV_arm_linux_android) \ 46126ed419d60369d0545510eba0832566e24452e1esewardj || defined(VGPV_x86_linux_android) \ 4629c6b05db45362b1afb981aa8298ab12ab4027b1adejanj || defined(VGPV_mips32_linux_android) 4639c7779b64eacf264ee427b97ae0df8596b1960ccbart STRLEN(NONE, __dl_strlen); /* in /system/bin/linker */ 4649c7779b64eacf264ee427b97ae0df8596b1960ccbart# endif 4659c7779b64eacf264ee427b97ae0df8596b1960ccbart 4669c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 4679c7779b64eacf264ee427b97ae0df8596b1960ccbart STRLEN(VG_Z_LIBC_SONAME, strlen) 4689090d2f691fd59c3a67c55e74f3c66c9c5671b01rhyskidd# if DARWIN_VERS >= DARWIN_10_9 469c3e09f66fa315ff9b207db6925a80bc5693ce838sewardj STRLEN(libsystemZucZddylib, strlen) 470c3e09f66fa315ff9b207db6925a80bc5693ce838sewardj# endif 4718eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 4728eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 4738eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRLEN(VG_Z_LIBC_SONAME, strlen) 4748eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRLEN(VG_Z_LD_SO_1, strlen) 4758eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 4769c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 4779c7779b64eacf264ee427b97ae0df8596b1960ccbart 4789c7779b64eacf264ee427b97ae0df8596b1960ccbart 4799c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strcpy ----------------------*/ 4809c7779b64eacf264ee427b97ae0df8596b1960ccbart 4819c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRCPY(soname, fnname) \ 4829c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20080,soname,fnname) \ 4839c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src ); \ 4849c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20080,soname,fnname) \ 4859c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src ) \ 4869c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 4879c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* src_orig = src; \ 4889c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar* dst_orig = dst; \ 4899c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 4909c7779b64eacf264ee427b97ae0df8596b1960ccbart while (*src) *dst++ = *src++; \ 4919c7779b64eacf264ee427b97ae0df8596b1960ccbart *dst = 0; \ 4929c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 4939c7779b64eacf264ee427b97ae0df8596b1960ccbart /* This checks for overlap after copying, unavoidable without */ \ 4949c7779b64eacf264ee427b97ae0df8596b1960ccbart /* pre-counting length... should be ok */ \ 4959c7779b64eacf264ee427b97ae0df8596b1960ccbart if (is_overlap(dst_orig, \ 4969c7779b64eacf264ee427b97ae0df8596b1960ccbart src_orig, \ 4979c7779b64eacf264ee427b97ae0df8596b1960ccbart (Addr)dst-(Addr)dst_orig+1, \ 4989c7779b64eacf264ee427b97ae0df8596b1960ccbart (Addr)src-(Addr)src_orig+1)) \ 4999c7779b64eacf264ee427b97ae0df8596b1960ccbart RECORD_OVERLAP_ERROR("strcpy", dst_orig, src_orig, 0); \ 5009c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 5019c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst_orig; \ 5029c7779b64eacf264ee427b97ae0df8596b1960ccbart } 5039c7779b64eacf264ee427b97ae0df8596b1960ccbart 5049c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 5059c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCPY(VG_Z_LIBC_SONAME, strcpy) 5069c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCPY(VG_Z_LIBC_SONAME, __GI_strcpy) 5079c7779b64eacf264ee427b97ae0df8596b1960ccbart 5089c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 5099c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCPY(VG_Z_LIBC_SONAME, strcpy) 510aec49a463fd7c90ef190ff72318e50224e463e90sewardj# if DARWIN_VERS == DARWIN_10_9 511aec49a463fd7c90ef190ff72318e50224e463e90sewardj STRCPY(libsystemZucZddylib, strcpy) 512aec49a463fd7c90ef190ff72318e50224e463e90sewardj# endif 5139c7779b64eacf264ee427b97ae0df8596b1960ccbart 5148eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 5158eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRCPY(VG_Z_LIBC_SONAME, strcpy) 5168eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRCPY(VG_Z_LD_SO_1, strcpy) 5178eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 5189c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 5199c7779b64eacf264ee427b97ae0df8596b1960ccbart 5209c7779b64eacf264ee427b97ae0df8596b1960ccbart 5219c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strncpy ----------------------*/ 5229c7779b64eacf264ee427b97ae0df8596b1960ccbart 5239c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRNCPY(soname, fnname) \ 5249c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20090,soname,fnname) \ 5259c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src, SizeT n ); \ 5269c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20090,soname,fnname) \ 5279c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src, SizeT n ) \ 5289c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 5299c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* src_orig = src; \ 5309c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar* dst_orig = dst; \ 5319c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT m = 0; \ 5329c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 5339c7779b64eacf264ee427b97ae0df8596b1960ccbart while (m < n && *src) { m++; *dst++ = *src++; } \ 5349c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Check for overlap after copying; all n bytes of dst are relevant, */ \ 5359c7779b64eacf264ee427b97ae0df8596b1960ccbart /* but only m+1 bytes of src if terminator was found */ \ 5369c7779b64eacf264ee427b97ae0df8596b1960ccbart if (is_overlap(dst_orig, src_orig, n, (m < n) ? m+1 : n)) \ 5379c7779b64eacf264ee427b97ae0df8596b1960ccbart RECORD_OVERLAP_ERROR("strncpy", dst, src, n); \ 5389c7779b64eacf264ee427b97ae0df8596b1960ccbart while (m++ < n) *dst++ = 0; /* must pad remainder with nulls */ \ 5399c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 5409c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst_orig; \ 5419c7779b64eacf264ee427b97ae0df8596b1960ccbart } 5429c7779b64eacf264ee427b97ae0df8596b1960ccbart 5439c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 5449c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCPY(VG_Z_LIBC_SONAME, strncpy) 5459c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCPY(VG_Z_LIBC_SONAME, __GI_strncpy) 5469c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCPY(VG_Z_LIBC_SONAME, __strncpy_sse2) 5479c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCPY(VG_Z_LIBC_SONAME, __strncpy_sse2_unaligned) 5489c7779b64eacf264ee427b97ae0df8596b1960ccbart 5499c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 5509c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCPY(VG_Z_LIBC_SONAME, strncpy) 5519090d2f691fd59c3a67c55e74f3c66c9c5671b01rhyskidd# if DARWIN_VERS >= DARWIN_10_9 552aec49a463fd7c90ef190ff72318e50224e463e90sewardj STRNCPY(libsystemZucZddylib, strncpy) 553aec49a463fd7c90ef190ff72318e50224e463e90sewardj# endif 5549c7779b64eacf264ee427b97ae0df8596b1960ccbart 5558eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 5568eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRNCPY(VG_Z_LIBC_SONAME, strncpy) 5578eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRNCPY(VG_Z_LD_SO_1, strncpy) 5588eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 5599c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 5609c7779b64eacf264ee427b97ae0df8596b1960ccbart 5619c7779b64eacf264ee427b97ae0df8596b1960ccbart 5629c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strlcpy ----------------------*/ 5639c7779b64eacf264ee427b97ae0df8596b1960ccbart 5649c7779b64eacf264ee427b97ae0df8596b1960ccbart/* Copy up to n-1 bytes from src to dst. Then nul-terminate dst if n > 0. 5659c7779b64eacf264ee427b97ae0df8596b1960ccbart Returns strlen(src). Does not zero-fill the remainder of dst. */ 5669c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRLCPY(soname, fnname) \ 5679c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20100,soname,fnname) \ 5689c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src, SizeT n ); \ 5699c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20100,soname,fnname) \ 5709c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src, SizeT n ) \ 5719c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 5729c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* src_orig = src; \ 5739c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar* dst_orig = dst; \ 5749c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT m = 0; \ 5759c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 5768eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRLCPY_CHECK_FOR_DSTSIZE_ZERO \ 5778eb8bab992e3998c33770b0cdb16059a8b918a06sewardj \ 5789c7779b64eacf264ee427b97ae0df8596b1960ccbart while (m < n-1 && *src) { m++; *dst++ = *src++; } \ 5799c7779b64eacf264ee427b97ae0df8596b1960ccbart /* m non-nul bytes have now been copied, and m <= n-1. */ \ 5809c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Check for overlap after copying; all n bytes of dst are relevant, */ \ 5819c7779b64eacf264ee427b97ae0df8596b1960ccbart /* but only m+1 bytes of src if terminator was found */ \ 5829c7779b64eacf264ee427b97ae0df8596b1960ccbart if (is_overlap(dst_orig, src_orig, n, (m < n) ? m+1 : n)) \ 5839c7779b64eacf264ee427b97ae0df8596b1960ccbart RECORD_OVERLAP_ERROR("strlcpy", dst, src, n); \ 5849c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Nul-terminate dst. */ \ 5859c7779b64eacf264ee427b97ae0df8596b1960ccbart if (n > 0) *dst = 0; \ 5869c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Finish counting strlen(src). */ \ 5879c7779b64eacf264ee427b97ae0df8596b1960ccbart while (*src) src++; \ 5889c7779b64eacf264ee427b97ae0df8596b1960ccbart return src - src_orig; \ 5899c7779b64eacf264ee427b97ae0df8596b1960ccbart } 5909c7779b64eacf264ee427b97ae0df8596b1960ccbart 5919c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 5929c7779b64eacf264ee427b97ae0df8596b1960ccbart 5939c6b05db45362b1afb981aa8298ab12ab4027b1adejanj#if defined(VGPV_arm_linux_android) || defined(VGPV_x86_linux_android) \ 5949c6b05db45362b1afb981aa8298ab12ab4027b1adejanj || defined(VGPV_mips32_linux_android) 5958eb8bab992e3998c33770b0cdb16059a8b918a06sewardj #define STRLCPY_CHECK_FOR_DSTSIZE_ZERO 5969c7779b64eacf264ee427b97ae0df8596b1960ccbart STRLCPY(VG_Z_LIBC_SONAME, strlcpy); 5979c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 5989c7779b64eacf264ee427b97ae0df8596b1960ccbart 5999c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 6008eb8bab992e3998c33770b0cdb16059a8b918a06sewardj #define STRLCPY_CHECK_FOR_DSTSIZE_ZERO 6019c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRLCPY(VG_Z_LIBC_SONAME, strlcpy) 6029c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRLCPY(VG_Z_DYLD, strlcpy) 6039c7779b64eacf264ee427b97ae0df8596b1960ccbart STRLCPY(VG_Z_LIBC_SONAME, strlcpy) 6049c7779b64eacf264ee427b97ae0df8596b1960ccbart 6058eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 6068eb8bab992e3998c33770b0cdb16059a8b918a06sewardj /* special case for n == 0 which is undocumented but heavily used */ 6078eb8bab992e3998c33770b0cdb16059a8b918a06sewardj #define STRLCPY_CHECK_FOR_DSTSIZE_ZERO \ 6088eb8bab992e3998c33770b0cdb16059a8b918a06sewardj if (n == 0) { \ 6098eb8bab992e3998c33770b0cdb16059a8b918a06sewardj while (*src) src++; \ 6108eb8bab992e3998c33770b0cdb16059a8b918a06sewardj return src - src_orig; \ 6118eb8bab992e3998c33770b0cdb16059a8b918a06sewardj } 6128eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 6138eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRLCPY(VG_Z_LIBC_SONAME, strlcpy) 6148eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 6159c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 6169c7779b64eacf264ee427b97ae0df8596b1960ccbart 6179c7779b64eacf264ee427b97ae0df8596b1960ccbart 6189c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strncmp ----------------------*/ 6199c7779b64eacf264ee427b97ae0df8596b1960ccbart 6209c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRNCMP(soname, fnname) \ 6219c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20110,soname,fnname) \ 6229c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* s1, const char* s2, SizeT nmax ); \ 6239c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20110,soname,fnname) \ 6249c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* s1, const char* s2, SizeT nmax ) \ 6259c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 6269c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT n = 0; \ 6279c7779b64eacf264ee427b97ae0df8596b1960ccbart while (True) { \ 6289c7779b64eacf264ee427b97ae0df8596b1960ccbart if (n >= nmax) return 0; \ 6299c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*s1 == 0 && *s2 == 0) return 0; \ 6309c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*s1 == 0) return -1; \ 6319c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*s2 == 0) return 1; \ 6329c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 6339c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*(const UChar*)s1 < *(const UChar*)s2) return -1; \ 6349c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*(const UChar*)s1 > *(const UChar*)s2) return 1; \ 6359c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 6369c7779b64eacf264ee427b97ae0df8596b1960ccbart s1++; s2++; n++; \ 6379c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 6389c7779b64eacf264ee427b97ae0df8596b1960ccbart } 6399c7779b64eacf264ee427b97ae0df8596b1960ccbart 6409c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 6419c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCMP(VG_Z_LIBC_SONAME, strncmp) 6429c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCMP(VG_Z_LIBC_SONAME, __GI_strncmp) 6439c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCMP(VG_Z_LIBC_SONAME, __strncmp_sse2) 6449c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCMP(VG_Z_LIBC_SONAME, __strncmp_sse42) 6459c7779b64eacf264ee427b97ae0df8596b1960ccbart 6469c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 6479c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCMP(VG_Z_LIBC_SONAME, strncmp) 6489090d2f691fd59c3a67c55e74f3c66c9c5671b01rhyskidd# if DARWIN_VERS >= DARWIN_10_9 649798e95b2ac2f772cc4b347650d37fa4ac2de1320sewardj STRNCMP(libsystemZuplatformZddylib, _platform_strncmp) 650798e95b2ac2f772cc4b347650d37fa4ac2de1320sewardj# endif 6519c7779b64eacf264ee427b97ae0df8596b1960ccbart 6528eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 6538eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRNCMP(VG_Z_LIBC_SONAME, strncmp) 6548eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 6559c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 6569c7779b64eacf264ee427b97ae0df8596b1960ccbart 6579c7779b64eacf264ee427b97ae0df8596b1960ccbart 6589c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strcasecmp ----------------------*/ 6599c7779b64eacf264ee427b97ae0df8596b1960ccbart 6609c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRCASECMP(soname, fnname) \ 6619c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20120,soname,fnname) \ 6629c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* s1, const char* s2 ); \ 6639c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20120,soname,fnname) \ 6649c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* s1, const char* s2 ) \ 6659c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 6669c7779b64eacf264ee427b97ae0df8596b1960ccbart extern int tolower(int); \ 6679c7779b64eacf264ee427b97ae0df8596b1960ccbart register UChar c1; \ 6689c7779b64eacf264ee427b97ae0df8596b1960ccbart register UChar c2; \ 6699c7779b64eacf264ee427b97ae0df8596b1960ccbart while (True) { \ 6709c7779b64eacf264ee427b97ae0df8596b1960ccbart c1 = tolower(*(const UChar *)s1); \ 6719c7779b64eacf264ee427b97ae0df8596b1960ccbart c2 = tolower(*(const UChar *)s2); \ 6729c7779b64eacf264ee427b97ae0df8596b1960ccbart if (c1 != c2) break; \ 6739c7779b64eacf264ee427b97ae0df8596b1960ccbart if (c1 == 0) break; \ 6749c7779b64eacf264ee427b97ae0df8596b1960ccbart s1++; s2++; \ 6759c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 6769c7779b64eacf264ee427b97ae0df8596b1960ccbart if ((UChar)c1 < (UChar)c2) return -1; \ 6779c7779b64eacf264ee427b97ae0df8596b1960ccbart if ((UChar)c1 > (UChar)c2) return 1; \ 6789c7779b64eacf264ee427b97ae0df8596b1960ccbart return 0; \ 6799c7779b64eacf264ee427b97ae0df8596b1960ccbart } 6809c7779b64eacf264ee427b97ae0df8596b1960ccbart 6819c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 68226ed419d60369d0545510eba0832566e24452e1esewardj# if !defined(VGPV_arm_linux_android) \ 68326ed419d60369d0545510eba0832566e24452e1esewardj && !defined(VGPV_x86_linux_android) \ 68426ed419d60369d0545510eba0832566e24452e1esewardj && !defined(VGPV_mips32_linux_android) \ 68526ed419d60369d0545510eba0832566e24452e1esewardj && !defined(VGPV_arm64_linux_android) 6869c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCASECMP(VG_Z_LIBC_SONAME, strcasecmp) 6879c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCASECMP(VG_Z_LIBC_SONAME, __GI_strcasecmp) 6889c7779b64eacf264ee427b97ae0df8596b1960ccbart# endif 6899c7779b64eacf264ee427b97ae0df8596b1960ccbart 6909c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 6919c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRCASECMP(VG_Z_LIBC_SONAME, strcasecmp) 6929c7779b64eacf264ee427b97ae0df8596b1960ccbart 6938eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 6948eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRCASECMP(VG_Z_LIBC_SONAME, strcasecmp) 6958eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 6969c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 6979c7779b64eacf264ee427b97ae0df8596b1960ccbart 6989c7779b64eacf264ee427b97ae0df8596b1960ccbart 6999c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strncasecmp ----------------------*/ 7009c7779b64eacf264ee427b97ae0df8596b1960ccbart 7019c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRNCASECMP(soname, fnname) \ 7029c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20130,soname,fnname) \ 7039c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* s1, const char* s2, SizeT nmax ); \ 7049c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20130,soname,fnname) \ 7059c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* s1, const char* s2, SizeT nmax ) \ 7069c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 7079c7779b64eacf264ee427b97ae0df8596b1960ccbart extern int tolower(int); \ 7089c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT n = 0; \ 7099c7779b64eacf264ee427b97ae0df8596b1960ccbart while (True) { \ 7109c7779b64eacf264ee427b97ae0df8596b1960ccbart if (n >= nmax) return 0; \ 7119c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*s1 == 0 && *s2 == 0) return 0; \ 7129c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*s1 == 0) return -1; \ 7139c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*s2 == 0) return 1; \ 7149c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 7159c7779b64eacf264ee427b97ae0df8596b1960ccbart if (tolower(*(const UChar *)s1) \ 7169c7779b64eacf264ee427b97ae0df8596b1960ccbart < tolower(*(const UChar*)s2)) return -1; \ 7179c7779b64eacf264ee427b97ae0df8596b1960ccbart if (tolower(*(const UChar *)s1) \ 7189c7779b64eacf264ee427b97ae0df8596b1960ccbart > tolower(*(const UChar *)s2)) return 1; \ 7199c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 7209c7779b64eacf264ee427b97ae0df8596b1960ccbart s1++; s2++; n++; \ 7219c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 7229c7779b64eacf264ee427b97ae0df8596b1960ccbart } 7239c7779b64eacf264ee427b97ae0df8596b1960ccbart 7249c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 72526ed419d60369d0545510eba0832566e24452e1esewardj# if !defined(VGPV_arm_linux_android) \ 72626ed419d60369d0545510eba0832566e24452e1esewardj && !defined(VGPV_x86_linux_android) \ 72726ed419d60369d0545510eba0832566e24452e1esewardj && !defined(VGPV_mips32_linux_android) \ 72826ed419d60369d0545510eba0832566e24452e1esewardj && !defined(VGPV_arm64_linux_android) 7299c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCASECMP(VG_Z_LIBC_SONAME, strncasecmp) 7309c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCASECMP(VG_Z_LIBC_SONAME, __GI_strncasecmp) 7319c7779b64eacf264ee427b97ae0df8596b1960ccbart# endif 7329c7779b64eacf264ee427b97ae0df8596b1960ccbart 7339c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 7349c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRNCASECMP(VG_Z_LIBC_SONAME, strncasecmp) 7359c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRNCASECMP(VG_Z_DYLD, strncasecmp) 7369c7779b64eacf264ee427b97ae0df8596b1960ccbart 7378eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 7388eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRNCASECMP(VG_Z_LIBC_SONAME, strncasecmp) 7398eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 7409c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 7419c7779b64eacf264ee427b97ae0df8596b1960ccbart 7429c7779b64eacf264ee427b97ae0df8596b1960ccbart 7439c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strcasecmp_l ----------------------*/ 7449c7779b64eacf264ee427b97ae0df8596b1960ccbart 7459c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRCASECMP_L(soname, fnname) \ 7469c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20140,soname,fnname) \ 7479c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* s1, const char* s2, void* locale ); \ 7489c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20140,soname,fnname) \ 7499c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* s1, const char* s2, void* locale ) \ 7509c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 7519c7779b64eacf264ee427b97ae0df8596b1960ccbart extern int tolower_l(int, void*) __attribute__((weak)); \ 7529c7779b64eacf264ee427b97ae0df8596b1960ccbart register UChar c1; \ 7539c7779b64eacf264ee427b97ae0df8596b1960ccbart register UChar c2; \ 7549c7779b64eacf264ee427b97ae0df8596b1960ccbart while (True) { \ 7559c7779b64eacf264ee427b97ae0df8596b1960ccbart c1 = tolower_l(*(const UChar *)s1, locale); \ 7569c7779b64eacf264ee427b97ae0df8596b1960ccbart c2 = tolower_l(*(const UChar *)s2, locale); \ 7579c7779b64eacf264ee427b97ae0df8596b1960ccbart if (c1 != c2) break; \ 7589c7779b64eacf264ee427b97ae0df8596b1960ccbart if (c1 == 0) break; \ 7599c7779b64eacf264ee427b97ae0df8596b1960ccbart s1++; s2++; \ 7609c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 7619c7779b64eacf264ee427b97ae0df8596b1960ccbart if ((UChar)c1 < (UChar)c2) return -1; \ 7629c7779b64eacf264ee427b97ae0df8596b1960ccbart if ((UChar)c1 > (UChar)c2) return 1; \ 7639c7779b64eacf264ee427b97ae0df8596b1960ccbart return 0; \ 7649c7779b64eacf264ee427b97ae0df8596b1960ccbart } 7659c7779b64eacf264ee427b97ae0df8596b1960ccbart 7669c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 7679c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCASECMP_L(VG_Z_LIBC_SONAME, strcasecmp_l) 7689c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCASECMP_L(VG_Z_LIBC_SONAME, __GI_strcasecmp_l) 7699c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCASECMP_L(VG_Z_LIBC_SONAME, __GI___strcasecmp_l) 7709c7779b64eacf264ee427b97ae0df8596b1960ccbart 7719c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 7729c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRCASECMP_L(VG_Z_LIBC_SONAME, strcasecmp_l) 7739c7779b64eacf264ee427b97ae0df8596b1960ccbart 7748eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 7758eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 7769c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 7779c7779b64eacf264ee427b97ae0df8596b1960ccbart 7789c7779b64eacf264ee427b97ae0df8596b1960ccbart 7799c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strncasecmp_l ----------------------*/ 7809c7779b64eacf264ee427b97ae0df8596b1960ccbart 7819c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRNCASECMP_L(soname, fnname) \ 7829c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20150,soname,fnname) \ 7839c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* s1, const char* s2, SizeT nmax, void* locale ); \ 7849c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20150,soname,fnname) \ 7859c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* s1, const char* s2, SizeT nmax, void* locale ) \ 7869c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 7879c7779b64eacf264ee427b97ae0df8596b1960ccbart extern int tolower_l(int, void*) __attribute__((weak)); \ 7889c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT n = 0; \ 7899c7779b64eacf264ee427b97ae0df8596b1960ccbart while (True) { \ 7909c7779b64eacf264ee427b97ae0df8596b1960ccbart if (n >= nmax) return 0; \ 7919c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*s1 == 0 && *s2 == 0) return 0; \ 7929c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*s1 == 0) return -1; \ 7939c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*s2 == 0) return 1; \ 7949c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 7959c7779b64eacf264ee427b97ae0df8596b1960ccbart if (tolower_l(*(const UChar *)s1, locale) \ 7969c7779b64eacf264ee427b97ae0df8596b1960ccbart < tolower_l(*(const UChar *)s2, locale)) return -1; \ 7979c7779b64eacf264ee427b97ae0df8596b1960ccbart if (tolower_l(*(const UChar *)s1, locale) \ 7989c7779b64eacf264ee427b97ae0df8596b1960ccbart > tolower_l(*(const UChar *)s2, locale)) return 1; \ 7999c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 8009c7779b64eacf264ee427b97ae0df8596b1960ccbart s1++; s2++; n++; \ 8019c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 8029c7779b64eacf264ee427b97ae0df8596b1960ccbart } 8039c7779b64eacf264ee427b97ae0df8596b1960ccbart 8049c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 8059c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCASECMP_L(VG_Z_LIBC_SONAME, strncasecmp_l) 8069c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCASECMP_L(VG_Z_LIBC_SONAME, __GI_strncasecmp_l) 8079c7779b64eacf264ee427b97ae0df8596b1960ccbart STRNCASECMP_L(VG_Z_LIBC_SONAME, __GI___strncasecmp_l) 8089c7779b64eacf264ee427b97ae0df8596b1960ccbart 8099c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 8109c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRNCASECMP_L(VG_Z_LIBC_SONAME, strncasecmp_l) 8119c7779b64eacf264ee427b97ae0df8596b1960ccbart //STRNCASECMP_L(VG_Z_DYLD, strncasecmp_l) 8129c7779b64eacf264ee427b97ae0df8596b1960ccbart 8138eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 8148eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 8159c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 8169c7779b64eacf264ee427b97ae0df8596b1960ccbart 8179c7779b64eacf264ee427b97ae0df8596b1960ccbart 8189c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strcmp ----------------------*/ 8199c7779b64eacf264ee427b97ae0df8596b1960ccbart 8209c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRCMP(soname, fnname) \ 8219c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20160,soname,fnname) \ 8229c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* s1, const char* s2 ); \ 8239c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20160,soname,fnname) \ 8249c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const char* s1, const char* s2 ) \ 8259c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 8269c7779b64eacf264ee427b97ae0df8596b1960ccbart register UChar c1; \ 8279c7779b64eacf264ee427b97ae0df8596b1960ccbart register UChar c2; \ 8289c7779b64eacf264ee427b97ae0df8596b1960ccbart while (True) { \ 8299c7779b64eacf264ee427b97ae0df8596b1960ccbart c1 = *(const UChar *)s1; \ 8309c7779b64eacf264ee427b97ae0df8596b1960ccbart c2 = *(const UChar *)s2; \ 8319c7779b64eacf264ee427b97ae0df8596b1960ccbart if (c1 != c2) break; \ 8329c7779b64eacf264ee427b97ae0df8596b1960ccbart if (c1 == 0) break; \ 8339c7779b64eacf264ee427b97ae0df8596b1960ccbart s1++; s2++; \ 8349c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 8359c7779b64eacf264ee427b97ae0df8596b1960ccbart if ((UChar)c1 < (UChar)c2) return -1; \ 8369c7779b64eacf264ee427b97ae0df8596b1960ccbart if ((UChar)c1 > (UChar)c2) return 1; \ 8379c7779b64eacf264ee427b97ae0df8596b1960ccbart return 0; \ 8389c7779b64eacf264ee427b97ae0df8596b1960ccbart } 8399c7779b64eacf264ee427b97ae0df8596b1960ccbart 8409c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 8419c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCMP(VG_Z_LIBC_SONAME, strcmp) 8429c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCMP(VG_Z_LIBC_SONAME, __GI_strcmp) 8439c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCMP(VG_Z_LIBC_SONAME, __strcmp_sse2) 8449c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCMP(VG_Z_LIBC_SONAME, __strcmp_sse42) 8459c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCMP(VG_Z_LD_LINUX_X86_64_SO_2, strcmp) 8469c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCMP(VG_Z_LD64_SO_1, strcmp) 8479c6b05db45362b1afb981aa8298ab12ab4027b1adejanj# if defined(VGPV_arm_linux_android) || defined(VGPV_x86_linux_android) \ 8489c6b05db45362b1afb981aa8298ab12ab4027b1adejanj || defined(VGPV_mips32_linux_android) 8499c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCMP(NONE, __dl_strcmp); /* in /system/bin/linker */ 8509c7779b64eacf264ee427b97ae0df8596b1960ccbart# endif 8519c7779b64eacf264ee427b97ae0df8596b1960ccbart 8529c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 8539c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCMP(VG_Z_LIBC_SONAME, strcmp) 8549090d2f691fd59c3a67c55e74f3c66c9c5671b01rhyskidd# if DARWIN_VERS >= DARWIN_10_9 855c3e09f66fa315ff9b207db6925a80bc5693ce838sewardj STRCMP(libsystemZuplatformZddylib, _platform_strcmp) 856c3e09f66fa315ff9b207db6925a80bc5693ce838sewardj# endif 8579c7779b64eacf264ee427b97ae0df8596b1960ccbart 8588eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 8598eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRCMP(VG_Z_LIBC_SONAME, strcmp) 8608eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRCMP(VG_Z_LD_SO_1, strcmp) 8618eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 8629c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 8639c7779b64eacf264ee427b97ae0df8596b1960ccbart 8649c7779b64eacf264ee427b97ae0df8596b1960ccbart 8659c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- memchr ----------------------*/ 8669c7779b64eacf264ee427b97ae0df8596b1960ccbart 8679c7779b64eacf264ee427b97ae0df8596b1960ccbart#define MEMCHR(soname, fnname) \ 8689c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZU(20170,soname,fnname) \ 8699c7779b64eacf264ee427b97ae0df8596b1960ccbart (const void *s, int c, SizeT n); \ 8709c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZU(20170,soname,fnname) \ 8719c7779b64eacf264ee427b97ae0df8596b1960ccbart (const void *s, int c, SizeT n) \ 8729c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 8739c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT i; \ 8749c7779b64eacf264ee427b97ae0df8596b1960ccbart UChar c0 = (UChar)c; \ 87570a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian const UChar* p = s; \ 8769c7779b64eacf264ee427b97ae0df8596b1960ccbart for (i = 0; i < n; i++) \ 87770a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian if (p[i] == c0) return CONST_CAST(void *,&p[i]); \ 8789c7779b64eacf264ee427b97ae0df8596b1960ccbart return NULL; \ 8799c7779b64eacf264ee427b97ae0df8596b1960ccbart } 8809c7779b64eacf264ee427b97ae0df8596b1960ccbart 8819c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 8829c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCHR(VG_Z_LIBC_SONAME, memchr) 8839c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCHR(VG_Z_LIBC_SONAME, __GI_memchr) 8849c7779b64eacf264ee427b97ae0df8596b1960ccbart 8859c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 886aec49a463fd7c90ef190ff72318e50224e463e90sewardj# if DARWIN_VERS == DARWIN_10_9 887798e95b2ac2f772cc4b347650d37fa4ac2de1320sewardj MEMCHR(VG_Z_DYLD, memchr) 888aec49a463fd7c90ef190ff72318e50224e463e90sewardj MEMCHR(libsystemZuplatformZddylib, _platform_memchr) 889aec49a463fd7c90ef190ff72318e50224e463e90sewardj# endif 8909090d2f691fd59c3a67c55e74f3c66c9c5671b01rhyskidd# if DARWIN_VERS >= DARWIN_10_10 891a95abead5600e5b0e7a430d4d373aad7e267e35csewardj MEMCHR(VG_Z_DYLD, memchr) 892312bcb109bfb6899086dda47b02a5436f26516d4sewardj /* _platform_memchr$VARIANT$Generic */ 893312bcb109bfb6899086dda47b02a5436f26516d4sewardj MEMCHR(libsystemZuplatformZddylib, _platform_memchr$VARIANT$Generic) 894312bcb109bfb6899086dda47b02a5436f26516d4sewardj# endif 8959c7779b64eacf264ee427b97ae0df8596b1960ccbart 8968eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 8978eb8bab992e3998c33770b0cdb16059a8b918a06sewardj MEMCHR(VG_Z_LIBC_SONAME, memchr) 8988eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 8999c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 9009c7779b64eacf264ee427b97ae0df8596b1960ccbart 9019c7779b64eacf264ee427b97ae0df8596b1960ccbart 9029c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- memrchr ----------------------*/ 9039c7779b64eacf264ee427b97ae0df8596b1960ccbart 9049c7779b64eacf264ee427b97ae0df8596b1960ccbart#define MEMRCHR(soname, fnname) \ 9059c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZU(20360,soname,fnname) \ 9069c7779b64eacf264ee427b97ae0df8596b1960ccbart (const void *s, int c, SizeT n); \ 9079c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZU(20360,soname,fnname) \ 9089c7779b64eacf264ee427b97ae0df8596b1960ccbart (const void *s, int c, SizeT n) \ 9099c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 9109c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT i; \ 9119c7779b64eacf264ee427b97ae0df8596b1960ccbart UChar c0 = (UChar)c; \ 91270a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian const UChar* p = s; \ 9139c7779b64eacf264ee427b97ae0df8596b1960ccbart for (i = 0; i < n; i++) \ 91470a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian if (p[n-1-i] == c0) return CONST_CAST(void *,&p[n-1-i]); \ 9159c7779b64eacf264ee427b97ae0df8596b1960ccbart return NULL; \ 9169c7779b64eacf264ee427b97ae0df8596b1960ccbart } 9179c7779b64eacf264ee427b97ae0df8596b1960ccbart 9189c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 9199c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMRCHR(VG_Z_LIBC_SONAME, memrchr) 9209c7779b64eacf264ee427b97ae0df8596b1960ccbart 9219c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 9229c7779b64eacf264ee427b97ae0df8596b1960ccbart //MEMRCHR(VG_Z_LIBC_SONAME, memrchr) 9239c7779b64eacf264ee427b97ae0df8596b1960ccbart //MEMRCHR(VG_Z_DYLD, memrchr) 9249c7779b64eacf264ee427b97ae0df8596b1960ccbart 9258eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 9268eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 9279c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 9289c7779b64eacf264ee427b97ae0df8596b1960ccbart 9299c7779b64eacf264ee427b97ae0df8596b1960ccbart 9309c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- memcpy ----------------------*/ 9319c7779b64eacf264ee427b97ae0df8596b1960ccbart 9329c7779b64eacf264ee427b97ae0df8596b1960ccbart#define MEMMOVE_OR_MEMCPY(becTag, soname, fnname, do_ol_check) \ 9339c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZZ(becTag,soname,fnname) \ 9349c7779b64eacf264ee427b97ae0df8596b1960ccbart ( void *dst, const void *src, SizeT len ); \ 9359c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZZ(becTag,soname,fnname) \ 9369c7779b64eacf264ee427b97ae0df8596b1960ccbart ( void *dst, const void *src, SizeT len ) \ 9379c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 9389c7779b64eacf264ee427b97ae0df8596b1960ccbart if (do_ol_check && is_overlap(dst, src, len, len)) \ 9399c7779b64eacf264ee427b97ae0df8596b1960ccbart RECORD_OVERLAP_ERROR("memcpy", dst, src, len); \ 9409c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 9419c7779b64eacf264ee427b97ae0df8596b1960ccbart const Addr WS = sizeof(UWord); /* 8 or 4 */ \ 9429c7779b64eacf264ee427b97ae0df8596b1960ccbart const Addr WM = WS - 1; /* 7 or 3 */ \ 9439c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 9449c7779b64eacf264ee427b97ae0df8596b1960ccbart if (len > 0) { \ 9459c7779b64eacf264ee427b97ae0df8596b1960ccbart if (dst < src || !is_overlap(dst, src, len, len)) { \ 9469c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 9479c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Copying backwards. */ \ 9489c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT n = len; \ 9499c7779b64eacf264ee427b97ae0df8596b1960ccbart Addr d = (Addr)dst; \ 9509c7779b64eacf264ee427b97ae0df8596b1960ccbart Addr s = (Addr)src; \ 9519c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 9529c7779b64eacf264ee427b97ae0df8596b1960ccbart if (((s^d) & WM) == 0) { \ 9539c7779b64eacf264ee427b97ae0df8596b1960ccbart /* s and d have same UWord alignment. */ \ 9549c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Pull up to a UWord boundary. */ \ 9559c7779b64eacf264ee427b97ae0df8596b1960ccbart while ((s & WM) != 0 && n >= 1) \ 9569c7779b64eacf264ee427b97ae0df8596b1960ccbart { *(UChar*)d = *(UChar*)s; s += 1; d += 1; n -= 1; } \ 9579c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Copy UWords. */ \ 9589c7779b64eacf264ee427b97ae0df8596b1960ccbart while (n >= WS) \ 9599c7779b64eacf264ee427b97ae0df8596b1960ccbart { *(UWord*)d = *(UWord*)s; s += WS; d += WS; n -= WS; } \ 9609c7779b64eacf264ee427b97ae0df8596b1960ccbart if (n == 0) \ 9619c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst; \ 9629c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 9639c7779b64eacf264ee427b97ae0df8596b1960ccbart if (((s|d) & 1) == 0) { \ 9649c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Both are 16-aligned; copy what we can thusly. */ \ 9659c7779b64eacf264ee427b97ae0df8596b1960ccbart while (n >= 2) \ 9669c7779b64eacf264ee427b97ae0df8596b1960ccbart { *(UShort*)d = *(UShort*)s; s += 2; d += 2; n -= 2; } \ 9679c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 9689c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Copy leftovers, or everything if misaligned. */ \ 9699c7779b64eacf264ee427b97ae0df8596b1960ccbart while (n >= 1) \ 9709c7779b64eacf264ee427b97ae0df8596b1960ccbart { *(UChar*)d = *(UChar*)s; s += 1; d += 1; n -= 1; } \ 9719c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 9729c7779b64eacf264ee427b97ae0df8596b1960ccbart } else if (dst > src) { \ 9739c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 9749c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT n = len; \ 9759c7779b64eacf264ee427b97ae0df8596b1960ccbart Addr d = ((Addr)dst) + n; \ 9769c7779b64eacf264ee427b97ae0df8596b1960ccbart Addr s = ((Addr)src) + n; \ 9779c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 9789c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Copying forwards. */ \ 9799c7779b64eacf264ee427b97ae0df8596b1960ccbart if (((s^d) & WM) == 0) { \ 9809c7779b64eacf264ee427b97ae0df8596b1960ccbart /* s and d have same UWord alignment. */ \ 9819c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Back down to a UWord boundary. */ \ 9829c7779b64eacf264ee427b97ae0df8596b1960ccbart while ((s & WM) != 0 && n >= 1) \ 9839c7779b64eacf264ee427b97ae0df8596b1960ccbart { s -= 1; d -= 1; *(UChar*)d = *(UChar*)s; n -= 1; } \ 9849c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Copy UWords. */ \ 9859c7779b64eacf264ee427b97ae0df8596b1960ccbart while (n >= WS) \ 9869c7779b64eacf264ee427b97ae0df8596b1960ccbart { s -= WS; d -= WS; *(UWord*)d = *(UWord*)s; n -= WS; } \ 9879c7779b64eacf264ee427b97ae0df8596b1960ccbart if (n == 0) \ 9889c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst; \ 9899c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 9909c7779b64eacf264ee427b97ae0df8596b1960ccbart if (((s|d) & 1) == 0) { \ 9919c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Both are 16-aligned; copy what we can thusly. */ \ 9929c7779b64eacf264ee427b97ae0df8596b1960ccbart while (n >= 2) \ 9939c7779b64eacf264ee427b97ae0df8596b1960ccbart { s -= 2; d -= 2; *(UShort*)d = *(UShort*)s; n -= 2; } \ 9949c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 9959c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Copy leftovers, or everything if misaligned. */ \ 9969c7779b64eacf264ee427b97ae0df8596b1960ccbart while (n >= 1) \ 9979c7779b64eacf264ee427b97ae0df8596b1960ccbart { s -= 1; d -= 1; *(UChar*)d = *(UChar*)s; n -= 1; } \ 9989c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 9999c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 10009c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 10019c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 10029c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst; \ 10039c7779b64eacf264ee427b97ae0df8596b1960ccbart } 10049c7779b64eacf264ee427b97ae0df8596b1960ccbart 10059c7779b64eacf264ee427b97ae0df8596b1960ccbart#define MEMMOVE(soname, fnname) \ 10069c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMMOVE_OR_MEMCPY(20181, soname, fnname, 0) 10079c7779b64eacf264ee427b97ae0df8596b1960ccbart 10089c7779b64eacf264ee427b97ae0df8596b1960ccbart#define MEMCPY(soname, fnname) \ 10099c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMMOVE_OR_MEMCPY(20180, soname, fnname, 1) 10109c7779b64eacf264ee427b97ae0df8596b1960ccbart 10119c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 10129c7779b64eacf264ee427b97ae0df8596b1960ccbart /* For older memcpy we have to use memmove-like semantics and skip 10139c7779b64eacf264ee427b97ae0df8596b1960ccbart the overlap check; sigh; see #275284. */ 10149c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMMOVE(VG_Z_LIBC_SONAME, memcpyZAGLIBCZu2Zd2Zd5) /* memcpy@GLIBC_2.2.5 */ 10159c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCPY(VG_Z_LIBC_SONAME, memcpyZAZAGLIBCZu2Zd14) /* memcpy@@GLIBC_2.14 */ 10169c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCPY(VG_Z_LIBC_SONAME, memcpy) /* fallback case */ 10179c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCPY(VG_Z_LIBC_SONAME, __GI_memcpy) 10189c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCPY(VG_Z_LIBC_SONAME, __memcpy_sse2) 10199c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCPY(VG_Z_LD_SO_1, memcpy) /* ld.so.1 */ 10209c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCPY(VG_Z_LD64_SO_1, memcpy) /* ld64.so.1 */ 10219c7779b64eacf264ee427b97ae0df8596b1960ccbart /* icc9 blats these around all over the place. Not only in the main 10229c7779b64eacf264ee427b97ae0df8596b1960ccbart executable but various .so's. They are highly tuned and read 10239c7779b64eacf264ee427b97ae0df8596b1960ccbart memory beyond the source boundary (although work correctly and 10249c7779b64eacf264ee427b97ae0df8596b1960ccbart never go across page boundaries), so give errors when run 10259c7779b64eacf264ee427b97ae0df8596b1960ccbart natively, at least for misaligned source arg. Just intercepting 10269c7779b64eacf264ee427b97ae0df8596b1960ccbart in the exe only until we understand more about the problem. See 10279c7779b64eacf264ee427b97ae0df8596b1960ccbart http://bugs.kde.org/show_bug.cgi?id=139776 10289c7779b64eacf264ee427b97ae0df8596b1960ccbart */ 10299c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCPY(NONE, ZuintelZufastZumemcpy) 10309c7779b64eacf264ee427b97ae0df8596b1960ccbart 10319c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 10329c7779b64eacf264ee427b97ae0df8596b1960ccbart# if DARWIN_VERS <= DARWIN_10_6 10339c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCPY(VG_Z_LIBC_SONAME, memcpy) 10349c7779b64eacf264ee427b97ae0df8596b1960ccbart# endif 10359c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCPY(VG_Z_LIBC_SONAME, memcpyZDVARIANTZDsse3x) /* memcpy$VARIANT$sse3x */ 10369c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCPY(VG_Z_LIBC_SONAME, memcpyZDVARIANTZDsse42) /* memcpy$VARIANT$sse42 */ 10379c7779b64eacf264ee427b97ae0df8596b1960ccbart 10388eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 10398eb8bab992e3998c33770b0cdb16059a8b918a06sewardj MEMCPY(VG_Z_LIBC_SONAME, memcpy) 10408eb8bab992e3998c33770b0cdb16059a8b918a06sewardj MEMCPY(VG_Z_LD_SO_1, memcpy) 10418eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 10429c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 10439c7779b64eacf264ee427b97ae0df8596b1960ccbart 10449c7779b64eacf264ee427b97ae0df8596b1960ccbart 10459c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- memcmp ----------------------*/ 10469c7779b64eacf264ee427b97ae0df8596b1960ccbart 10479c7779b64eacf264ee427b97ae0df8596b1960ccbart#define MEMCMP(soname, fnname) \ 10489c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20190,soname,fnname) \ 10499c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const void *s1V, const void *s2V, SizeT n ); \ 10509c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20190,soname,fnname) \ 10519c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const void *s1V, const void *s2V, SizeT n ) \ 10529c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 1053094b991ef067868dcaa5076d12d851e24eb33bbasewardj const SizeT WS = sizeof(UWord); /* 8 or 4 */ \ 1054094b991ef067868dcaa5076d12d851e24eb33bbasewardj const SizeT WM = WS - 1; /* 7 or 3 */ \ 105511e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj Addr s1A = (Addr)s1V; \ 105611e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj Addr s2A = (Addr)s2V; \ 105711e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj \ 105811e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj if (((s1A | s2A) & WM) == 0) { \ 105911e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj /* Both areas are word aligned. Skip over the */ \ 106011e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj /* equal prefix as fast as possible. */ \ 106111e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj while (n >= WS) { \ 106211e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj UWord w1 = *(UWord*)s1A; \ 106311e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj UWord w2 = *(UWord*)s2A; \ 106411e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj if (w1 != w2) break; \ 106511e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj s1A += WS; \ 106611e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj s2A += WS; \ 106711e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj n -= WS; \ 106811e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj } \ 106911e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj } \ 107011e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj \ 107111e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj const UChar* s1 = (const UChar*) s1A; \ 107211e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj const UChar* s2 = (const UChar*) s2A; \ 10739c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 10749c7779b64eacf264ee427b97ae0df8596b1960ccbart while (n != 0) { \ 107511e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj UChar a0 = s1[0]; \ 107611e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj UChar b0 = s2[0]; \ 10779c7779b64eacf264ee427b97ae0df8596b1960ccbart s1 += 1; \ 10789c7779b64eacf264ee427b97ae0df8596b1960ccbart s2 += 1; \ 107911e20f70b6da76415ca57b8fc75a4ac8d6411e53sewardj int res = ((int)a0) - ((int)b0); \ 10809c7779b64eacf264ee427b97ae0df8596b1960ccbart if (res != 0) \ 10819c7779b64eacf264ee427b97ae0df8596b1960ccbart return res; \ 10829c7779b64eacf264ee427b97ae0df8596b1960ccbart n -= 1; \ 10839c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 10849c7779b64eacf264ee427b97ae0df8596b1960ccbart return 0; \ 10859c7779b64eacf264ee427b97ae0df8596b1960ccbart } 10869c7779b64eacf264ee427b97ae0df8596b1960ccbart 10879c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 10889c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCMP(VG_Z_LIBC_SONAME, memcmp) 10899c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCMP(VG_Z_LIBC_SONAME, __GI_memcmp) 10909c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCMP(VG_Z_LIBC_SONAME, __memcmp_sse2) 10919c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCMP(VG_Z_LIBC_SONAME, __memcmp_sse4_1) 10929c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCMP(VG_Z_LIBC_SONAME, bcmp) 10939c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMCMP(VG_Z_LD_SO_1, bcmp) 10949c7779b64eacf264ee427b97ae0df8596b1960ccbart 10959c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 10969090d2f691fd59c3a67c55e74f3c66c9c5671b01rhyskidd# if DARWIN_VERS >= DARWIN_10_9 1097aec49a463fd7c90ef190ff72318e50224e463e90sewardj MEMCMP(libsystemZuplatformZddylib, _platform_memcmp) 1098aec49a463fd7c90ef190ff72318e50224e463e90sewardj# endif 10999c7779b64eacf264ee427b97ae0df8596b1960ccbart 11008eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 11018eb8bab992e3998c33770b0cdb16059a8b918a06sewardj MEMCMP(VG_Z_LIBC_SONAME, memcmp) 11028eb8bab992e3998c33770b0cdb16059a8b918a06sewardj MEMCMP(VG_Z_LIBC_SONAME, bcmp) 11038eb8bab992e3998c33770b0cdb16059a8b918a06sewardj MEMCMP(VG_Z_LD_SO_1, memcmp) 11048eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 11059c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 11069c7779b64eacf264ee427b97ae0df8596b1960ccbart 11079c7779b64eacf264ee427b97ae0df8596b1960ccbart 11089c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- stpcpy ----------------------*/ 11099c7779b64eacf264ee427b97ae0df8596b1960ccbart 11109c7779b64eacf264ee427b97ae0df8596b1960ccbart/* Copy SRC to DEST, returning the address of the terminating '\0' in 11119c7779b64eacf264ee427b97ae0df8596b1960ccbart DEST. (minor variant of strcpy) */ 11129c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STPCPY(soname, fnname) \ 11139c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20200,soname,fnname) \ 11149c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src ); \ 11159c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20200,soname,fnname) \ 11169c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src ) \ 11179c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 11189c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* src_orig = src; \ 11199c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar* dst_orig = dst; \ 11209c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 11219c7779b64eacf264ee427b97ae0df8596b1960ccbart while (*src) *dst++ = *src++; \ 11229c7779b64eacf264ee427b97ae0df8596b1960ccbart *dst = 0; \ 11239c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 11249c7779b64eacf264ee427b97ae0df8596b1960ccbart /* This checks for overlap after copying, unavoidable without */ \ 11259c7779b64eacf264ee427b97ae0df8596b1960ccbart /* pre-counting length... should be ok */ \ 11269c7779b64eacf264ee427b97ae0df8596b1960ccbart if (is_overlap(dst_orig, \ 11279c7779b64eacf264ee427b97ae0df8596b1960ccbart src_orig, \ 11289c7779b64eacf264ee427b97ae0df8596b1960ccbart (Addr)dst-(Addr)dst_orig+1, \ 11299c7779b64eacf264ee427b97ae0df8596b1960ccbart (Addr)src-(Addr)src_orig+1)) \ 11309c7779b64eacf264ee427b97ae0df8596b1960ccbart RECORD_OVERLAP_ERROR("stpcpy", dst_orig, src_orig, 0); \ 11319c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 11329c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst; \ 11339c7779b64eacf264ee427b97ae0df8596b1960ccbart } 11349c7779b64eacf264ee427b97ae0df8596b1960ccbart 11359c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 11369c7779b64eacf264ee427b97ae0df8596b1960ccbart STPCPY(VG_Z_LIBC_SONAME, stpcpy) 11379c7779b64eacf264ee427b97ae0df8596b1960ccbart STPCPY(VG_Z_LIBC_SONAME, __GI_stpcpy) 11389c7779b64eacf264ee427b97ae0df8596b1960ccbart STPCPY(VG_Z_LIBC_SONAME, __stpcpy_sse2) 11399c7779b64eacf264ee427b97ae0df8596b1960ccbart STPCPY(VG_Z_LIBC_SONAME, __stpcpy_sse2_unaligned) 11409c7779b64eacf264ee427b97ae0df8596b1960ccbart STPCPY(VG_Z_LD_LINUX_SO_2, stpcpy) 11419c7779b64eacf264ee427b97ae0df8596b1960ccbart STPCPY(VG_Z_LD_LINUX_X86_64_SO_2, stpcpy) 11429c7779b64eacf264ee427b97ae0df8596b1960ccbart 11439c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 11449c7779b64eacf264ee427b97ae0df8596b1960ccbart //STPCPY(VG_Z_LIBC_SONAME, stpcpy) 11459c7779b64eacf264ee427b97ae0df8596b1960ccbart //STPCPY(VG_Z_DYLD, stpcpy) 11469c7779b64eacf264ee427b97ae0df8596b1960ccbart 11478eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 11488eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STPCPY(VG_Z_LIBC_SONAME, stpcpy) 11498eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 11509c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 11519c7779b64eacf264ee427b97ae0df8596b1960ccbart 11529c7779b64eacf264ee427b97ae0df8596b1960ccbart 11539c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- stpncpy ----------------------*/ 11549c7779b64eacf264ee427b97ae0df8596b1960ccbart 11559c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STPNCPY(soname, fnname) \ 11569c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20420,soname,fnname) \ 11579c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src, SizeT n ); \ 11589c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20420,soname,fnname) \ 11599c7779b64eacf264ee427b97ae0df8596b1960ccbart ( char* dst, const char* src, SizeT n ) \ 11609c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 11619c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* src_orig = src; \ 11629c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar* dst_str = dst; \ 11639c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT m = 0; \ 11649c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 11659c7779b64eacf264ee427b97ae0df8596b1960ccbart while (m < n && *src) { m++; *dst++ = *src++; } \ 11669c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Check for overlap after copying; all n bytes of dst are relevant, */ \ 11679c7779b64eacf264ee427b97ae0df8596b1960ccbart /* but only m+1 bytes of src if terminator was found */ \ 11689c7779b64eacf264ee427b97ae0df8596b1960ccbart if (is_overlap(dst_str, src_orig, n, (m < n) ? m+1 : n)) \ 11699c7779b64eacf264ee427b97ae0df8596b1960ccbart RECORD_OVERLAP_ERROR("stpncpy", dst, src, n); \ 11709c7779b64eacf264ee427b97ae0df8596b1960ccbart dst_str = dst; \ 11719c7779b64eacf264ee427b97ae0df8596b1960ccbart while (m++ < n) *dst++ = 0; /* must pad remainder with nulls */ \ 11729c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 11739c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst_str; \ 11749c7779b64eacf264ee427b97ae0df8596b1960ccbart } 11759c7779b64eacf264ee427b97ae0df8596b1960ccbart 11769c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 11779c7779b64eacf264ee427b97ae0df8596b1960ccbart STPNCPY(VG_Z_LIBC_SONAME, stpncpy) 11789c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 11799c7779b64eacf264ee427b97ae0df8596b1960ccbart 11809c7779b64eacf264ee427b97ae0df8596b1960ccbart 11819c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- memset ----------------------*/ 11829c7779b64eacf264ee427b97ae0df8596b1960ccbart 11839c7779b64eacf264ee427b97ae0df8596b1960ccbart/* Why are we bothering to intercept this? It seems entirely 11849c7779b64eacf264ee427b97ae0df8596b1960ccbart pointless. */ 11859c7779b64eacf264ee427b97ae0df8596b1960ccbart 11869c7779b64eacf264ee427b97ae0df8596b1960ccbart#define MEMSET(soname, fnname) \ 11879c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZU(20210,soname,fnname) \ 11889c7779b64eacf264ee427b97ae0df8596b1960ccbart (void *s, Int c, SizeT n); \ 11899c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZU(20210,soname,fnname) \ 11909c7779b64eacf264ee427b97ae0df8596b1960ccbart (void *s, Int c, SizeT n) \ 11919c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 11929c7779b64eacf264ee427b97ae0df8596b1960ccbart if (sizeof(void*) == 8) { \ 11939c7779b64eacf264ee427b97ae0df8596b1960ccbart Addr a = (Addr)s; \ 11949c7779b64eacf264ee427b97ae0df8596b1960ccbart ULong c8 = (c & 0xFF); \ 11959c7779b64eacf264ee427b97ae0df8596b1960ccbart c8 = (c8 << 8) | c8; \ 11969c7779b64eacf264ee427b97ae0df8596b1960ccbart c8 = (c8 << 16) | c8; \ 11979c7779b64eacf264ee427b97ae0df8596b1960ccbart c8 = (c8 << 32) | c8; \ 11989c7779b64eacf264ee427b97ae0df8596b1960ccbart while ((a & 7) != 0 && n >= 1) \ 11999c7779b64eacf264ee427b97ae0df8596b1960ccbart { *(UChar*)a = (UChar)c; a += 1; n -= 1; } \ 12009c7779b64eacf264ee427b97ae0df8596b1960ccbart while (n >= 8) \ 12019c7779b64eacf264ee427b97ae0df8596b1960ccbart { *(ULong*)a = c8; a += 8; n -= 8; } \ 12029c7779b64eacf264ee427b97ae0df8596b1960ccbart while (n >= 1) \ 12039c7779b64eacf264ee427b97ae0df8596b1960ccbart { *(UChar*)a = (UChar)c; a += 1; n -= 1; } \ 12049c7779b64eacf264ee427b97ae0df8596b1960ccbart return s; \ 12059c7779b64eacf264ee427b97ae0df8596b1960ccbart } else { \ 12069c7779b64eacf264ee427b97ae0df8596b1960ccbart Addr a = (Addr)s; \ 12079c7779b64eacf264ee427b97ae0df8596b1960ccbart UInt c4 = (c & 0xFF); \ 12089c7779b64eacf264ee427b97ae0df8596b1960ccbart c4 = (c4 << 8) | c4; \ 12099c7779b64eacf264ee427b97ae0df8596b1960ccbart c4 = (c4 << 16) | c4; \ 12109c7779b64eacf264ee427b97ae0df8596b1960ccbart while ((a & 3) != 0 && n >= 1) \ 12119c7779b64eacf264ee427b97ae0df8596b1960ccbart { *(UChar*)a = (UChar)c; a += 1; n -= 1; } \ 12129c7779b64eacf264ee427b97ae0df8596b1960ccbart while (n >= 4) \ 12139c7779b64eacf264ee427b97ae0df8596b1960ccbart { *(UInt*)a = c4; a += 4; n -= 4; } \ 12149c7779b64eacf264ee427b97ae0df8596b1960ccbart while (n >= 1) \ 12159c7779b64eacf264ee427b97ae0df8596b1960ccbart { *(UChar*)a = (UChar)c; a += 1; n -= 1; } \ 12169c7779b64eacf264ee427b97ae0df8596b1960ccbart return s; \ 12179c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 12189c7779b64eacf264ee427b97ae0df8596b1960ccbart } 12199c7779b64eacf264ee427b97ae0df8596b1960ccbart 12209c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 12219c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMSET(VG_Z_LIBC_SONAME, memset) 12229c7779b64eacf264ee427b97ae0df8596b1960ccbart 12239c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 12249c7779b64eacf264ee427b97ae0df8596b1960ccbart //MEMSET(VG_Z_LIBC_SONAME, memset) 12259c7779b64eacf264ee427b97ae0df8596b1960ccbart //MEMSET(VG_Z_DYLD, memset) 12269c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMSET(VG_Z_LIBC_SONAME, memset) 12279c7779b64eacf264ee427b97ae0df8596b1960ccbart 12288eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 12298eb8bab992e3998c33770b0cdb16059a8b918a06sewardj MEMSET(VG_Z_LIBC_SONAME, memset) 12308eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 12319c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 12329c7779b64eacf264ee427b97ae0df8596b1960ccbart 12339c7779b64eacf264ee427b97ae0df8596b1960ccbart 12349c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- memmove ----------------------*/ 12359c7779b64eacf264ee427b97ae0df8596b1960ccbart 12369c7779b64eacf264ee427b97ae0df8596b1960ccbart/* memmove -- use the MEMMOVE defn above. */ 12379c7779b64eacf264ee427b97ae0df8596b1960ccbart 12389c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 12399c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMMOVE(VG_Z_LIBC_SONAME, memmove) 12409c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMMOVE(VG_Z_LIBC_SONAME, __GI_memmove) 1241b97cf8e9a718e61a540e63001d4c9346773c630emjw /* See bug #349828 Override for ld64.so.1 like memcpy, because for some 1242b97cf8e9a718e61a540e63001d4c9346773c630emjw arches MEMCPY_OK_FOR_FORWARD_MEMMOVE is set, which might cause memmove 1243b97cf8e9a718e61a540e63001d4c9346773c630emjw to call memcpy. */ 1244b97cf8e9a718e61a540e63001d4c9346773c630emjw MEMMOVE(VG_Z_LD64_SO_1, memmove) 12459c7779b64eacf264ee427b97ae0df8596b1960ccbart 12469c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 12479c7779b64eacf264ee427b97ae0df8596b1960ccbart# if DARWIN_VERS <= DARWIN_10_6 12489c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMMOVE(VG_Z_LIBC_SONAME, memmove) 12499c7779b64eacf264ee427b97ae0df8596b1960ccbart# endif 12509c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMMOVE(VG_Z_LIBC_SONAME, memmoveZDVARIANTZDsse3x) /* memmove$VARIANT$sse3x */ 12519c7779b64eacf264ee427b97ae0df8596b1960ccbart MEMMOVE(VG_Z_LIBC_SONAME, memmoveZDVARIANTZDsse42) /* memmove$VARIANT$sse42 */ 12529090d2f691fd59c3a67c55e74f3c66c9c5671b01rhyskidd# if DARWIN_VERS >= DARWIN_10_9 1253312bcb109bfb6899086dda47b02a5436f26516d4sewardj /* _platform_memmove$VARIANT$Ivybridge */ 1254eb86ddab35602995b31767f72a2babb6a692c3f3sewardj MEMMOVE(libsystemZuplatformZddylib, ZuplatformZumemmoveZDVARIANTZDIvybridge) 1255eb86ddab35602995b31767f72a2babb6a692c3f3sewardj# endif 12568eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 12578eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 12588eb8bab992e3998c33770b0cdb16059a8b918a06sewardj MEMMOVE(VG_Z_LIBC_SONAME, memmove) 12598eb8bab992e3998c33770b0cdb16059a8b918a06sewardj MEMMOVE(VG_Z_LD_SO_1, memmove) 12608eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 12619c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 12629c7779b64eacf264ee427b97ae0df8596b1960ccbart 12639c7779b64eacf264ee427b97ae0df8596b1960ccbart 12649c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- bcopy ----------------------*/ 12659c7779b64eacf264ee427b97ae0df8596b1960ccbart 12669c7779b64eacf264ee427b97ae0df8596b1960ccbart#define BCOPY(soname, fnname) \ 12679c7779b64eacf264ee427b97ae0df8596b1960ccbart void VG_REPLACE_FUNCTION_EZU(20230,soname,fnname) \ 12689c7779b64eacf264ee427b97ae0df8596b1960ccbart (const void *srcV, void *dstV, SizeT n); \ 12699c7779b64eacf264ee427b97ae0df8596b1960ccbart void VG_REPLACE_FUNCTION_EZU(20230,soname,fnname) \ 12709c7779b64eacf264ee427b97ae0df8596b1960ccbart (const void *srcV, void *dstV, SizeT n) \ 12719c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 12729c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT i; \ 12739c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar* dst = dstV; \ 12749c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* src = srcV; \ 12759c7779b64eacf264ee427b97ae0df8596b1960ccbart if (dst < src) { \ 12769c7779b64eacf264ee427b97ae0df8596b1960ccbart for (i = 0; i < n; i++) \ 12779c7779b64eacf264ee427b97ae0df8596b1960ccbart dst[i] = src[i]; \ 12789c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 12799c7779b64eacf264ee427b97ae0df8596b1960ccbart else \ 12809c7779b64eacf264ee427b97ae0df8596b1960ccbart if (dst > src) { \ 12819c7779b64eacf264ee427b97ae0df8596b1960ccbart for (i = 0; i < n; i++) \ 12829c7779b64eacf264ee427b97ae0df8596b1960ccbart dst[n-i-1] = src[n-i-1]; \ 12839c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 12849c7779b64eacf264ee427b97ae0df8596b1960ccbart } 12859c7779b64eacf264ee427b97ae0df8596b1960ccbart 12869c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 12879c7779b64eacf264ee427b97ae0df8596b1960ccbart BCOPY(VG_Z_LIBC_SONAME, bcopy) 12889c7779b64eacf264ee427b97ae0df8596b1960ccbart 12899c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 12909c7779b64eacf264ee427b97ae0df8596b1960ccbart //BCOPY(VG_Z_LIBC_SONAME, bcopy) 12919c7779b64eacf264ee427b97ae0df8596b1960ccbart //BCOPY(VG_Z_DYLD, bcopy) 12929c7779b64eacf264ee427b97ae0df8596b1960ccbart 12938eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_darwin) 12948eb8bab992e3998c33770b0cdb16059a8b918a06sewardj BCOPY(VG_Z_LIBC_SONAME, bcopy) 12958eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 12969c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 12979c7779b64eacf264ee427b97ae0df8596b1960ccbart 12989c7779b64eacf264ee427b97ae0df8596b1960ccbart 12999c7779b64eacf264ee427b97ae0df8596b1960ccbart/*-------------------- memmove_chk --------------------*/ 13009c7779b64eacf264ee427b97ae0df8596b1960ccbart 13019c7779b64eacf264ee427b97ae0df8596b1960ccbart/* glibc 2.5 variant of memmove which checks the dest is big enough. 13029c7779b64eacf264ee427b97ae0df8596b1960ccbart There is no specific part of glibc that this is copied from. */ 13039c7779b64eacf264ee427b97ae0df8596b1960ccbart#define GLIBC25___MEMMOVE_CHK(soname, fnname) \ 13049c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZU(20240,soname,fnname) \ 13059c7779b64eacf264ee427b97ae0df8596b1960ccbart (void *dstV, const void *srcV, SizeT n, SizeT destlen); \ 13069c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZU(20240,soname,fnname) \ 13079c7779b64eacf264ee427b97ae0df8596b1960ccbart (void *dstV, const void *srcV, SizeT n, SizeT destlen) \ 13089c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 13099c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT i; \ 13109c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar* dst = dstV; \ 13119c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* src = srcV; \ 13129c7779b64eacf264ee427b97ae0df8596b1960ccbart if (destlen < n) \ 13139c7779b64eacf264ee427b97ae0df8596b1960ccbart goto badness; \ 13149c7779b64eacf264ee427b97ae0df8596b1960ccbart if (dst < src) { \ 13159c7779b64eacf264ee427b97ae0df8596b1960ccbart for (i = 0; i < n; i++) \ 13169c7779b64eacf264ee427b97ae0df8596b1960ccbart dst[i] = src[i]; \ 13179c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 13189c7779b64eacf264ee427b97ae0df8596b1960ccbart else \ 13199c7779b64eacf264ee427b97ae0df8596b1960ccbart if (dst > src) { \ 13209c7779b64eacf264ee427b97ae0df8596b1960ccbart for (i = 0; i < n; i++) \ 13219c7779b64eacf264ee427b97ae0df8596b1960ccbart dst[n-i-1] = src[n-i-1]; \ 13229c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 13239c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst; \ 13249c7779b64eacf264ee427b97ae0df8596b1960ccbart badness: \ 13259c7779b64eacf264ee427b97ae0df8596b1960ccbart VALGRIND_PRINTF_BACKTRACE( \ 13269c7779b64eacf264ee427b97ae0df8596b1960ccbart "*** memmove_chk: buffer overflow detected ***: " \ 13279c7779b64eacf264ee427b97ae0df8596b1960ccbart "program terminated\n"); \ 13289c7779b64eacf264ee427b97ae0df8596b1960ccbart my_exit(127); \ 13299c7779b64eacf264ee427b97ae0df8596b1960ccbart /*NOTREACHED*/ \ 13309c7779b64eacf264ee427b97ae0df8596b1960ccbart return NULL; \ 13319c7779b64eacf264ee427b97ae0df8596b1960ccbart } 13329c7779b64eacf264ee427b97ae0df8596b1960ccbart 13339c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 13349c7779b64eacf264ee427b97ae0df8596b1960ccbart GLIBC25___MEMMOVE_CHK(VG_Z_LIBC_SONAME, __memmove_chk) 13359c7779b64eacf264ee427b97ae0df8596b1960ccbart 13369c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 13379c7779b64eacf264ee427b97ae0df8596b1960ccbart 13388eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 13398eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 13409c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 13419c7779b64eacf264ee427b97ae0df8596b1960ccbart 13429c7779b64eacf264ee427b97ae0df8596b1960ccbart 13439c7779b64eacf264ee427b97ae0df8596b1960ccbart/*-------------------- strchrnul --------------------*/ 13449c7779b64eacf264ee427b97ae0df8596b1960ccbart 13459c7779b64eacf264ee427b97ae0df8596b1960ccbart/* Find the first occurrence of C in S or the final NUL byte. */ 13469c7779b64eacf264ee427b97ae0df8596b1960ccbart#define GLIBC232_STRCHRNUL(soname, fnname) \ 13479c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20250,soname,fnname) \ 13489c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* s, int c_in); \ 13499c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20250,soname,fnname) \ 13509c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* s, int c_in) \ 13519c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 135270a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian HChar c = (HChar) c_in; \ 135370a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian const HChar* char_ptr = s; \ 13549c7779b64eacf264ee427b97ae0df8596b1960ccbart while (1) { \ 135570a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian if (*char_ptr == 0) return CONST_CAST(HChar *,char_ptr); \ 135670a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian if (*char_ptr == c) return CONST_CAST(HChar *,char_ptr); \ 13579c7779b64eacf264ee427b97ae0df8596b1960ccbart char_ptr++; \ 13589c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 13599c7779b64eacf264ee427b97ae0df8596b1960ccbart } 13609c7779b64eacf264ee427b97ae0df8596b1960ccbart 13619c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 13629c7779b64eacf264ee427b97ae0df8596b1960ccbart GLIBC232_STRCHRNUL(VG_Z_LIBC_SONAME, strchrnul) 13639c7779b64eacf264ee427b97ae0df8596b1960ccbart 13649c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 13659c7779b64eacf264ee427b97ae0df8596b1960ccbart 13668eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 13678eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 13689c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 13699c7779b64eacf264ee427b97ae0df8596b1960ccbart 13709c7779b64eacf264ee427b97ae0df8596b1960ccbart 13719c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- rawmemchr ----------------------*/ 13729c7779b64eacf264ee427b97ae0df8596b1960ccbart 13739c7779b64eacf264ee427b97ae0df8596b1960ccbart/* Find the first occurrence of C in S. */ 13749c7779b64eacf264ee427b97ae0df8596b1960ccbart#define GLIBC232_RAWMEMCHR(soname, fnname) \ 13751ef205bfce335a8d54b6b188e83254b92c52d7adflorian void* VG_REPLACE_FUNCTION_EZU(20260,soname,fnname) \ 13761ef205bfce335a8d54b6b188e83254b92c52d7adflorian (const void* s, int c_in); \ 13771ef205bfce335a8d54b6b188e83254b92c52d7adflorian void* VG_REPLACE_FUNCTION_EZU(20260,soname,fnname) \ 13781ef205bfce335a8d54b6b188e83254b92c52d7adflorian (const void* s, int c_in) \ 13799c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 13801ef205bfce335a8d54b6b188e83254b92c52d7adflorian UChar c = (UChar) c_in; \ 13811ef205bfce335a8d54b6b188e83254b92c52d7adflorian const UChar* char_ptr = s; \ 13829c7779b64eacf264ee427b97ae0df8596b1960ccbart while (1) { \ 138370a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian if (*char_ptr == c) return CONST_CAST(void *,char_ptr); \ 13849c7779b64eacf264ee427b97ae0df8596b1960ccbart char_ptr++; \ 13859c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 13869c7779b64eacf264ee427b97ae0df8596b1960ccbart } 13879c7779b64eacf264ee427b97ae0df8596b1960ccbart 13889c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined (VGO_linux) 13899c7779b64eacf264ee427b97ae0df8596b1960ccbart GLIBC232_RAWMEMCHR(VG_Z_LIBC_SONAME, rawmemchr) 13909c7779b64eacf264ee427b97ae0df8596b1960ccbart GLIBC232_RAWMEMCHR(VG_Z_LIBC_SONAME, __GI___rawmemchr) 13919c7779b64eacf264ee427b97ae0df8596b1960ccbart 13929c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 13939c7779b64eacf264ee427b97ae0df8596b1960ccbart 13948eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 13958eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 13969c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 13979c7779b64eacf264ee427b97ae0df8596b1960ccbart 13989c7779b64eacf264ee427b97ae0df8596b1960ccbart 13999c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strcpy_chk ----------------------*/ 14009c7779b64eacf264ee427b97ae0df8596b1960ccbart 14019c7779b64eacf264ee427b97ae0df8596b1960ccbart/* glibc variant of strcpy that checks the dest is big enough. 14029c7779b64eacf264ee427b97ae0df8596b1960ccbart Copied from glibc-2.5/debug/test-strcpy_chk.c. */ 14039c7779b64eacf264ee427b97ae0df8596b1960ccbart#define GLIBC25___STRCPY_CHK(soname,fnname) \ 14049c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20270,soname,fnname) \ 14059c7779b64eacf264ee427b97ae0df8596b1960ccbart (char* dst, const char* src, SizeT len); \ 14069c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20270,soname,fnname) \ 14079c7779b64eacf264ee427b97ae0df8596b1960ccbart (char* dst, const char* src, SizeT len) \ 14089c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 14099c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar* ret = dst; \ 14109c7779b64eacf264ee427b97ae0df8596b1960ccbart if (! len) \ 14119c7779b64eacf264ee427b97ae0df8596b1960ccbart goto badness; \ 14129c7779b64eacf264ee427b97ae0df8596b1960ccbart while ((*dst++ = *src++) != '\0') \ 14139c7779b64eacf264ee427b97ae0df8596b1960ccbart if (--len == 0) \ 14149c7779b64eacf264ee427b97ae0df8596b1960ccbart goto badness; \ 14159c7779b64eacf264ee427b97ae0df8596b1960ccbart return ret; \ 14169c7779b64eacf264ee427b97ae0df8596b1960ccbart badness: \ 14179c7779b64eacf264ee427b97ae0df8596b1960ccbart VALGRIND_PRINTF_BACKTRACE( \ 14189c7779b64eacf264ee427b97ae0df8596b1960ccbart "*** strcpy_chk: buffer overflow detected ***: " \ 14199c7779b64eacf264ee427b97ae0df8596b1960ccbart "program terminated\n"); \ 14209c7779b64eacf264ee427b97ae0df8596b1960ccbart my_exit(127); \ 14219c7779b64eacf264ee427b97ae0df8596b1960ccbart /*NOTREACHED*/ \ 14229c7779b64eacf264ee427b97ae0df8596b1960ccbart return NULL; \ 14239c7779b64eacf264ee427b97ae0df8596b1960ccbart } 14249c7779b64eacf264ee427b97ae0df8596b1960ccbart 14259c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 14269c7779b64eacf264ee427b97ae0df8596b1960ccbart GLIBC25___STRCPY_CHK(VG_Z_LIBC_SONAME, __strcpy_chk) 14279c7779b64eacf264ee427b97ae0df8596b1960ccbart 14289c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 14299c7779b64eacf264ee427b97ae0df8596b1960ccbart 14308eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 14318eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 14329c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 14339c7779b64eacf264ee427b97ae0df8596b1960ccbart 14349c7779b64eacf264ee427b97ae0df8596b1960ccbart 14359c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- stpcpy_chk ----------------------*/ 14369c7779b64eacf264ee427b97ae0df8596b1960ccbart 14379c7779b64eacf264ee427b97ae0df8596b1960ccbart/* glibc variant of stpcpy that checks the dest is big enough. 14389c7779b64eacf264ee427b97ae0df8596b1960ccbart Copied from glibc-2.5/debug/test-stpcpy_chk.c. */ 14399c7779b64eacf264ee427b97ae0df8596b1960ccbart#define GLIBC25___STPCPY_CHK(soname,fnname) \ 14409c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20280,soname,fnname) \ 14419c7779b64eacf264ee427b97ae0df8596b1960ccbart (char* dst, const char* src, SizeT len); \ 14429c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20280,soname,fnname) \ 14439c7779b64eacf264ee427b97ae0df8596b1960ccbart (char* dst, const char* src, SizeT len) \ 14449c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 14459c7779b64eacf264ee427b97ae0df8596b1960ccbart if (! len) \ 14469c7779b64eacf264ee427b97ae0df8596b1960ccbart goto badness; \ 14479c7779b64eacf264ee427b97ae0df8596b1960ccbart while ((*dst++ = *src++) != '\0') \ 14489c7779b64eacf264ee427b97ae0df8596b1960ccbart if (--len == 0) \ 14499c7779b64eacf264ee427b97ae0df8596b1960ccbart goto badness; \ 14509c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst - 1; \ 14519c7779b64eacf264ee427b97ae0df8596b1960ccbart badness: \ 14529c7779b64eacf264ee427b97ae0df8596b1960ccbart VALGRIND_PRINTF_BACKTRACE( \ 14539c7779b64eacf264ee427b97ae0df8596b1960ccbart "*** stpcpy_chk: buffer overflow detected ***: " \ 14549c7779b64eacf264ee427b97ae0df8596b1960ccbart "program terminated\n"); \ 14559c7779b64eacf264ee427b97ae0df8596b1960ccbart my_exit(127); \ 14569c7779b64eacf264ee427b97ae0df8596b1960ccbart /*NOTREACHED*/ \ 14579c7779b64eacf264ee427b97ae0df8596b1960ccbart return NULL; \ 14589c7779b64eacf264ee427b97ae0df8596b1960ccbart } 14599c7779b64eacf264ee427b97ae0df8596b1960ccbart 14609c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 14619c7779b64eacf264ee427b97ae0df8596b1960ccbart GLIBC25___STPCPY_CHK(VG_Z_LIBC_SONAME, __stpcpy_chk) 14629c7779b64eacf264ee427b97ae0df8596b1960ccbart 14639c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 14649c7779b64eacf264ee427b97ae0df8596b1960ccbart 14658eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 14668eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 14679c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 14689c7779b64eacf264ee427b97ae0df8596b1960ccbart 14699c7779b64eacf264ee427b97ae0df8596b1960ccbart 14709c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- mempcpy ----------------------*/ 14719c7779b64eacf264ee427b97ae0df8596b1960ccbart 14729c7779b64eacf264ee427b97ae0df8596b1960ccbart/* mempcpy */ 14739c7779b64eacf264ee427b97ae0df8596b1960ccbart#define GLIBC25_MEMPCPY(soname, fnname) \ 14749c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZU(20290,soname,fnname) \ 14759c7779b64eacf264ee427b97ae0df8596b1960ccbart ( void *dst, const void *src, SizeT len ); \ 14769c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZU(20290,soname,fnname) \ 14779c7779b64eacf264ee427b97ae0df8596b1960ccbart ( void *dst, const void *src, SizeT len ) \ 14789c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 14799c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT len_saved = len; \ 14809c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 14819c7779b64eacf264ee427b97ae0df8596b1960ccbart if (len == 0) \ 14829c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst; \ 14839c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 14849c7779b64eacf264ee427b97ae0df8596b1960ccbart if (is_overlap(dst, src, len, len)) \ 14859c7779b64eacf264ee427b97ae0df8596b1960ccbart RECORD_OVERLAP_ERROR("mempcpy", dst, src, len); \ 14869c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 14879c7779b64eacf264ee427b97ae0df8596b1960ccbart if ( dst > src ) { \ 148809041e493017aee3d5c52fb2e1dc6db064518e5cflorian register HChar *d = (char *)dst + len - 1; \ 148909041e493017aee3d5c52fb2e1dc6db064518e5cflorian register const HChar *s = (const char *)src + len - 1; \ 14909c7779b64eacf264ee427b97ae0df8596b1960ccbart while ( len-- ) { \ 14919c7779b64eacf264ee427b97ae0df8596b1960ccbart *d-- = *s--; \ 14929c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 14939c7779b64eacf264ee427b97ae0df8596b1960ccbart } else if ( dst < src ) { \ 149409041e493017aee3d5c52fb2e1dc6db064518e5cflorian register HChar *d = dst; \ 149509041e493017aee3d5c52fb2e1dc6db064518e5cflorian register const HChar *s = src; \ 14969c7779b64eacf264ee427b97ae0df8596b1960ccbart while ( len-- ) { \ 14979c7779b64eacf264ee427b97ae0df8596b1960ccbart *d++ = *s++; \ 14989c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 14999c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 15009c7779b64eacf264ee427b97ae0df8596b1960ccbart return (void*)( ((char*)dst) + len_saved ); \ 15019c7779b64eacf264ee427b97ae0df8596b1960ccbart } 15029c7779b64eacf264ee427b97ae0df8596b1960ccbart 15039c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 15049c7779b64eacf264ee427b97ae0df8596b1960ccbart GLIBC25_MEMPCPY(VG_Z_LIBC_SONAME, mempcpy) 1505a9176d9640606a083a6e9b97515b15f631de5059mjw GLIBC25_MEMPCPY(VG_Z_LIBC_SONAME, __GI_mempcpy) 15069c7779b64eacf264ee427b97ae0df8596b1960ccbart GLIBC25_MEMPCPY(VG_Z_LD_SO_1, mempcpy) /* ld.so.1 */ 1507f2d866396dd99ebc9247221282916be9efd4fb4abart GLIBC25_MEMPCPY(VG_Z_LD_LINUX_SO_3, mempcpy) /* ld-linux.so.3 */ 1508f2d866396dd99ebc9247221282916be9efd4fb4abart GLIBC25_MEMPCPY(VG_Z_LD_LINUX_X86_64_SO_2, mempcpy) /* ld-linux-x86-64.so.2 */ 15099c7779b64eacf264ee427b97ae0df8596b1960ccbart 15109c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 15119c7779b64eacf264ee427b97ae0df8596b1960ccbart //GLIBC25_MEMPCPY(VG_Z_LIBC_SONAME, mempcpy) 15129c7779b64eacf264ee427b97ae0df8596b1960ccbart 15138eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 15148eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 15159c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 15169c7779b64eacf264ee427b97ae0df8596b1960ccbart 15179c7779b64eacf264ee427b97ae0df8596b1960ccbart 15189c7779b64eacf264ee427b97ae0df8596b1960ccbart/*-------------------- memcpy_chk --------------------*/ 15199c7779b64eacf264ee427b97ae0df8596b1960ccbart 15209c7779b64eacf264ee427b97ae0df8596b1960ccbart#define GLIBC26___MEMCPY_CHK(soname, fnname) \ 15219c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZU(20300,soname,fnname) \ 15229c7779b64eacf264ee427b97ae0df8596b1960ccbart (void* dst, const void* src, SizeT len, SizeT dstlen ); \ 15239c7779b64eacf264ee427b97ae0df8596b1960ccbart void* VG_REPLACE_FUNCTION_EZU(20300,soname,fnname) \ 15249c7779b64eacf264ee427b97ae0df8596b1960ccbart (void* dst, const void* src, SizeT len, SizeT dstlen ) \ 15259c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 15269c7779b64eacf264ee427b97ae0df8596b1960ccbart register HChar *d; \ 15279c7779b64eacf264ee427b97ae0df8596b1960ccbart register const HChar *s; \ 15289c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 15299c7779b64eacf264ee427b97ae0df8596b1960ccbart if (dstlen < len) goto badness; \ 15309c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 15319c7779b64eacf264ee427b97ae0df8596b1960ccbart if (len == 0) \ 15329c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst; \ 15339c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 15349c7779b64eacf264ee427b97ae0df8596b1960ccbart if (is_overlap(dst, src, len, len)) \ 15359c7779b64eacf264ee427b97ae0df8596b1960ccbart RECORD_OVERLAP_ERROR("memcpy_chk", dst, src, len); \ 15369c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 15379c7779b64eacf264ee427b97ae0df8596b1960ccbart if ( dst > src ) { \ 15389c7779b64eacf264ee427b97ae0df8596b1960ccbart d = (HChar *)dst + len - 1; \ 15399c7779b64eacf264ee427b97ae0df8596b1960ccbart s = (const HChar *)src + len - 1; \ 15409c7779b64eacf264ee427b97ae0df8596b1960ccbart while ( len-- ) { \ 15419c7779b64eacf264ee427b97ae0df8596b1960ccbart *d-- = *s--; \ 15429c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 15439c7779b64eacf264ee427b97ae0df8596b1960ccbart } else if ( dst < src ) { \ 15449c7779b64eacf264ee427b97ae0df8596b1960ccbart d = (HChar *)dst; \ 15459c7779b64eacf264ee427b97ae0df8596b1960ccbart s = (const HChar *)src; \ 15469c7779b64eacf264ee427b97ae0df8596b1960ccbart while ( len-- ) { \ 15479c7779b64eacf264ee427b97ae0df8596b1960ccbart *d++ = *s++; \ 15489c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 15499c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 15509c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst; \ 15519c7779b64eacf264ee427b97ae0df8596b1960ccbart badness: \ 15529c7779b64eacf264ee427b97ae0df8596b1960ccbart VALGRIND_PRINTF_BACKTRACE( \ 15539c7779b64eacf264ee427b97ae0df8596b1960ccbart "*** memcpy_chk: buffer overflow detected ***: " \ 15549c7779b64eacf264ee427b97ae0df8596b1960ccbart "program terminated\n"); \ 15559c7779b64eacf264ee427b97ae0df8596b1960ccbart my_exit(127); \ 15569c7779b64eacf264ee427b97ae0df8596b1960ccbart /*NOTREACHED*/ \ 15579c7779b64eacf264ee427b97ae0df8596b1960ccbart return NULL; \ 15589c7779b64eacf264ee427b97ae0df8596b1960ccbart } 15599c7779b64eacf264ee427b97ae0df8596b1960ccbart 15609c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 15619c7779b64eacf264ee427b97ae0df8596b1960ccbart GLIBC26___MEMCPY_CHK(VG_Z_LIBC_SONAME, __memcpy_chk) 15629c7779b64eacf264ee427b97ae0df8596b1960ccbart 15639c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 15649c7779b64eacf264ee427b97ae0df8596b1960ccbart 15658eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 15668eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 15679c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 15689c7779b64eacf264ee427b97ae0df8596b1960ccbart 15699c7779b64eacf264ee427b97ae0df8596b1960ccbart 15709c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strstr ----------------------*/ 15719c7779b64eacf264ee427b97ae0df8596b1960ccbart 15729c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRSTR(soname, fnname) \ 15739c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20310,soname,fnname) \ 15749c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* haystack, const char* needle); \ 15759c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20310,soname,fnname) \ 15769c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* haystack, const char* needle) \ 15779c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 15789c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* h = haystack; \ 15799c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* n = needle; \ 15809c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 15819c7779b64eacf264ee427b97ae0df8596b1960ccbart /* find the length of n, not including terminating zero */ \ 15829c7779b64eacf264ee427b97ae0df8596b1960ccbart UWord nlen = 0; \ 15839c7779b64eacf264ee427b97ae0df8596b1960ccbart while (n[nlen]) nlen++; \ 15849c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 15859c7779b64eacf264ee427b97ae0df8596b1960ccbart /* if n is the empty string, match immediately. */ \ 158670a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian if (nlen == 0) return CONST_CAST(HChar *,h); \ 15879c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 15889c7779b64eacf264ee427b97ae0df8596b1960ccbart /* assert(nlen >= 1); */ \ 15899c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar n0 = n[0]; \ 15909c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 15919c7779b64eacf264ee427b97ae0df8596b1960ccbart while (1) { \ 15929c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar hh = *h; \ 15939c7779b64eacf264ee427b97ae0df8596b1960ccbart if (hh == 0) return NULL; \ 15949c7779b64eacf264ee427b97ae0df8596b1960ccbart if (hh != n0) { h++; continue; } \ 15959c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 15969c7779b64eacf264ee427b97ae0df8596b1960ccbart UWord i; \ 15979c7779b64eacf264ee427b97ae0df8596b1960ccbart for (i = 0; i < nlen; i++) { \ 15989c7779b64eacf264ee427b97ae0df8596b1960ccbart if (n[i] != h[i]) \ 15999c7779b64eacf264ee427b97ae0df8596b1960ccbart break; \ 16009c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 16019c7779b64eacf264ee427b97ae0df8596b1960ccbart /* assert(i >= 0 && i <= nlen); */ \ 16029c7779b64eacf264ee427b97ae0df8596b1960ccbart if (i == nlen) \ 160370a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian return CONST_CAST(HChar *,h); \ 16049c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 16059c7779b64eacf264ee427b97ae0df8596b1960ccbart h++; \ 16069c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 16079c7779b64eacf264ee427b97ae0df8596b1960ccbart } 16089c7779b64eacf264ee427b97ae0df8596b1960ccbart 16099c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 16109c7779b64eacf264ee427b97ae0df8596b1960ccbart STRSTR(VG_Z_LIBC_SONAME, strstr) 16119c7779b64eacf264ee427b97ae0df8596b1960ccbart STRSTR(VG_Z_LIBC_SONAME, __strstr_sse2) 16129c7779b64eacf264ee427b97ae0df8596b1960ccbart STRSTR(VG_Z_LIBC_SONAME, __strstr_sse42) 16139c7779b64eacf264ee427b97ae0df8596b1960ccbart 16149c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 16159c7779b64eacf264ee427b97ae0df8596b1960ccbart 16168eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 16178eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRSTR(VG_Z_LIBC_SONAME, strstr) 16188eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 16199c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 16209c7779b64eacf264ee427b97ae0df8596b1960ccbart 16219c7779b64eacf264ee427b97ae0df8596b1960ccbart 16229c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strpbrk ----------------------*/ 16239c7779b64eacf264ee427b97ae0df8596b1960ccbart 16249c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRPBRK(soname, fnname) \ 16259c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20320,soname,fnname) \ 16269c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* sV, const char* acceptV); \ 16279c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20320,soname,fnname) \ 16289c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* sV, const char* acceptV) \ 16299c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 16309c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* s = sV; \ 16319c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* accept = acceptV; \ 16329c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 16339c7779b64eacf264ee427b97ae0df8596b1960ccbart /* find the length of 'accept', not including terminating zero */ \ 16349c7779b64eacf264ee427b97ae0df8596b1960ccbart UWord nacc = 0; \ 16359c7779b64eacf264ee427b97ae0df8596b1960ccbart while (accept[nacc]) nacc++; \ 16369c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 16379c7779b64eacf264ee427b97ae0df8596b1960ccbart /* if n is the empty string, fail immediately. */ \ 16389c7779b64eacf264ee427b97ae0df8596b1960ccbart if (nacc == 0) return NULL; \ 16399c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 16409c7779b64eacf264ee427b97ae0df8596b1960ccbart /* assert(nacc >= 1); */ \ 16419c7779b64eacf264ee427b97ae0df8596b1960ccbart while (1) { \ 16429c7779b64eacf264ee427b97ae0df8596b1960ccbart UWord i; \ 16439c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar sc = *s; \ 16449c7779b64eacf264ee427b97ae0df8596b1960ccbart if (sc == 0) \ 16459c7779b64eacf264ee427b97ae0df8596b1960ccbart break; \ 16469c7779b64eacf264ee427b97ae0df8596b1960ccbart for (i = 0; i < nacc; i++) { \ 16479c7779b64eacf264ee427b97ae0df8596b1960ccbart if (sc == accept[i]) \ 164870a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian return CONST_CAST(HChar *,s); \ 16499c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 16509c7779b64eacf264ee427b97ae0df8596b1960ccbart s++; \ 16519c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 16529c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 16539c7779b64eacf264ee427b97ae0df8596b1960ccbart return NULL; \ 16549c7779b64eacf264ee427b97ae0df8596b1960ccbart } 16559c7779b64eacf264ee427b97ae0df8596b1960ccbart 16569c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 16579c7779b64eacf264ee427b97ae0df8596b1960ccbart STRPBRK(VG_Z_LIBC_SONAME, strpbrk) 16589c7779b64eacf264ee427b97ae0df8596b1960ccbart 16599c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 16609c7779b64eacf264ee427b97ae0df8596b1960ccbart 16618eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 16628eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRPBRK(VG_Z_LIBC_SONAME, strpbrk) 16638eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 16649c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 16659c7779b64eacf264ee427b97ae0df8596b1960ccbart 16669c7779b64eacf264ee427b97ae0df8596b1960ccbart 16679c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strcspn ----------------------*/ 16689c7779b64eacf264ee427b97ae0df8596b1960ccbart 16699c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRCSPN(soname, fnname) \ 16709c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20330,soname,fnname) \ 16719c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* sV, const char* rejectV); \ 16729c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20330,soname,fnname) \ 16739c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* sV, const char* rejectV) \ 16749c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 16759c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* s = sV; \ 16769c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* reject = rejectV; \ 16779c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 16789c7779b64eacf264ee427b97ae0df8596b1960ccbart /* find the length of 'reject', not including terminating zero */ \ 16799c7779b64eacf264ee427b97ae0df8596b1960ccbart UWord nrej = 0; \ 16809c7779b64eacf264ee427b97ae0df8596b1960ccbart while (reject[nrej]) nrej++; \ 16819c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 16829c7779b64eacf264ee427b97ae0df8596b1960ccbart UWord len = 0; \ 16839c7779b64eacf264ee427b97ae0df8596b1960ccbart while (1) { \ 16849c7779b64eacf264ee427b97ae0df8596b1960ccbart UWord i; \ 16859c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar sc = *s; \ 16869c7779b64eacf264ee427b97ae0df8596b1960ccbart if (sc == 0) \ 16879c7779b64eacf264ee427b97ae0df8596b1960ccbart break; \ 16889c7779b64eacf264ee427b97ae0df8596b1960ccbart for (i = 0; i < nrej; i++) { \ 16899c7779b64eacf264ee427b97ae0df8596b1960ccbart if (sc == reject[i]) \ 16909c7779b64eacf264ee427b97ae0df8596b1960ccbart break; \ 16919c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 16929c7779b64eacf264ee427b97ae0df8596b1960ccbart /* assert(i >= 0 && i <= nrej); */ \ 16939c7779b64eacf264ee427b97ae0df8596b1960ccbart if (i < nrej) \ 16949c7779b64eacf264ee427b97ae0df8596b1960ccbart break; \ 16959c7779b64eacf264ee427b97ae0df8596b1960ccbart s++; \ 16969c7779b64eacf264ee427b97ae0df8596b1960ccbart len++; \ 16979c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 16989c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 16999c7779b64eacf264ee427b97ae0df8596b1960ccbart return len; \ 17009c7779b64eacf264ee427b97ae0df8596b1960ccbart } 17019c7779b64eacf264ee427b97ae0df8596b1960ccbart 17029c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 17039c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCSPN(VG_Z_LIBC_SONAME, strcspn) 17049c7779b64eacf264ee427b97ae0df8596b1960ccbart 17059c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 17069c7779b64eacf264ee427b97ae0df8596b1960ccbart 17078eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 17088eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRCSPN(VG_Z_LIBC_SONAME, strcspn) 17098eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 17109c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 17119c7779b64eacf264ee427b97ae0df8596b1960ccbart 17129c7779b64eacf264ee427b97ae0df8596b1960ccbart 17139c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strspn ----------------------*/ 17149c7779b64eacf264ee427b97ae0df8596b1960ccbart 17159c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRSPN(soname, fnname) \ 17169c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20340,soname,fnname) \ 17179c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* sV, const char* acceptV); \ 17189c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20340,soname,fnname) \ 17199c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* sV, const char* acceptV) \ 17209c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 17219c7779b64eacf264ee427b97ae0df8596b1960ccbart const UChar* s = (const UChar *)sV; \ 17229c7779b64eacf264ee427b97ae0df8596b1960ccbart const UChar* accept = (const UChar *)acceptV; \ 17239c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 17249c7779b64eacf264ee427b97ae0df8596b1960ccbart /* find the length of 'accept', not including terminating zero */ \ 17259c7779b64eacf264ee427b97ae0df8596b1960ccbart UWord nacc = 0; \ 17269c7779b64eacf264ee427b97ae0df8596b1960ccbart while (accept[nacc]) nacc++; \ 17279c7779b64eacf264ee427b97ae0df8596b1960ccbart if (nacc == 0) return 0; \ 17289c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 17299c7779b64eacf264ee427b97ae0df8596b1960ccbart UWord len = 0; \ 17309c7779b64eacf264ee427b97ae0df8596b1960ccbart while (1) { \ 17319c7779b64eacf264ee427b97ae0df8596b1960ccbart UWord i; \ 17329c7779b64eacf264ee427b97ae0df8596b1960ccbart HChar sc = *s; \ 17339c7779b64eacf264ee427b97ae0df8596b1960ccbart if (sc == 0) \ 17349c7779b64eacf264ee427b97ae0df8596b1960ccbart break; \ 17359c7779b64eacf264ee427b97ae0df8596b1960ccbart for (i = 0; i < nacc; i++) { \ 17369c7779b64eacf264ee427b97ae0df8596b1960ccbart if (sc == accept[i]) \ 17379c7779b64eacf264ee427b97ae0df8596b1960ccbart break; \ 17389c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 17399c7779b64eacf264ee427b97ae0df8596b1960ccbart /* assert(i >= 0 && i <= nacc); */ \ 17409c7779b64eacf264ee427b97ae0df8596b1960ccbart if (i == nacc) \ 17419c7779b64eacf264ee427b97ae0df8596b1960ccbart break; \ 17429c7779b64eacf264ee427b97ae0df8596b1960ccbart s++; \ 17439c7779b64eacf264ee427b97ae0df8596b1960ccbart len++; \ 17449c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 17459c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 17469c7779b64eacf264ee427b97ae0df8596b1960ccbart return len; \ 17479c7779b64eacf264ee427b97ae0df8596b1960ccbart } 17489c7779b64eacf264ee427b97ae0df8596b1960ccbart 17499c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 17509c7779b64eacf264ee427b97ae0df8596b1960ccbart STRSPN(VG_Z_LIBC_SONAME, strspn) 17519c7779b64eacf264ee427b97ae0df8596b1960ccbart 17529c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 17539c7779b64eacf264ee427b97ae0df8596b1960ccbart 17548eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 17558eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRSPN(VG_Z_LIBC_SONAME, strspn) 17568eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 17579c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 17589c7779b64eacf264ee427b97ae0df8596b1960ccbart 17599c7779b64eacf264ee427b97ae0df8596b1960ccbart 17609c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- strcasestr ----------------------*/ 17619c7779b64eacf264ee427b97ae0df8596b1960ccbart 17629c7779b64eacf264ee427b97ae0df8596b1960ccbart#define STRCASESTR(soname, fnname) \ 17639c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20350,soname,fnname) \ 17649c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* haystack, const char* needle); \ 17659c7779b64eacf264ee427b97ae0df8596b1960ccbart char* VG_REPLACE_FUNCTION_EZU(20350,soname,fnname) \ 17669c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* haystack, const char* needle) \ 17679c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 17689c7779b64eacf264ee427b97ae0df8596b1960ccbart extern int tolower(int); \ 17699c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* h = haystack; \ 17709c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* n = needle; \ 17719c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 17729c7779b64eacf264ee427b97ae0df8596b1960ccbart /* find the length of n, not including terminating zero */ \ 17739c7779b64eacf264ee427b97ae0df8596b1960ccbart UWord nlen = 0; \ 17749c7779b64eacf264ee427b97ae0df8596b1960ccbart while (n[nlen]) nlen++; \ 17759c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 17769c7779b64eacf264ee427b97ae0df8596b1960ccbart /* if n is the empty string, match immediately. */ \ 177770a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian if (nlen == 0) return CONST_CAST(HChar *,h); \ 17789c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 17799c7779b64eacf264ee427b97ae0df8596b1960ccbart /* assert(nlen >= 1); */ \ 17809c7779b64eacf264ee427b97ae0df8596b1960ccbart UChar n0 = tolower(n[0]); \ 17819c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 17829c7779b64eacf264ee427b97ae0df8596b1960ccbart while (1) { \ 17839c7779b64eacf264ee427b97ae0df8596b1960ccbart UChar hh = tolower(*h); \ 17849c7779b64eacf264ee427b97ae0df8596b1960ccbart if (hh == 0) return NULL; \ 17859c7779b64eacf264ee427b97ae0df8596b1960ccbart if (hh != n0) { h++; continue; } \ 17869c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 17879c7779b64eacf264ee427b97ae0df8596b1960ccbart UWord i; \ 17889c7779b64eacf264ee427b97ae0df8596b1960ccbart for (i = 0; i < nlen; i++) { \ 17899c7779b64eacf264ee427b97ae0df8596b1960ccbart if (tolower(n[i]) != tolower(h[i])) \ 17909c7779b64eacf264ee427b97ae0df8596b1960ccbart break; \ 17919c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 17929c7779b64eacf264ee427b97ae0df8596b1960ccbart /* assert(i >= 0 && i <= nlen); */ \ 17939c7779b64eacf264ee427b97ae0df8596b1960ccbart if (i == nlen) \ 179470a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian return CONST_CAST(HChar *,h); \ 17959c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 17969c7779b64eacf264ee427b97ae0df8596b1960ccbart h++; \ 17979c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 17989c7779b64eacf264ee427b97ae0df8596b1960ccbart } 17999c7779b64eacf264ee427b97ae0df8596b1960ccbart 18009c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 180126ed419d60369d0545510eba0832566e24452e1esewardj# if !defined(VGPV_arm_linux_android) \ 180226ed419d60369d0545510eba0832566e24452e1esewardj && !defined(VGPV_x86_linux_android) \ 180326ed419d60369d0545510eba0832566e24452e1esewardj && !defined(VGPV_mips32_linux_android) \ 180426ed419d60369d0545510eba0832566e24452e1esewardj && !defined(VGPV_arm64_linux_android) 18059c7779b64eacf264ee427b97ae0df8596b1960ccbart STRCASESTR(VG_Z_LIBC_SONAME, strcasestr) 18069c7779b64eacf264ee427b97ae0df8596b1960ccbart# endif 18079c7779b64eacf264ee427b97ae0df8596b1960ccbart 18089c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 18099c7779b64eacf264ee427b97ae0df8596b1960ccbart 18108eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 18118eb8bab992e3998c33770b0cdb16059a8b918a06sewardj STRCASESTR(VG_Z_LIBC_SONAME, strcasestr) 18128eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 18139c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 18149c7779b64eacf264ee427b97ae0df8596b1960ccbart 18159c7779b64eacf264ee427b97ae0df8596b1960ccbart 18169c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- wcslen ----------------------*/ 18179c7779b64eacf264ee427b97ae0df8596b1960ccbart 18189c7779b64eacf264ee427b97ae0df8596b1960ccbart// This is a wchar_t equivalent to strlen. Unfortunately 18199c7779b64eacf264ee427b97ae0df8596b1960ccbart// we don't have wchar_t available here, but it looks like 18209c7779b64eacf264ee427b97ae0df8596b1960ccbart// a 32 bit int on Linux. I don't know if that is also 18219c7779b64eacf264ee427b97ae0df8596b1960ccbart// valid on MacOSX. 18229c7779b64eacf264ee427b97ae0df8596b1960ccbart 18239c7779b64eacf264ee427b97ae0df8596b1960ccbart#define WCSLEN(soname, fnname) \ 18249c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20370,soname,fnname) \ 18259c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const UInt* str ); \ 18269c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT VG_REPLACE_FUNCTION_EZU(20370,soname,fnname) \ 18279c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const UInt* str ) \ 18289c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 18299c7779b64eacf264ee427b97ae0df8596b1960ccbart SizeT i = 0; \ 18309c7779b64eacf264ee427b97ae0df8596b1960ccbart while (str[i] != 0) i++; \ 18319c7779b64eacf264ee427b97ae0df8596b1960ccbart return i; \ 18329c7779b64eacf264ee427b97ae0df8596b1960ccbart } 18339c7779b64eacf264ee427b97ae0df8596b1960ccbart 18349c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 18359c7779b64eacf264ee427b97ae0df8596b1960ccbart WCSLEN(VG_Z_LIBC_SONAME, wcslen) 18369c7779b64eacf264ee427b97ae0df8596b1960ccbart 18379c7779b64eacf264ee427b97ae0df8596b1960ccbart#elif defined(VGO_darwin) 18389c7779b64eacf264ee427b97ae0df8596b1960ccbart 18398eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#elif defined(VGO_solaris) 18408eb8bab992e3998c33770b0cdb16059a8b918a06sewardj WCSLEN(VG_Z_LIBC_SONAME, wcslen) 18418eb8bab992e3998c33770b0cdb16059a8b918a06sewardj 18429c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 18439c7779b64eacf264ee427b97ae0df8596b1960ccbart 18449c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- wcscmp ----------------------*/ 18459c7779b64eacf264ee427b97ae0df8596b1960ccbart 18469c7779b64eacf264ee427b97ae0df8596b1960ccbart// This is a wchar_t equivalent to strcmp. We don't 18479c7779b64eacf264ee427b97ae0df8596b1960ccbart// have wchar_t available here, but in the GNU C Library 18489c7779b64eacf264ee427b97ae0df8596b1960ccbart// wchar_t is always 32 bits wide and wcscmp uses signed 18499c7779b64eacf264ee427b97ae0df8596b1960ccbart// comparison, not unsigned as in strcmp function. 18509c7779b64eacf264ee427b97ae0df8596b1960ccbart 18519c7779b64eacf264ee427b97ae0df8596b1960ccbart#define WCSCMP(soname, fnname) \ 18529c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20380,soname,fnname) \ 18539c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const Int* s1, const Int* s2 ); \ 18549c7779b64eacf264ee427b97ae0df8596b1960ccbart int VG_REPLACE_FUNCTION_EZU(20380,soname,fnname) \ 18559c7779b64eacf264ee427b97ae0df8596b1960ccbart ( const Int* s1, const Int* s2 ) \ 18569c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 18579c7779b64eacf264ee427b97ae0df8596b1960ccbart register Int c1; \ 18589c7779b64eacf264ee427b97ae0df8596b1960ccbart register Int c2; \ 18599c7779b64eacf264ee427b97ae0df8596b1960ccbart while (True) { \ 18609c7779b64eacf264ee427b97ae0df8596b1960ccbart c1 = *s1; \ 18619c7779b64eacf264ee427b97ae0df8596b1960ccbart c2 = *s2; \ 18629c7779b64eacf264ee427b97ae0df8596b1960ccbart if (c1 != c2) break; \ 18639c7779b64eacf264ee427b97ae0df8596b1960ccbart if (c1 == 0) break; \ 18649c7779b64eacf264ee427b97ae0df8596b1960ccbart s1++; s2++; \ 18659c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 18669c7779b64eacf264ee427b97ae0df8596b1960ccbart if (c1 < c2) return -1; \ 18679c7779b64eacf264ee427b97ae0df8596b1960ccbart if (c1 > c2) return 1; \ 18689c7779b64eacf264ee427b97ae0df8596b1960ccbart return 0; \ 18699c7779b64eacf264ee427b97ae0df8596b1960ccbart } 18709c7779b64eacf264ee427b97ae0df8596b1960ccbart 18719c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 18729c7779b64eacf264ee427b97ae0df8596b1960ccbart WCSCMP(VG_Z_LIBC_SONAME, wcscmp) 18739c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 18749c7779b64eacf264ee427b97ae0df8596b1960ccbart 18759c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- wcscpy ----------------------*/ 18769c7779b64eacf264ee427b97ae0df8596b1960ccbart 18779c7779b64eacf264ee427b97ae0df8596b1960ccbart// This is a wchar_t equivalent to strcpy. We don't 18789c7779b64eacf264ee427b97ae0df8596b1960ccbart// have wchar_t available here, but in the GNU C Library 18799c7779b64eacf264ee427b97ae0df8596b1960ccbart// wchar_t is always 32 bits wide. 18809c7779b64eacf264ee427b97ae0df8596b1960ccbart 18819c7779b64eacf264ee427b97ae0df8596b1960ccbart#define WCSCPY(soname, fnname) \ 18829c7779b64eacf264ee427b97ae0df8596b1960ccbart Int* VG_REPLACE_FUNCTION_EZU(20390,soname,fnname) \ 18839c7779b64eacf264ee427b97ae0df8596b1960ccbart ( Int* dst, const Int* src ); \ 18849c7779b64eacf264ee427b97ae0df8596b1960ccbart Int* VG_REPLACE_FUNCTION_EZU(20390,soname,fnname) \ 18859c7779b64eacf264ee427b97ae0df8596b1960ccbart ( Int* dst, const Int* src ) \ 18869c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 18879c7779b64eacf264ee427b97ae0df8596b1960ccbart const Int* src_orig = src; \ 18889c7779b64eacf264ee427b97ae0df8596b1960ccbart Int* dst_orig = dst; \ 18899c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 18909c7779b64eacf264ee427b97ae0df8596b1960ccbart while (*src) *dst++ = *src++; \ 18919c7779b64eacf264ee427b97ae0df8596b1960ccbart *dst = 0; \ 18929c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 18939c7779b64eacf264ee427b97ae0df8596b1960ccbart /* This checks for overlap after copying, unavoidable without */ \ 18949c7779b64eacf264ee427b97ae0df8596b1960ccbart /* pre-counting length... should be ok */ \ 18959c7779b64eacf264ee427b97ae0df8596b1960ccbart if (is_overlap(dst_orig, \ 18969c7779b64eacf264ee427b97ae0df8596b1960ccbart src_orig, \ 18979c7779b64eacf264ee427b97ae0df8596b1960ccbart (Addr)dst-(Addr)dst_orig+1, \ 18989c7779b64eacf264ee427b97ae0df8596b1960ccbart (Addr)src-(Addr)src_orig+1)) \ 18999c7779b64eacf264ee427b97ae0df8596b1960ccbart RECORD_OVERLAP_ERROR("wcscpy", dst_orig, src_orig, 0); \ 19009c7779b64eacf264ee427b97ae0df8596b1960ccbart \ 19019c7779b64eacf264ee427b97ae0df8596b1960ccbart return dst_orig; \ 19029c7779b64eacf264ee427b97ae0df8596b1960ccbart } 19039c7779b64eacf264ee427b97ae0df8596b1960ccbart 19049c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 19059c7779b64eacf264ee427b97ae0df8596b1960ccbart WCSCPY(VG_Z_LIBC_SONAME, wcscpy) 19069c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 19079c7779b64eacf264ee427b97ae0df8596b1960ccbart 19089c7779b64eacf264ee427b97ae0df8596b1960ccbart 19099c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- wcschr ----------------------*/ 19109c7779b64eacf264ee427b97ae0df8596b1960ccbart 19119c7779b64eacf264ee427b97ae0df8596b1960ccbart// This is a wchar_t equivalent to strchr. We don't 19129c7779b64eacf264ee427b97ae0df8596b1960ccbart// have wchar_t available here, but in the GNU C Library 19139c7779b64eacf264ee427b97ae0df8596b1960ccbart// wchar_t is always 32 bits wide. 19149c7779b64eacf264ee427b97ae0df8596b1960ccbart 19159c7779b64eacf264ee427b97ae0df8596b1960ccbart#define WCSCHR(soname, fnname) \ 19169c7779b64eacf264ee427b97ae0df8596b1960ccbart Int* VG_REPLACE_FUNCTION_EZU(20400,soname,fnname) ( const Int* s, Int c ); \ 19179c7779b64eacf264ee427b97ae0df8596b1960ccbart Int* VG_REPLACE_FUNCTION_EZU(20400,soname,fnname) ( const Int* s, Int c ) \ 19189c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 191970a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian const Int* p = s; \ 19209c7779b64eacf264ee427b97ae0df8596b1960ccbart while (True) { \ 192170a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian if (*p == c) return CONST_CAST(Int *,p); \ 19229c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*p == 0) return NULL; \ 19239c7779b64eacf264ee427b97ae0df8596b1960ccbart p++; \ 19249c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 19259c7779b64eacf264ee427b97ae0df8596b1960ccbart } 19269c7779b64eacf264ee427b97ae0df8596b1960ccbart 19279c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 19289c7779b64eacf264ee427b97ae0df8596b1960ccbart WCSCHR(VG_Z_LIBC_SONAME, wcschr) 19299c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 19309c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- wcsrchr ----------------------*/ 19319c7779b64eacf264ee427b97ae0df8596b1960ccbart 19329c7779b64eacf264ee427b97ae0df8596b1960ccbart// This is a wchar_t equivalent to strrchr. We don't 19339c7779b64eacf264ee427b97ae0df8596b1960ccbart// have wchar_t available here, but in the GNU C Library 19349c7779b64eacf264ee427b97ae0df8596b1960ccbart// wchar_t is always 32 bits wide. 19359c7779b64eacf264ee427b97ae0df8596b1960ccbart 19369c7779b64eacf264ee427b97ae0df8596b1960ccbart#define WCSRCHR(soname, fnname) \ 19379c7779b64eacf264ee427b97ae0df8596b1960ccbart Int* VG_REPLACE_FUNCTION_EZU(20410,soname,fnname)( const Int* s, Int c ); \ 19389c7779b64eacf264ee427b97ae0df8596b1960ccbart Int* VG_REPLACE_FUNCTION_EZU(20410,soname,fnname)( const Int* s, Int c ) \ 19399c7779b64eacf264ee427b97ae0df8596b1960ccbart { \ 194070a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian const Int* p = s; \ 194170a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian const Int* last = NULL; \ 19429c7779b64eacf264ee427b97ae0df8596b1960ccbart while (True) { \ 19439c7779b64eacf264ee427b97ae0df8596b1960ccbart if (*p == c) last = p; \ 194470a5de1d6c1a5c74b91b564b0ead8ae8a460173cflorian if (*p == 0) return CONST_CAST(Int *,last); \ 19459c7779b64eacf264ee427b97ae0df8596b1960ccbart p++; \ 19469c7779b64eacf264ee427b97ae0df8596b1960ccbart } \ 19479c7779b64eacf264ee427b97ae0df8596b1960ccbart } 19489c7779b64eacf264ee427b97ae0df8596b1960ccbart 19499c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 19509c7779b64eacf264ee427b97ae0df8596b1960ccbart WCSRCHR(VG_Z_LIBC_SONAME, wcsrchr) 19519c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif 19529c7779b64eacf264ee427b97ae0df8596b1960ccbart 19539c7779b64eacf264ee427b97ae0df8596b1960ccbart/*------------------------------------------------------------*/ 19549c7779b64eacf264ee427b97ae0df8596b1960ccbart/*--- Improve definedness checking of process environment ---*/ 19559c7779b64eacf264ee427b97ae0df8596b1960ccbart/*------------------------------------------------------------*/ 19569c7779b64eacf264ee427b97ae0df8596b1960ccbart 19579c7779b64eacf264ee427b97ae0df8596b1960ccbart#if defined(VGO_linux) 19589c7779b64eacf264ee427b97ae0df8596b1960ccbart 19599c7779b64eacf264ee427b97ae0df8596b1960ccbart/* If these wind up getting generated via a macro, so that multiple 19609c7779b64eacf264ee427b97ae0df8596b1960ccbart versions of each function exist (as above), use the _EZU variants 19619c7779b64eacf264ee427b97ae0df8596b1960ccbart to assign equivalance class tags. */ 19629c7779b64eacf264ee427b97ae0df8596b1960ccbart 19639c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- putenv ----------------------*/ 19649c7779b64eacf264ee427b97ae0df8596b1960ccbart 19659c7779b64eacf264ee427b97ae0df8596b1960ccbartint VG_WRAP_FUNCTION_ZU(VG_Z_LIBC_SONAME, putenv) (char* string); 19669c7779b64eacf264ee427b97ae0df8596b1960ccbartint VG_WRAP_FUNCTION_ZU(VG_Z_LIBC_SONAME, putenv) (char* string) 19679c7779b64eacf264ee427b97ae0df8596b1960ccbart{ 19689c7779b64eacf264ee427b97ae0df8596b1960ccbart OrigFn fn; 19699c7779b64eacf264ee427b97ae0df8596b1960ccbart Word result; 19709c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* p = string; 19719c7779b64eacf264ee427b97ae0df8596b1960ccbart VALGRIND_GET_ORIG_FN(fn); 19729c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Now by walking over the string we magically produce 19739c7779b64eacf264ee427b97ae0df8596b1960ccbart traces when hitting undefined memory. */ 19749c7779b64eacf264ee427b97ae0df8596b1960ccbart if (p) 19759c7779b64eacf264ee427b97ae0df8596b1960ccbart while (*p++) 19769c7779b64eacf264ee427b97ae0df8596b1960ccbart __asm__ __volatile__("" ::: "memory"); 19779c7779b64eacf264ee427b97ae0df8596b1960ccbart CALL_FN_W_W(result, fn, string); 19789c7779b64eacf264ee427b97ae0df8596b1960ccbart return result; 19799c7779b64eacf264ee427b97ae0df8596b1960ccbart} 19809c7779b64eacf264ee427b97ae0df8596b1960ccbart 19819c7779b64eacf264ee427b97ae0df8596b1960ccbart 19829c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- unsetenv ----------------------*/ 19839c7779b64eacf264ee427b97ae0df8596b1960ccbart 19849c7779b64eacf264ee427b97ae0df8596b1960ccbartint VG_WRAP_FUNCTION_ZU(VG_Z_LIBC_SONAME, unsetenv) (const char* name); 19859c7779b64eacf264ee427b97ae0df8596b1960ccbartint VG_WRAP_FUNCTION_ZU(VG_Z_LIBC_SONAME, unsetenv) (const char* name) 19869c7779b64eacf264ee427b97ae0df8596b1960ccbart{ 19879c7779b64eacf264ee427b97ae0df8596b1960ccbart OrigFn fn; 19889c7779b64eacf264ee427b97ae0df8596b1960ccbart Word result; 19899c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* p = name; 19909c7779b64eacf264ee427b97ae0df8596b1960ccbart VALGRIND_GET_ORIG_FN(fn); 19919c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Now by walking over the string we magically produce 19929c7779b64eacf264ee427b97ae0df8596b1960ccbart traces when hitting undefined memory. */ 19939c7779b64eacf264ee427b97ae0df8596b1960ccbart if (p) 19949c7779b64eacf264ee427b97ae0df8596b1960ccbart while (*p++) 19959c7779b64eacf264ee427b97ae0df8596b1960ccbart __asm__ __volatile__("" ::: "memory"); 19969c7779b64eacf264ee427b97ae0df8596b1960ccbart CALL_FN_W_W(result, fn, name); 19979c7779b64eacf264ee427b97ae0df8596b1960ccbart return result; 19989c7779b64eacf264ee427b97ae0df8596b1960ccbart} 19999c7779b64eacf264ee427b97ae0df8596b1960ccbart 20009c7779b64eacf264ee427b97ae0df8596b1960ccbart 20019c7779b64eacf264ee427b97ae0df8596b1960ccbart/*---------------------- setenv ----------------------*/ 20029c7779b64eacf264ee427b97ae0df8596b1960ccbart 20039c7779b64eacf264ee427b97ae0df8596b1960ccbart/* setenv */ 20049c7779b64eacf264ee427b97ae0df8596b1960ccbartint VG_WRAP_FUNCTION_ZU(VG_Z_LIBC_SONAME, setenv) 20059c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* name, const char* value, int overwrite); 20069c7779b64eacf264ee427b97ae0df8596b1960ccbartint VG_WRAP_FUNCTION_ZU(VG_Z_LIBC_SONAME, setenv) 20079c7779b64eacf264ee427b97ae0df8596b1960ccbart (const char* name, const char* value, int overwrite) 20089c7779b64eacf264ee427b97ae0df8596b1960ccbart{ 20099c7779b64eacf264ee427b97ae0df8596b1960ccbart OrigFn fn; 20109c7779b64eacf264ee427b97ae0df8596b1960ccbart Word result; 20119c7779b64eacf264ee427b97ae0df8596b1960ccbart const HChar* p; 20129c7779b64eacf264ee427b97ae0df8596b1960ccbart VALGRIND_GET_ORIG_FN(fn); 20139c7779b64eacf264ee427b97ae0df8596b1960ccbart /* Now by walking over the string we magically produce 20149c7779b64eacf264ee427b97ae0df8596b1960ccbart traces when hitting undefined memory. */ 20159c7779b64eacf264ee427b97ae0df8596b1960ccbart if (name) 20169c7779b64eacf264ee427b97ae0df8596b1960ccbart for (p = name; *p; p++) 20179c7779b64eacf264ee427b97ae0df8596b1960ccbart __asm__ __volatile__("" ::: "memory"); 20189c7779b64eacf264ee427b97ae0df8596b1960ccbart if (value) 20199c7779b64eacf264ee427b97ae0df8596b1960ccbart for (p = value; *p; p++) 20209c7779b64eacf264ee427b97ae0df8596b1960ccbart __asm__ __volatile__("" ::: "memory"); 20219c7779b64eacf264ee427b97ae0df8596b1960ccbart (void) VALGRIND_CHECK_VALUE_IS_DEFINED (overwrite); 20229c7779b64eacf264ee427b97ae0df8596b1960ccbart CALL_FN_W_WWW(result, fn, name, value, overwrite); 20239c7779b64eacf264ee427b97ae0df8596b1960ccbart return result; 20249c7779b64eacf264ee427b97ae0df8596b1960ccbart} 20259c7779b64eacf264ee427b97ae0df8596b1960ccbart 20269c7779b64eacf264ee427b97ae0df8596b1960ccbart#endif /* defined(VGO_linux) */ 20279c7779b64eacf264ee427b97ae0df8596b1960ccbart 20289c7779b64eacf264ee427b97ae0df8596b1960ccbart/*--------------------------------------------------------------------*/ 20299c7779b64eacf264ee427b97ae0df8596b1960ccbart/*--- end ---*/ 20309c7779b64eacf264ee427b97ae0df8596b1960ccbart/*--------------------------------------------------------------------*/ 2031