git/list[1] front-page[2] threads[3] people[4] search[5] about
 

[PATCH 1/6] do not discard const: the simple cases

From
Michael J Gruber <git@grubix.eu>
Date
Mar 26, 2026, 15:22 UTC
Message-ID
<a3a1d2759a0ec5a3ee285689832832e5e3a63768.1774537954.git.git@grubix.eu>
In-Reply-To
<cover.1774537954.git.git@grubix.eu>

Depending on glibc version and compiler flags (ISOC23), strchr() and friends from string.h may return const pointers for const arguments and non-const for non-const (rather than non-const for all argument types). In particular, our current code base gives warnings such as:

```
builtin/config.c: In function 'get_urlmatch':
builtin/config.c:855:22: warning: assignment discards 'const' qualifier from pointer target type [-Wdiscarded-qualifiers]
  855 |         section_tail = strchr(config.section, '.');
      |                      ^
```

Note that with ``` const char *foo; char *bar; ``` we can always assign `foo = bar` but `bar = foo` throws said warning. In particular, we often pass in `char *` for a `const char *` argument and expect `char *` back but get a `const char *` in said scenario.

This patch covers the easy cases where we deal with a non-const pointer
to begin with. It is solved by the cast `bar = (char *) foo`.
---
 builtin/config.c       | 2 +-
 builtin/receive-pack.c | 6 +++---
 http.c                 | 2 +-
 pager.c                | 2 +-
 range-diff.c           | 2 +-
 refs/files-backend.c   | 2 +-
 remote.c               | 2 +-
 send-pack.c            | 6 +++---
 transport-helper.c     | 2 +-
 9 files changed, 13 insertions(+), 13 deletions(-)
