Added case insensitivity search to ReplaceString (bug 3639, r=dvander).

This commit is contained in:
Fyren 2009-03-01 16:41:44 -05:00
parent 96a3671bb6
commit e04d2a4a10
4 changed files with 36 additions and 12 deletions

View File

@ -1362,14 +1362,14 @@ char *sm_strdup(const char *str)
return ptr; return ptr;
} }
unsigned int UTIL_ReplaceAll(char *subject, size_t maxlength, const char *search, const char *replace) unsigned int UTIL_ReplaceAll(char *subject, size_t maxlength, const char *search, const char *replace, bool caseSensitive)
{ {
size_t searchLen = strlen(search); size_t searchLen = strlen(search);
size_t replaceLen = strlen(replace); size_t replaceLen = strlen(replace);
char *ptr = subject; char *ptr = subject;
unsigned int total = 0; unsigned int total = 0;
while ((ptr = UTIL_ReplaceEx(ptr, maxlength, search, searchLen, replace, replaceLen)) != NULL) while ((ptr = UTIL_ReplaceEx(ptr, maxlength, search, searchLen, replace, replaceLen, caseSensitive)) != NULL)
{ {
total++; total++;
if (*ptr == '\0') if (*ptr == '\0')
@ -1394,7 +1394,7 @@ unsigned int UTIL_ReplaceAll(char *subject, size_t maxlength, const char *search
* bad buffer sizes. Instead, this function will smartly cut off the * bad buffer sizes. Instead, this function will smartly cut off the
* string in a way that pushes old data out. * string in a way that pushes old data out.
*/ */
char *UTIL_ReplaceEx(char *subject, size_t maxLen, const char *search, size_t searchLen, const char *replace, size_t replaceLen) char *UTIL_ReplaceEx(char *subject, size_t maxLen, const char *search, size_t searchLen, const char *replace, size_t replaceLen, bool caseSensitive)
{ {
char *ptr = subject; char *ptr = subject;
size_t browsed = 0; size_t browsed = 0;
@ -1414,7 +1414,7 @@ char *UTIL_ReplaceEx(char *subject, size_t maxLen, const char *search, size_t se
/* If the search matches and the replace length is 0, /* If the search matches and the replace length is 0,
* we can just terminate the string and be done. * we can just terminate the string and be done.
*/ */
if (strcmp(subject, search) == 0 && replaceLen == 0) if ((caseSensitive ? strcmp(subject, search) : strcasecmp(subject, search)) == 0 && replaceLen == 0)
{ {
*subject = '\0'; *subject = '\0';
return subject; return subject;
@ -1431,7 +1431,7 @@ char *UTIL_ReplaceEx(char *subject, size_t maxLen, const char *search, size_t se
while (*ptr != '\0' && (browsed <= textLen - searchLen)) while (*ptr != '\0' && (browsed <= textLen - searchLen))
{ {
/* See if we get a comparison */ /* See if we get a comparison */
if (strncmp(ptr, search, searchLen) == 0) if ((caseSensitive ? strncmp(ptr, search, searchLen) : strncasecmp(ptr, search, searchLen)) == 0)
{ {
if (replaceLen > searchLen) if (replaceLen > searchLen)
{ {
@ -1507,7 +1507,7 @@ char *UTIL_ReplaceEx(char *subject, size_t maxLen, const char *search, size_t se
* Search : BBB * Search : BBB
* Replace: D * Replace: D
* OUTPUT : AADCCC * OUTPUT : AADCCC
* POSOTION: ^ * POSITION: ^
*/ */
/* If the replacement does not grow the string length, we do not /* If the replacement does not grow the string length, we do not
* need to do any fancy checking at all. Yay! * need to do any fancy checking at all. Yay!

View File

@ -57,8 +57,8 @@ bool gnprintf(char *buffer,
size_t UTIL_Format(char *buffer, size_t maxlength, const char *fmt, ...); size_t UTIL_Format(char *buffer, size_t maxlength, const char *fmt, ...);
size_t UTIL_FormatArgs(char *buffer, size_t maxlength, const char *fmt, va_list ap); size_t UTIL_FormatArgs(char *buffer, size_t maxlength, const char *fmt, va_list ap);
char *sm_strdup(const char *str); char *sm_strdup(const char *str);
unsigned int UTIL_ReplaceAll(char *subject, size_t maxlength, const char *search, const char *replace); unsigned int UTIL_ReplaceAll(char *subject, size_t maxlength, const char *search, const char *replace, bool caseSensitive = true);
char *UTIL_ReplaceEx(char *subject, size_t maxLen, const char *search, size_t searchLen, const char *replace, size_t replaceLen); char *UTIL_ReplaceEx(char *subject, size_t maxLen, const char *search, size_t searchLen, const char *replace, size_t replaceLen, bool caseSensitive = true);
char *UTIL_TrimWhitespace(char *str, size_t &len); char *UTIL_TrimWhitespace(char *str, size_t &len);
#endif // _INCLUDE_SOURCEMOD_STRINGUTIL_H_ #endif // _INCLUDE_SOURCEMOD_STRINGUTIL_H_

View File

@ -491,24 +491,36 @@ static cell_t ReplaceString(IPluginContext *pContext, const cell_t *params)
{ {
char *text, *search, *replace; char *text, *search, *replace;
size_t maxlength; size_t maxlength;
bool caseSensitive;
pContext->LocalToString(params[1], &text); pContext->LocalToString(params[1], &text);
pContext->LocalToString(params[3], &search); pContext->LocalToString(params[3], &search);
pContext->LocalToString(params[4], &replace); pContext->LocalToString(params[4], &replace);
maxlength = (size_t)params[2]; maxlength = (size_t)params[2];
/* Account for old binary plugins that won't pass the last parameter */
if (params[0] == 5)
{
caseSensitive = (bool)params[5];
}
else
{
caseSensitive = true;
}
if (search[0] == '\0') if (search[0] == '\0')
{ {
return pContext->ThrowNativeError("Cannot replace searches of empty strings"); return pContext->ThrowNativeError("Cannot replace searches of empty strings");
} }
return UTIL_ReplaceAll(text, maxlength, search, replace); return UTIL_ReplaceAll(text, maxlength, search, replace, caseSensitive);
} }
static cell_t ReplaceStringEx(IPluginContext *pContext, const cell_t *params) static cell_t ReplaceStringEx(IPluginContext *pContext, const cell_t *params)
{ {
char *text, *search, *replace; char *text, *search, *replace;
size_t maxlength; size_t maxlength;
bool caseSensitive;
pContext->LocalToString(params[1], &text); pContext->LocalToString(params[1], &text);
pContext->LocalToString(params[3], &search); pContext->LocalToString(params[3], &search);
@ -518,12 +530,22 @@ static cell_t ReplaceStringEx(IPluginContext *pContext, const cell_t *params)
size_t searchLen = (params[5] == -1) ? strlen(search) : (size_t)params[5]; size_t searchLen = (params[5] == -1) ? strlen(search) : (size_t)params[5];
size_t replaceLen = (params[6] == -1) ? strlen(replace) : (size_t)params[6]; size_t replaceLen = (params[6] == -1) ? strlen(replace) : (size_t)params[6];
/* Account for old binary plugins that won't pass the last parameter */
if (params[0] == 7)
{
caseSensitive = (bool)params[7];
}
else
{
caseSensitive = true;
}
if (searchLen == 0) if (searchLen == 0)
{ {
return pContext->ThrowNativeError("Cannot replace searches of empty strings"); return pContext->ThrowNativeError("Cannot replace searches of empty strings");
} }
char *ptr = UTIL_ReplaceEx(text, maxlength, search, searchLen, replace, replaceLen); char *ptr = UTIL_ReplaceEx(text, maxlength, search, searchLen, replace, replaceLen, caseSensitive);
if (ptr == NULL) if (ptr == NULL)
{ {

View File

@ -284,9 +284,10 @@ native SplitString(const String:source[], const String:split[], String:part[], p
* @param maxlength Maximum length of the string buffer. * @param maxlength Maximum length of the string buffer.
* @param search String to search for. * @param search String to search for.
* @param replace String to replace the search string with. * @param replace String to replace the search string with.
* @param caseSensitive If true (default), search is case sensitive.
* @return Number of replacements that were performed. * @return Number of replacements that were performed.
*/ */
native ReplaceString(String:text[], maxlength, const String:search[], const String:replace[]); native ReplaceString(String:text[], maxlength, const String:search[], const String:replace[], bool:caseSensitive=true);
/** /**
* Given a string, replaces the first occurrence of a search string with a * Given a string, replaces the first occurrence of a search string with a
@ -300,11 +301,12 @@ native ReplaceString(String:text[], maxlength, const String:search[], const Stri
* a strlen() call on the search parameter. * a strlen() call on the search parameter.
* @param replaceLen If higher than -1, its value will be used instead of * @param replaceLen If higher than -1, its value will be used instead of
* a strlen() call on the replace parameter. * a strlen() call on the replace parameter.
* @param caseSensitive If true (default), search is case sensitive.
* @return Index into the buffer (relative to the start) from where * @return Index into the buffer (relative to the start) from where
* the last replacement ended, or -1 if no replacements were * the last replacement ended, or -1 if no replacements were
* made. * made.
*/ */
native ReplaceStringEx(String:text[], maxlength, const String:search[], const String:replace[], searchLen=-1, replaceLen=-1); native ReplaceStringEx(String:text[], maxlength, const String:search[], const String:replace[], searchLen=-1, replaceLen=-1, bool:caseSensitive=true);
/** /**
* Returns the number of bytes a character is using. This is * Returns the number of bytes a character is using. This is