From 201b852c277bdf4bf70a656871d502318bd5b25b Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Tue, 26 Jun 2012 10:48:31 -0400 Subject: [PATCH 1/3] Fix a compilation warning with clang 3.0 In b1ad1a1d0266a20bb we introduced an implicit (but safe) long-to-int shortening that clang didn't like. Warning not in any released version of Tor. --- src/common/util.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/common/util.c b/src/common/util.c index e5b51b9a94..d94dcf2003 100644 --- a/src/common/util.c +++ b/src/common/util.c @@ -3347,7 +3347,7 @@ format_helper_exit_status(unsigned char child_state, int saved_errno, *cur++ = '\n'; *cur++ = '\0'; - res = cur - hex_errno - 1; + res = (int)(cur - hex_errno - 1); goto done; From 9c8ec0aa20cda1787ee27a96e666af84f1081f5b Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Tue, 26 Jun 2012 10:50:37 -0400 Subject: [PATCH 2/3] Add a unit test for environment_variable_names_equal I need this because I'm about to frob that function to stop using strcspn() in order to get rid of a clang warning. --- changes/envvar_test | 2 ++ src/test/test_util.c | 34 ++++++++++++++++++++++++++++++++++ 2 files changed, 36 insertions(+) create mode 100644 changes/envvar_test diff --git a/changes/envvar_test b/changes/envvar_test new file mode 100644 index 0000000000..d76a817078 --- /dev/null +++ b/changes/envvar_test @@ -0,0 +1,2 @@ + o New unit tests: + - Add a unit test for the environment_variable_names_equal function. \ No newline at end of file diff --git a/src/test/test_util.c b/src/test/test_util.c index fab95953bd..d2d0a55520 100644 --- a/src/test/test_util.c +++ b/src/test/test_util.c @@ -2869,6 +2869,39 @@ test_util_sl_new_from_text_lines(void *ptr) } } +static void +test_util_envnames(void *ptr) +{ + (void) ptr; + + tt_assert(environment_variable_names_equal("abc", "abc")); + tt_assert(environment_variable_names_equal("abc", "abc=")); + tt_assert(environment_variable_names_equal("abc", "abc=def")); + tt_assert(environment_variable_names_equal("abc=def", "abc")); + tt_assert(environment_variable_names_equal("abc=def", "abc=ghi")); + + tt_assert(environment_variable_names_equal("abc", "abc")); + tt_assert(environment_variable_names_equal("abc", "abc=")); + tt_assert(environment_variable_names_equal("abc", "abc=def")); + tt_assert(environment_variable_names_equal("abc=def", "abc")); + tt_assert(environment_variable_names_equal("abc=def", "abc=ghi")); + + tt_assert(!environment_variable_names_equal("abc", "abcd")); + tt_assert(!environment_variable_names_equal("abc=", "abcd")); + tt_assert(!environment_variable_names_equal("abc=", "abcd")); + tt_assert(!environment_variable_names_equal("abc=", "def")); + tt_assert(!environment_variable_names_equal("abc=", "def=")); + tt_assert(!environment_variable_names_equal("abc=x", "def=x")); + + tt_assert(!environment_variable_names_equal("", "a=def")); + /* A bit surprising. */ + tt_assert(environment_variable_names_equal("", "=def")); + tt_assert(environment_variable_names_equal("=y", "=x")); + + done: + ; +} + /** Test process_environment_make */ static void test_util_make_environment(void *ptr) @@ -3081,6 +3114,7 @@ struct testcase_t util_tests[] = { UTIL_TEST(n_bits_set, 0), UTIL_TEST(eat_whitespace, 0), UTIL_TEST(sl_new_from_text_lines, 0), + UTIL_TEST(envnames, 0), UTIL_TEST(make_environment, 0), UTIL_TEST(set_env_var_in_sl, 0), END_OF_TESTCASES From 5fad3dc36b3aad7f2ea13e56d838c3eb37fb029d Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Tue, 26 Jun 2012 10:55:23 -0400 Subject: [PATCH 3/3] Fix a warning when using glibc's strcspn with clang. With glibc 2.15 and clang 3.0, I get warnings from where we use the strcpsn implementation in the header as strcspn(string, "="). This is apparently because clang sees that part of the strcspn macro expands to "="[2], and doesn't realize that that part of the macro is only evaluated when "="[1] != 0. --- changes/clang_strcspn | 3 +++ src/common/util.c | 19 ++++++++++++++++--- 2 files changed, 19 insertions(+), 3 deletions(-) create mode 100644 changes/clang_strcspn diff --git a/changes/clang_strcspn b/changes/clang_strcspn new file mode 100644 index 0000000000..38670ac376 --- /dev/null +++ b/changes/clang_strcspn @@ -0,0 +1,3 @@ + o Minor bugfixes: + - Avoid a warning caused by using strcspn from glibc with clang 3.0. + Bugfix on 0.2.3.13-alpha. diff --git a/src/common/util.c b/src/common/util.c index d94dcf2003..51d932146d 100644 --- a/src/common/util.c +++ b/src/common/util.c @@ -3887,13 +3887,26 @@ tor_get_exit_code(const process_handle_t *process_handle, return PROCESS_EXIT_EXITED; } +/** Helper: return the number of characters in s preceding the first + * occurence of ch. If ch does not occur in s, return + * the length of s. Should be equivalent to strspn(s, "ch"). */ +static INLINE size_t +str_num_before(const char *s, char ch) +{ + const char *cp = strchr(s, ch); + if (cp) + return cp - s; + else + return strlen(s); +} + /** Return non-zero iff getenv would consider s1 and s2 * to have the same name as strings in a process's environment. */ int environment_variable_names_equal(const char *s1, const char *s2) { - size_t s1_name_len = strcspn(s1, "="); - size_t s2_name_len = strcspn(s2, "="); + size_t s1_name_len = str_num_before(s1, '='); + size_t s2_name_len = str_num_before(s2, '='); return (s1_name_len == s2_name_len && tor_memeq(s1, s2, s1_name_len)); @@ -3968,7 +3981,7 @@ process_environment_make(struct smartlist_t *env_vars) for (i = 0; i < n_env_vars; ++i) { const char *s = smartlist_get(env_vars_sorted, i); size_t slen = strlen(s); - size_t s_name_len = strcspn(s, "="); + size_t s_name_len = str_num_before(s, '='); if (s_name_len == slen) { log_warn(LD_GENERAL,