1 /* 2 Functions for replacing substrings in strings. 3 4 Copyright (C) 2013-2024 5 Free Software Foundation, Inc. 6 7 Written by: 8 Slava Zanko <slavazanko@gmail.com>, 2013; 9 10 This file is part of the Midnight Commander. 11 12 The Midnight Commander is free software: you can redistribute it 13 and/or modify it under the terms of the GNU General Public License as 14 published by the Free Software Foundation, either version 3 of the License, 15 or (at your option) any later version. 16 17 The Midnight Commander is distributed in the hope that it will be useful, 18 but WITHOUT ANY WARRANTY; without even the implied warranty of 19 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 20 GNU General Public License for more details. 21 22 You should have received a copy of the GNU General Public License 23 along with this program. If not, see <http://www.gnu.org/licenses/>. 24 */ 25 26 #include <config.h> 27 28 #include "lib/global.h" 29 #include "lib/strutil.h" 30 31 /*** global variables ****************************************************************************/ 32 33 /*** file scope macro definitions ****************************************************************/ 34 35 /*** file scope type declarations ****************************************************************/ 36 37 /*** forward declarations (file scope functions) *************************************************/ 38 39 /*** file scope variables ************************************************************************/ 40 41 /* --------------------------------------------------------------------------------------------- */ 42 /*** file scope functions ************************************************************************/ 43 /* --------------------------------------------------------------------------------------------- */ 44 45 /* --------------------------------------------------------------------------------------------- */ 46 /*** public functions ****************************************************************************/ 47 /* --------------------------------------------------------------------------------------------- */ 48 /** 49 * Replace all substrings 'needle' in string 'haystack' by 'replacement'. 50 * If the 'needle' in the 'haystack' is escaped by backslash, 51 * then this occurrence isn't be replaced. 52 * 53 * @param haystack string contains substrings for replacement. Cannot be NULL. 54 * @param needle string for search. Cannot be NULL. 55 * @param replacement string for replace. Cannot be NULL. 56 * @return newly allocated string with replaced substrings or NULL if @haystack is empty. 57 */ 58 59 char * 60 str_replace_all (const char *haystack, const char *needle, const char *replacement) /* */ 61 { 62 size_t needle_len, replacement_len; 63 GString *return_str = NULL; 64 char *needle_in_str; 65 66 needle_len = strlen (needle); 67 replacement_len = strlen (replacement); 68 69 while ((needle_in_str = strstr (haystack, needle)) != NULL) 70 { 71 if (return_str == NULL) 72 return_str = g_string_sized_new (32); 73 74 if (str_is_char_escaped (haystack, needle_in_str)) 75 { 76 char *backslash = needle_in_str - 1; 77 78 if (haystack != backslash) 79 g_string_append_len (return_str, haystack, backslash - haystack); 80 g_string_append_len (return_str, needle_in_str, needle_in_str - backslash); 81 haystack = needle_in_str + 1; 82 } 83 else 84 { 85 if (needle_in_str != haystack) 86 g_string_append_len (return_str, haystack, needle_in_str - haystack); 87 g_string_append_len (return_str, replacement, replacement_len); 88 haystack = needle_in_str + needle_len; 89 } 90 } 91 92 if (*haystack != '\0') 93 { 94 if (return_str == NULL) 95 return strdup (haystack); 96 97 g_string_append (return_str, haystack); 98 } 99 100 return (return_str != NULL ? g_string_free (return_str, FALSE) : NULL); 101 } 102 103 /* --------------------------------------------------------------------------------------------- */