Reactos
at master 108 lines 3.2 kB view raw
1/*** 2*mbsrev.c - Reverse a string in place (MBCS) 3* 4* Copyright (c) Microsoft Corporation. All rights reserved. 5* 6*Purpose: 7* Reverse a string in place (MBCS) 8* 9*******************************************************************************/ 10#ifndef _MBCS 11 #error This file should only be compiled with _MBCS defined 12#endif 13 14#include <corecrt_internal_mbstring.h> 15#include <locale.h> 16#include <string.h> 17 18 19/*** 20* _mbsrev - Reverse a string in place (MBCS) 21* 22*Purpose: 23* Reverses the order of characters in the string. The terminating 24* null character remains in place. The order of MBCS characters 25* is not changed. 26* 27*Entry: 28* unsigned char *string = string to reverse 29* 30*Exit: 31* returns string - now with reversed characters 32* 33*Exceptions: 34* Input parameters are validated. Refer to the validation section of the function. 35* 36*******************************************************************************/ 37 38extern "C" unsigned char * __cdecl _mbsrev_l( 39 unsigned char *string, 40 _locale_t plocinfo 41 ) 42{ 43 unsigned char *start = string; 44 unsigned char *left = string; 45 unsigned char c; 46 _LocaleUpdate _loc_update(plocinfo); 47 48 /* validation section */ 49 _VALIDATE_RETURN(string != nullptr, EINVAL, nullptr); 50 51 if (_loc_update.GetLocaleT()->mbcinfo->ismbcodepage == 0) 52 return (unsigned char *)_strrev((char *)string); 53 54 55 /* first go through and reverse the bytes in MBCS chars */ 56 while ( *string ) { 57 if ( _ismbblead_l(*string++, _loc_update.GetLocaleT()) ) { 58 if ( *string ) { 59 c = *string; 60 *string = *(string - 1); 61 *(string - 1) = c; 62 string++; 63 } 64 else 65 { 66 /* second byte is EOS 67 There is nothing really satisfying to do here. We have a string 68 that ends in leadbyte,'\0'. Reversing this would lead to the leadbyte 69 becoming falsely attached to the character before it: 70 (XL0 -> LX0, X has suddenly become a trailbyte) 71 72 So what we choose to do is assert and purge the dud byte from within the 73 string. 74 */ 75 errno = EINVAL; 76 _ASSERTE(("Bad MBCS string passed into _mbsrev",0)); 77 78 /* String has at least moved once already, so this is safe */ 79 _ASSERTE(string>start); 80 81 /* move back one to point at the dud leadbyte */ 82 --string; 83 84 /* now truncate the string one byte earlier */ 85 *string='\0'; 86 87 break; 88 } 89 } 90 } 91 92 /* now reverse the whole string */ 93 string--; 94 while ( left < string ) { 95 c = *left; 96 *left++ = *string; 97 *string-- = c; 98 } 99 100 return ( start ); 101} 102 103extern "C" unsigned char * (__cdecl _mbsrev)( 104 unsigned char *string 105 ) 106{ 107 return _mbsrev_l(string, nullptr); 108}