diff --git a/builtin/config.c b/builtin/config.c
index 7c4857be62..bd277e5911 100644
--- a/builtin/config.c
+++ b/builtin/config.c
@@ -852,7 +852,7 @@ static int get_urlmatch(const struct config_location_options *opts,
 		die("%s", config.url.err);
 
 	config.section = xstrdup_tolower(var);
-	section_tail = strchr(config.section, '.');
+	section_tail = (char *) strchr(config.section, '.');
 	if (section_tail) {
 		*section_tail = '\0';
 		config.key = section_tail + 1;
diff --git a/builtin/receive-pack.c b/builtin/receive-pack.c
index e34edff406..7712a1c3c2 100644
--- a/builtin/receive-pack.c
+++ b/builtin/receive-pack.c
@@ -1042,7 +1042,7 @@ static int read_proc_receive_report(struct packet_reader *reader,
 		response++;
 
 		head = reader->line;
-		p = strchr(head, ' ');
+		p = (char *) strchr(head, ' ');
 		if (!p) {
 			strbuf_addf(errmsg, "proc-receive reported incomplete status line: '%s'\n", head);
 			code = -1;
@@ -1072,7 +1072,7 @@ static int read_proc_receive_report(struct packet_reader *reader,
 				new_report = 0;
 			}
 			key = p;
-			p = strchr(key, ' ');
+			p = (char *) strchr(key, ' ');
 			if (p)
 				*p++ = '\0';
 			val = p;
@@ -1095,7 +1095,7 @@ static int read_proc_receive_report(struct packet_reader *reader,
 		report = NULL;
 		new_report = 0;
 		refname = p;
-		p = strchr(refname, ' ');
+		p = (char *) strchr(refname, ' ');
 		if (p)
 			*p++ = '\0';
 		if (strcmp(head, "ok") && strcmp(head, "ng")) {
diff --git a/http.c b/http.c
index d8d016891b..02c4fbb234 100644
--- a/http.c
+++ b/http.c
@@ -774,7 +774,7 @@ static int redact_sensitive_header(struct strbuf *header, size_t offset)
 
 		while (cookie) {
 			char *equals;
-			char *semicolon = strstr(cookie, "; ");
+			char *semicolon = (char *) strstr(cookie, "; ");
 			if (semicolon)
 				*semicolon = 0;
 			equals = strchrnul(cookie, '=');
diff --git a/pager.c b/pager.c
index 5531fff50e..eb7011bfde 100644
--- a/pager.c
+++ b/pager.c
@@ -118,7 +118,7 @@ static void setup_pager_env(struct strvec *env)
 			split_cmdline_strerror(n));
 
 	for (i = 0; i < n; i++) {
-		char *cp = strchr(argv[i], '=');
+		char *cp = (char *) strchr(argv[i], '=');
 
 		if (!cp)
 			die("malformed build-time PAGER_ENV");
diff --git a/range-diff.c b/range-diff.c
index 2712a9a107..47e36a391f 100644
--- a/range-diff.c
+++ b/range-diff.c
@@ -106,7 +106,7 @@ static int read_patches(const char *range, struct string_list *list,
 				strbuf_reset(&buf);
 			}
 			CALLOC_ARRAY(util, 1);
-			if (include_merges && (q = strstr(p, " (from ")))
+			if (include_merges && (q = (char *) strstr(p, " (from ")))
 				*q = '\0';
 			if (repo_get_oid(the_repository, p, &util->oid)) {
 				error(_("could not parse commit '%s'"), p);
diff --git a/refs/files-backend.c b/refs/files-backend.c
index 0537a72b2a..71cab7e003 100644
--- a/refs/files-backend.c
+++ b/refs/files-backend.c
@@ -2196,7 +2196,7 @@ static int show_one_reflog_ent(struct files_ref_store *refs,
 	if (!sb->len || sb->buf[sb->len - 1] != '\n' ||
 	    parse_oid_hex_algop(p, &ooid, &p, refs->base.repo->hash_algo) || *p++ != ' ' ||
 	    parse_oid_hex_algop(p, &noid, &p, refs->base.repo->hash_algo) || *p++ != ' ' ||
-	    !(email_end = strchr(p, '>')) ||
+	    !(email_end = (char *) strchr(p, '>')) ||
 	    email_end[1] != ' ' ||
 	    !(timestamp = parse_timestamp(email_end + 2, &message, 10)) ||
 	    !message || message[0] != ' ' ||
diff --git a/remote.c b/remote.c
index 7ca2a6501b..d7a37016b5 100644
--- a/remote.c
+++ b/remote.c
@@ -2861,7 +2861,7 @@ void remote_state_clear(struct remote_state *remote_state)
  */
 static int chop_last_dir(char **remoteurl, int is_relative)
 {
-	char *rfind = find_last_dir_sep(*remoteurl);
+	char *rfind = (char *) find_last_dir_sep(*remoteurl);
 	if (rfind) {
 		*rfind = '\0';
 		return 0;
diff --git a/send-pack.c b/send-pack.c
index 07ecfae4de..8b9f7e2f2f 100644
--- a/send-pack.c
+++ b/send-pack.c
@@ -181,7 +181,7 @@ static int receive_status(struct repository *r,
 		if (packet_reader_read(reader) != PACKET_READ_NORMAL)
 			break;
 		head = reader->line;
-		p = strchr(head, ' ');
+		p = (char *) strchr(head, ' ');
 		if (!p) {
 			error("invalid status line from remote: %s", reader->line);
 			ret = -1;
@@ -212,7 +212,7 @@ static int receive_status(struct repository *r,
 				new_report = 0;
 			}
 			key = p;
-			p = strchr(key, ' ');
+			p = (char *) strchr(key, ' ');
 			if (p)
 				*p++ = '\0';
 			val = p;
@@ -237,7 +237,7 @@ static int receive_status(struct repository *r,
 			break;
 		}
 		refname = p;
-		p = strchr(refname, ' ');
+		p = (char *) strchr(refname, ' ');
 		if (p)
 			*p++ = '\0';
 		/* first try searching at our hint, falling back to all refs */
diff --git a/transport-helper.c b/transport-helper.c
index 4d95d84f9e..e7f2cb1812 100644
--- a/transport-helper.c
+++ b/transport-helper.c
@@ -800,7 +800,7 @@ static int push_update_ref_status(struct strbuf *buf,
 			state->new_report = 0;
 		}
 		key = buf->buf + 7;
-		p = strchr(key, ' ');
+		p = (char *) strchr(key, ' ');
 		if (p)
 			*p++ = '\0';
 		val = p;
-- 
2.53.0.1195.g771ffcb452
Previous: Jeff KingNext: Jeff King
Message 15 of 24 in “ISOC23: quell warnings on discarding const”
  1. 0/6 ISOC23: quell warnings on discarding constMichael J Gruber, Mar 26, 2026
  2. 5/6 do not discard const: keep signatureMichael J Gruber, Mar 26, 2026
  3. Junio C HamanoMar 26, 2026
  4. 6/6 do not discard const: the ugly truthMichael J Gruber, Mar 26, 2026
  5. Junio C HamanoMar 26, 2026
  6. Jeff KingMar 26, 2026
  7. 0/4 fix const issues in revision parserJeff King, Mar 26, 2026
  8. 1/4 revision: make handle_dotdot() interface less confusingJeff King, Mar 26, 2026
  9. Junio C HamanoMar 26, 2026
  10. Jeff KingMar 26, 2026
  11. Junio C HamanoMar 27, 2026
  12. 2/4 rev-parse: simplify dotdot parsingJeff King, Mar 26, 2026
  13. 3/4 revision: avoid writing to const string for parent marksJeff King, Mar 26, 2026
  14. 4/4 rev-parse: avoid writing to const string for parent marksJeff King, Mar 26, 2026
  15. 1/6 do not discard const: the simple casesMichael J Gruber, Mar 26, 2026
  16. Jeff KingMar 26, 2026
  17. Junio C HamanoMar 26, 2026
  18. config: store allocated string in non-const pointerJeff King, Mar 26, 2026
  19. 4/6 do not discard const: declare const where we stay constMichael J Gruber, Mar 26, 2026
  20. 2/6 do not discard const: make git-compat-util ISOC23-likeMichael J Gruber, Mar 26, 2026
  21. 3/6 do not discard const: adjust to non-const data typesMichael J Gruber, Mar 26, 2026
  22. Junio C HamanoMar 26, 2026
  23. D. Ben KnobleMar 26, 2026
  24. Michael J GruberMar 27, 2026

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.