{"thread":{"id":"36139","subject":"[PATCH] general style: replaces memcmp() with starts_with()","startedAt":"2014-03-12T13:44:14Z","lastAt":"2014-03-14T16:32:05Z","messageCount":10,"participants":["Quint Guvernator","Duy Nguyen","Jens Lehmann","Jeff King","Michael Haggerty"],"isPatch":true,"patchVersion":1,"patchTotal":null},"messages":[{"id":"236576","messageId":"1394631854-11208-1-git-send-email-quintus.public@gmail.com","threadId":"36139","inReplyTo":null,"subject":"[PATCH] general style: replaces memcmp() with starts_with()","fromName":"Quint Guvernator","fromEmail":"quintus.public@gmail.com","sentAt":"2014-03-12T13:44:14Z","receivedAt":"2014-03-12T13:44:14Z","isPatch":true,"sender":{"key":"quintus.public@gmail.com","avatar":"https://gravatar.com/avatar/0805695585d6191e00badd5057b262b501047d9fb2b22dd2495009ffb25d85fd?d=mp&s=160"},"body":"memcmp() is replaced with starts_with() when comparing strings from the\nbeginning. starts_with() looks nicer and it saves the extra argument of\nthe length of the comparing string.\n\nSigned-off-by: Quint Guvernator <quintus.public@gmail.com>\n---\n builtin/apply.c                           | 10 +++++-----\n builtin/cat-file.c                        |  2 +-\n builtin/commit-tree.c                     |  2 +-\n builtin/for-each-ref.c                    |  2 +-\n builtin/get-tar-commit-id.c               |  2 +-\n builtin/mailinfo.c                        | 10 +++++-----\n builtin/mktag.c                           |  8 ++++----\n builtin/patch-id.c                        | 18 +++++++++---------\n commit.c                                  | 18 +++++++++---------\n connect.c                                 |  8 ++++----\n contrib/convert-objects/convert-objects.c |  6 +++---\n convert.c                                 |  2 +-\n credential-cache.c                        |  2 +-\n fetch-pack.c                              |  2 +-\n fsck.c                                    |  8 ++++----\n http-walker.c                             |  4 ++--\n imap-send.c                               |  2 +-\n pack-write.c                              |  2 +-\n path.c                                    |  2 +-\n refs.c                                    |  2 +-\n remote.c                                  |  2 +-\n submodule.c                               |  2 +-\n transport.c                               |  2 +-\n xdiff-interface.c                         |  2 +-\n 24 files changed, 60 insertions(+), 60 deletions(-)\n\ndiff --git a/builtin/apply.c b/builtin/apply.c\nindex a7e72d5..8f21957 100644\n--- a/builtin/apply.c\n+++ b/builtin/apply.c\n@@ -846,8 +846,8 @@ static int has_epoch_timestamp(const char *nameline)\n \t * YYYY-MM-DD hh:mm:ss must be from either 1969-12-31\n \t * (west of GMT) or 1970-01-01 (east of GMT)\n \t */\n-\tif ((zoneoffset < 0 && memcmp(timestamp, \"1969-12-31\", 10)) ||\n-\t    (0 <= zoneoffset && memcmp(timestamp, \"1970-01-01\", 10)))\n+\tif ((zoneoffset < 0 && starts_with(timestamp, \"1969-12-31\")) ||\n+\t    (0 <= zoneoffset && starts_with(timestamp, \"1970-01-01\")))\n \t\treturn 0;\n \n \thourminute = (strtol(timestamp + 11, NULL, 10) * 60 +\n@@ -1631,7 +1631,7 @@ static int parse_fragment(const char *line, unsigned long size,\n \t\t * l10n of \"\\ No newline...\" is at least that long.\n \t\t */\n \t\tcase '\\\\':\n-\t\t\tif (len < 12 || memcmp(line, \"\\\\ \", 2))\n+\t\t\tif (len < 12 || starts_with(line, \"\\\\ \"))\n \t\t\t\treturn -1;\n \t\t\tbreak;\n \t\t}\n@@ -1646,7 +1646,7 @@ static int parse_fragment(const char *line, unsigned long size,\n \t * it in the above loop because we hit oldlines == newlines == 0\n \t * before seeing it.\n \t */\n-\tif (12 < size && !memcmp(line, \"\\\\ \", 2))\n+\tif (12 < size && !starts_with(line, \"\\\\ \"))\n \t\toffset += linelen(line, size);\n \n \tpatch->lines_added += added;\n@@ -1673,7 +1673,7 @@ static int parse_single_patch(const char *line, unsigned long size, struct patch\n \tunsigned long oldlines = 0, newlines = 0, context = 0;\n \tstruct fragment **fragp = &patch->fragments;\n \n-\twhile (size > 4 && !memcmp(line, \"@@ -\", 4)) {\n+\twhile (size > 4 && !starts_with(line, \"@@ -\")) {\n \t\tstruct fragment *fragment;\n \t\tint len;\n \ndiff --git a/builtin/cat-file.c b/builtin/cat-file.c\nindex d5a93e0..be83345 100644\n--- a/builtin/cat-file.c\n+++ b/builtin/cat-file.c\n@@ -82,7 +82,7 @@ static int cat_one_file(int opt, const char *exp_type, const char *obj_name)\n \t\t\t\tenum object_type type;\n \t\t\t\tunsigned long size;\n \t\t\t\tchar *buffer = read_sha1_file(sha1, &type, &size);\n-\t\t\t\tif (memcmp(buffer, \"object \", 7) ||\n+\t\t\t\tif (starts_with(buffer, \"object \") ||\n \t\t\t\t    get_sha1_hex(buffer + 7, blob_sha1))\n \t\t\t\t\tdie(\"%s not a valid tag\", sha1_to_hex(sha1));\n \t\t\t\tfree(buffer);\ndiff --git a/builtin/commit-tree.c b/builtin/commit-tree.c\nindex 987a4c3..2d995a2 100644\n--- a/builtin/commit-tree.c\n+++ b/builtin/commit-tree.c\n@@ -66,7 +66,7 @@ int cmd_commit_tree(int argc, const char **argv, const char *prefix)\n \t\t\tcontinue;\n \t\t}\n \n-\t\tif (!memcmp(arg, \"-S\", 2)) {\n+\t\tif (!starts_with(arg, \"-S\")) {\n \t\t\tsign_commit = arg + 2;\n \t\t\tcontinue;\n \t\t}\ndiff --git a/builtin/for-each-ref.c b/builtin/for-each-ref.c\nindex 51798b4..be14d71 100644\n--- a/builtin/for-each-ref.c\n+++ b/builtin/for-each-ref.c\n@@ -193,7 +193,7 @@ static int verify_format(const char *format)\n \t\tat = parse_atom(sp + 2, ep);\n \t\tcp = ep + 1;\n \n-\t\tif (!memcmp(used_atom[at], \"color:\", 6))\n+\t\tif (!starts_with(used_atom[at], \"color:\"))\n \t\t\tneed_color_reset_at_eol = !!strcmp(used_atom[at], color_reset);\n \t}\n \treturn 0;\ndiff --git a/builtin/get-tar-commit-id.c b/builtin/get-tar-commit-id.c\nindex aa72596..d645525 100644\n--- a/builtin/get-tar-commit-id.c\n+++ b/builtin/get-tar-commit-id.c\n@@ -29,7 +29,7 @@ int cmd_get_tar_commit_id(int argc, const char **argv, const char *prefix)\n \t\tdie(\"git get-tar-commit-id: read error\");\n \tif (header->typeflag[0] != 'g')\n \t\treturn 1;\n-\tif (memcmp(content, \"52 comment=\", 11))\n+\tif (starts_with(content, \"52 comment=\"))\n \t\treturn 1;\n \n \tn = write_in_full(1, content + 11, 41);\ndiff --git a/builtin/mailinfo.c b/builtin/mailinfo.c\nindex 2c3cd8e..63f0230 100644\n--- a/builtin/mailinfo.c\n+++ b/builtin/mailinfo.c\n@@ -626,7 +626,7 @@ static int handle_boundary(void)\n \tstrbuf_addch(&newline, '\\n');\n again:\n \tif (line.len >= (*content_top)->len + 2 &&\n-\t    !memcmp(line.buf + (*content_top)->len, \"--\", 2)) {\n+\t    !starts_with(line.buf + (*content_top)->len, \"--\")) {\n \t\t/* we hit an end boundary */\n \t\t/* pop the current boundary off the stack */\n \t\tstrbuf_release(*content_top);\n@@ -727,8 +727,8 @@ static int is_scissors_line(const struct strbuf *line)\n \t\t\tcontinue;\n \t\t}\n \t\tif (i + 1 < len &&\n-\t\t    (!memcmp(buf + i, \">8\", 2) || !memcmp(buf + i, \"8<\", 2) ||\n-\t\t     !memcmp(buf + i, \">%\", 2) || !memcmp(buf + i, \"%<\", 2))) {\n+\t\t    (!starts_with(buf + i, \">8\") || !starts_with(buf + i, \"8<\") ||\n+\t\t     !starts_with(buf + i, \">%\") || !starts_with(buf + i, \"%<\"))) {\n \t\t\tin_perforation = 1;\n \t\t\tperforation += 2;\n \t\t\tscissors += 2;\n@@ -929,13 +929,13 @@ static void handle_info(void)\n \t\telse\n \t\t\tcontinue;\n \n-\t\tif (!memcmp(header[i], \"Subject\", 7)) {\n+\t\tif (!starts_with(header[i], \"Subject\")) {\n \t\t\tif (!keep_subject) {\n \t\t\t\tcleanup_subject(hdr);\n \t\t\t\tcleanup_space(hdr);\n \t\t\t}\n \t\t\toutput_header_lines(fout, \"Subject\", hdr);\n-\t\t} else if (!memcmp(header[i], \"From\", 4)) {\n+\t\t} else if (!starts_with(header[i], \"From\")) {\n \t\t\tcleanup_space(hdr);\n \t\t\thandle_from(hdr);\n \t\t\tfprintf(fout, \"Author: %s\\n\", name.buf);\ndiff --git a/builtin/mktag.c b/builtin/mktag.c\nindex 640ab64..54ec4e1 100644\n--- a/builtin/mktag.c\n+++ b/builtin/mktag.c\n@@ -49,7 +49,7 @@ static int verify_tag(char *buffer, unsigned long size)\n \n \t/* Verify object line */\n \tobject = buffer;\n-\tif (memcmp(object, \"object \", 7))\n+\tif (starts_with(object, \"object \"))\n \t\treturn error(\"char%d: does not start with \\\"object \\\"\", 0);\n \n \tif (get_sha1_hex(object + 7, sha1))\n@@ -57,7 +57,7 @@ static int verify_tag(char *buffer, unsigned long size)\n \n \t/* Verify type line */\n \ttype_line = object + 48;\n-\tif (memcmp(type_line - 1, \"\\ntype \", 6))\n+\tif (starts_with(type_line - 1, \"\\ntype \"))\n \t\treturn error(\"char%d: could not find \\\"\\\\ntype \\\"\", 47);\n \n \t/* Verify tag-line */\n@@ -66,7 +66,7 @@ static int verify_tag(char *buffer, unsigned long size)\n \t\treturn error(\"char%\"PRIuMAX\": could not find next \\\"\\\\n\\\"\",\n \t\t\t\t(uintmax_t) (type_line - buffer));\n \ttag_line++;\n-\tif (memcmp(tag_line, \"tag \", 4) || tag_line[4] == '\\n')\n+\tif (starts_with(tag_line, \"tag \") || tag_line[4] == '\\n')\n \t\treturn error(\"char%\"PRIuMAX\": no \\\"tag \\\" found\",\n \t\t\t\t(uintmax_t) (tag_line - buffer));\n \n@@ -98,7 +98,7 @@ static int verify_tag(char *buffer, unsigned long size)\n \t/* Verify the tagger line */\n \ttagger_line = tag_line;\n \n-\tif (memcmp(tagger_line, \"tagger \", 7))\n+\tif (starts_with(tagger_line, \"tagger \"))\n \t\treturn error(\"char%\"PRIuMAX\": could not find \\\"tagger \\\"\",\n \t\t\t(uintmax_t) (tagger_line - buffer));\n \ndiff --git a/builtin/patch-id.c b/builtin/patch-id.c\nindex 3cfe02d..cc10f1d 100644\n--- a/builtin/patch-id.c\n+++ b/builtin/patch-id.c\n@@ -66,13 +66,13 @@ static int get_one_patchid(unsigned char *next_sha1, git_SHA_CTX *ctx, struct st\n \t\tchar *p = line;\n \t\tint len;\n \n-\t\tif (!memcmp(line, \"diff-tree \", 10))\n+\t\tif (!starts_with(line, \"diff-tree \"))\n \t\t\tp += 10;\n-\t\telse if (!memcmp(line, \"commit \", 7))\n+\t\telse if (!starts_with(line, \"commit \"))\n \t\t\tp += 7;\n-\t\telse if (!memcmp(line, \"From \", 5))\n+\t\telse if (!starts_with(line, \"From \"))\n \t\t\tp += 5;\n-\t\telse if (!memcmp(line, \"\\\\ \", 2) && 12 < strlen(line))\n+\t\telse if (!starts_with(line, \"\\\\ \") && 12 < strlen(line))\n \t\t\tcontinue;\n \n \t\tif (!get_sha1_hex(p, next_sha1)) {\n@@ -81,14 +81,14 @@ static int get_one_patchid(unsigned char *next_sha1, git_SHA_CTX *ctx, struct st\n \t\t}\n \n \t\t/* Ignore commit comments */\n-\t\tif (!patchlen && memcmp(line, \"diff \", 5))\n+\t\tif (!patchlen && starts_with(line, \"diff \"))\n \t\t\tcontinue;\n \n \t\t/* Parsing diff header?  */\n \t\tif (before == -1) {\n-\t\t\tif (!memcmp(line, \"index \", 6))\n+\t\t\tif (!starts_with(line, \"index \"))\n \t\t\t\tcontinue;\n-\t\t\telse if (!memcmp(line, \"--- \", 4))\n+\t\t\telse if (!starts_with(line, \"--- \"))\n \t\t\t\tbefore = after = 1;\n \t\t\telse if (!isalpha(line[0]))\n \t\t\t\tbreak;\n@@ -96,14 +96,14 @@ static int get_one_patchid(unsigned char *next_sha1, git_SHA_CTX *ctx, struct st\n \n \t\t/* Looking for a valid hunk header?  */\n \t\tif (before == 0 && after == 0) {\n-\t\t\tif (!memcmp(line, \"@@ -\", 4)) {\n+\t\t\tif (!starts_with(line, \"@@ -\")) {\n \t\t\t\t/* Parse next hunk, but ignore line numbers.  */\n \t\t\t\tscan_hunk_header(line, &before, &after);\n \t\t\t\tcontinue;\n \t\t\t}\n \n \t\t\t/* Split at the end of the patch.  */\n-\t\t\tif (memcmp(line, \"diff \", 5))\n+\t\t\tif (starts_with(line, \"diff \"))\n \t\t\t\tbreak;\n \n \t\t\t/* Else we're parsing another header.  */\ndiff --git a/commit.c b/commit.c\nindex 6bf4fe0..b259c17 100644\n--- a/commit.c\n+++ b/commit.c\n@@ -90,13 +90,13 @@ static unsigned long parse_commit_date(const char *buf, const char *tail)\n \n \tif (buf + 6 >= tail)\n \t\treturn 0;\n-\tif (memcmp(buf, \"author\", 6))\n+\tif (starts_with(buf, \"author\"))\n \t\treturn 0;\n \twhile (buf < tail && *buf++ != '\\n')\n \t\t/* nada */;\n \tif (buf + 9 >= tail)\n \t\treturn 0;\n-\tif (memcmp(buf, \"committer\", 9))\n+\tif (starts_with(buf, \"committer\"))\n \t\treturn 0;\n \twhile (buf < tail && *buf++ != '>')\n \t\t/* nada */;\n@@ -269,7 +269,7 @@ int parse_commit_buffer(struct commit *item, const void *buffer, unsigned long s\n \t\treturn 0;\n \titem->object.parsed = 1;\n \ttail += size;\n-\tif (tail <= bufptr + 46 || memcmp(bufptr, \"tree \", 5) || bufptr[45] != '\\n')\n+\tif (tail <= bufptr + 46 || starts_with(bufptr, \"tree \") || bufptr[45] != '\\n')\n \t\treturn error(\"bogus commit object %s\", sha1_to_hex(item->object.sha1));\n \tif (get_sha1_hex(bufptr + 5, parent) < 0)\n \t\treturn error(\"bad tree pointer in commit %s\",\n@@ -279,7 +279,7 @@ int parse_commit_buffer(struct commit *item, const void *buffer, unsigned long s\n \tpptr = &item->parents;\n \n \tgraft = lookup_commit_graft(item->object.sha1);\n-\twhile (bufptr + 48 < tail && !memcmp(bufptr, \"parent \", 7)) {\n+\twhile (bufptr + 48 < tail && !starts_with(bufptr, \"parent \")) {\n \t\tstruct commit *new_parent;\n \n \t\tif (tail <= bufptr + 48 ||\n@@ -1279,11 +1279,11 @@ struct commit_extra_header *read_commit_extra_headers(struct commit *commit,\n \n static inline int standard_header_field(const char *field, size_t len)\n {\n-\treturn ((len == 4 && !memcmp(field, \"tree \", 5)) ||\n-\t\t(len == 6 && !memcmp(field, \"parent \", 7)) ||\n-\t\t(len == 6 && !memcmp(field, \"author \", 7)) ||\n-\t\t(len == 9 && !memcmp(field, \"committer \", 10)) ||\n-\t\t(len == 8 && !memcmp(field, \"encoding \", 9)));\n+\treturn ((len == 4 && !starts_with(field, \"tree \")) ||\n+\t\t(len == 6 && !starts_with(field, \"parent \")) ||\n+\t\t(len == 6 && !starts_with(field, \"author \")) ||\n+\t\t(len == 9 && !starts_with(field, \"committer \")) ||\n+\t\t(len == 8 && !starts_with(field, \"encoding \")));\n }\n \n static int excluded_header_field(const char *field, size_t len, const char **exclude)\ndiff --git a/connect.c b/connect.c\nindex 4150412..4cb1c7c 100644\n--- a/connect.c\n+++ b/connect.c\n@@ -18,7 +18,7 @@ static int check_ref(const char *name, int len, unsigned int flags)\n \tif (!flags)\n \t\treturn 1;\n \n-\tif (len < 5 || memcmp(name, \"refs/\", 5))\n+\tif (len < 5 || starts_with(name, \"refs/\"))\n \t\treturn 0;\n \n \t/* Skip the \"refs/\" part */\n@@ -30,11 +30,11 @@ static int check_ref(const char *name, int len, unsigned int flags)\n \t\treturn 0;\n \n \t/* REF_HEADS means that we want regular branch heads */\n-\tif ((flags & REF_HEADS) && !memcmp(name, \"heads/\", 6))\n+\tif ((flags & REF_HEADS) && !starts_with(name, \"heads/\"))\n \t\treturn 1;\n \n \t/* REF_TAGS means that we want tags */\n-\tif ((flags & REF_TAGS) && !memcmp(name, \"tags/\", 5))\n+\tif ((flags & REF_TAGS) && !starts_with(name, \"tags/\"))\n \t\treturn 1;\n \n \t/* All type bits clear means that we are ok with anything */\n@@ -514,7 +514,7 @@ static int git_proxy_command_options(const char *var, const char *value,\n \t\tif (0 <= matchlen) {\n \t\t\t/* core.gitproxy = none for kernel.org */\n \t\t\tif (matchlen == 4 &&\n-\t\t\t    !memcmp(value, \"none\", 4))\n+\t\t\t    !starts_with(value, \"none\"))\n \t\t\t\tmatchlen = 0;\n \t\t\tgit_proxy_command = xmemdupz(value, matchlen);\n \t\t}\ndiff --git a/contrib/convert-objects/convert-objects.c b/contrib/convert-objects/convert-objects.c\nindex f3b57bf..72914e1 100644\n--- a/contrib/convert-objects/convert-objects.c\n+++ b/contrib/convert-objects/convert-objects.c\n@@ -245,7 +245,7 @@ static void convert_date(void *buffer, unsigned long size, unsigned char *result\n \tsize -= 46;\n \n \t/* \"parent <sha1>\\n\" */\n-\twhile (!memcmp(buffer, \"parent \", 7)) {\n+\twhile (!starts_with(buffer, \"parent \")) {\n \t\tmemcpy(new + newlen, buffer, 48);\n \t\tnewlen += 48;\n \t\tbuffer = (char *) buffer + 48;\n@@ -270,11 +270,11 @@ static void convert_commit(void *buffer, unsigned long size, unsigned char *resu\n \tvoid *orig_buffer = buffer;\n \tunsigned long orig_size = size;\n \n-\tif (memcmp(buffer, \"tree \", 5))\n+\tif (starts_with(buffer, \"tree \"))\n \t\tdie(\"Bad commit '%s'\", (char *) buffer);\n \tconvert_ascii_sha1((char *) buffer + 5);\n \tbuffer = (char *) buffer + 46;    /* \"tree \" + \"hex sha1\" + \"\\n\" */\n-\twhile (!memcmp(buffer, \"parent \", 7)) {\n+\twhile (!starts_with(buffer, \"parent \")) {\n \t\tconvert_ascii_sha1((char *) buffer + 7);\n \t\tbuffer = (char *) buffer + 48;\n \t}\ndiff --git a/convert.c b/convert.c\nindex ab80b72..8f0b1bd 100644\n--- a/convert.c\n+++ b/convert.c\n@@ -543,7 +543,7 @@ static int ident_to_git(const char *path, const char *src, size_t len,\n \t\tlen -= dollar + 1 - src;\n \t\tsrc  = dollar + 1;\n \n-\t\tif (len > 3 && !memcmp(src, \"Id:\", 3)) {\n+\t\tif (len > 3 && !starts_with(src, \"Id:\")) {\n \t\t\tdollar = memchr(src + 3, '$', len - 3);\n \t\t\tif (!dollar)\n \t\t\t\tbreak;\ndiff --git a/credential-cache.c b/credential-cache.c\nindex 9a03792..0b55946 100644\n--- a/credential-cache.c\n+++ b/credential-cache.c\n@@ -54,7 +54,7 @@ static void spawn_daemon(const char *socket)\n \tr = read_in_full(daemon.out, buf, sizeof(buf));\n \tif (r < 0)\n \t\tdie_errno(\"unable to read result code from cache daemon\");\n-\tif (r != 3 || memcmp(buf, \"ok\\n\", 3))\n+\tif (r != 3 || starts_with(buf, \"ok\\n\"))\n \t\tdie(\"cache daemon did not start: %.*s\", r, buf);\n \tclose(daemon.out);\n }\ndiff --git a/fetch-pack.c b/fetch-pack.c\nindex f061f1f..10abe9e 100644\n--- a/fetch-pack.c\n+++ b/fetch-pack.c\n@@ -506,7 +506,7 @@ static void filter_refs(struct fetch_pack_args *args,\n \t\tint keep = 0;\n \t\tnext = ref->next;\n \n-\t\tif (!memcmp(ref->name, \"refs/\", 5) &&\n+\t\tif (!starts_with(ref->name, \"refs/\") &&\n \t\t    check_refname_format(ref->name, 0))\n \t\t\t; /* trash */\n \t\telse {\ndiff --git a/fsck.c b/fsck.c\nindex 99c0497..10b70ca 100644\n--- a/fsck.c\n+++ b/fsck.c\n@@ -290,12 +290,12 @@ static int fsck_commit(struct commit *commit, fsck_error error_func)\n \tif (commit->date == ULONG_MAX)\n \t\treturn error_func(&commit->object, FSCK_ERROR, \"invalid author/committer line\");\n \n-\tif (memcmp(buffer, \"tree \", 5))\n+\tif (starts_with(buffer, \"tree \"))\n \t\treturn error_func(&commit->object, FSCK_ERROR, \"invalid format - expected 'tree' line\");\n \tif (get_sha1_hex(buffer+5, tree_sha1) || buffer[45] != '\\n')\n \t\treturn error_func(&commit->object, FSCK_ERROR, \"invalid 'tree' line format - bad sha1\");\n \tbuffer += 46;\n-\twhile (!memcmp(buffer, \"parent \", 7)) {\n+\twhile (!starts_with(buffer, \"parent \")) {\n \t\tif (get_sha1_hex(buffer+7, sha1) || buffer[47] != '\\n')\n \t\t\treturn error_func(&commit->object, FSCK_ERROR, \"invalid 'parent' line format - bad sha1\");\n \t\tbuffer += 48;\n@@ -322,13 +322,13 @@ static int fsck_commit(struct commit *commit, fsck_error error_func)\n \t\tif (p || parents)\n \t\t\treturn error_func(&commit->object, FSCK_ERROR, \"parent objects missing\");\n \t}\n-\tif (memcmp(buffer, \"author \", 7))\n+\tif (starts_with(buffer, \"author \"))\n \t\treturn error_func(&commit->object, FSCK_ERROR, \"invalid format - expected 'author' line\");\n \tbuffer += 7;\n \terr = fsck_ident(&buffer, &commit->object, error_func);\n \tif (err)\n \t\treturn err;\n-\tif (memcmp(buffer, \"committer \", strlen(\"committer \")))\n+\tif (starts_with(buffer, \"committer \"))\n \t\treturn error_func(&commit->object, FSCK_ERROR, \"invalid format - expected 'committer' line\");\n \tbuffer += strlen(\"committer \");\n \terr = fsck_ident(&buffer, &commit->object, error_func);\ndiff --git a/http-walker.c b/http-walker.c\nindex 1516c5e..9ffe05e 100644\n--- a/http-walker.c\n+++ b/http-walker.c\n@@ -245,7 +245,7 @@ static void process_alternates_response(void *callback_data)\n \t\t\t\t\t\t     - base);\n \t\t\t\t\tokay = 1;\n \t\t\t\t}\n-\t\t\t} else if (!memcmp(data + i, \"../\", 3)) {\n+\t\t\t} else if (!starts_with(data + i, \"../\")) {\n \t\t\t\t/*\n \t\t\t\t * Relative URL; chop the corresponding\n \t\t\t\t * number of subpath from base (and ../\n@@ -267,7 +267,7 @@ static void process_alternates_response(void *callback_data)\n \t\t\t\ti += 3;\n \t\t\t\tserverlen = strlen(base);\n \t\t\t\twhile (i + 2 < posn &&\n-\t\t\t\t       !memcmp(data + i, \"../\", 3)) {\n+\t\t\t\t       !starts_with(data + i, \"../\")) {\n \t\t\t\t\tdo {\n \t\t\t\t\t\tserverlen--;\n \t\t\t\t\t} while (serverlen &&\ndiff --git a/imap-send.c b/imap-send.c\nindex 0bc6f7f..334b425 100644\n--- a/imap-send.c\n+++ b/imap-send.c\n@@ -802,7 +802,7 @@ static int get_cmd_result(struct imap_store *ctx, struct imap_cmd *tcmd)\n \t\t\t\tresp = DRV_OK;\n \t\t\telse {\n \t\t\t\tif (!strcmp(\"NO\", arg)) {\n-\t\t\t\t\tif (cmdp->cb.create && cmd && (cmdp->cb.trycreate || !memcmp(cmd, \"[TRYCREATE]\", 11))) { /* SELECT, APPEND or UID COPY */\n+\t\t\t\t\tif (cmdp->cb.create && cmd && (cmdp->cb.trycreate || !starts_with(cmd, \"[TRYCREATE]\"))) { /* SELECT, APPEND or UID COPY */\n \t\t\t\t\t\tp = strchr(cmdp->cmd, '\"');\n \t\t\t\t\t\tif (!issue_imap_cmd(ctx, NULL, \"CREATE \\\"%.*s\\\"\", (int)(strchr(p + 1, '\"') - p + 1), p)) {\n \t\t\t\t\t\t\tresp = RESP_BAD;\ndiff --git a/pack-write.c b/pack-write.c\nindex 9b8308b..6f58024 100644\n--- a/pack-write.c\n+++ b/pack-write.c\n@@ -289,7 +289,7 @@ char *index_pack_lockfile(int ip_out)\n \t * later on.  If we don't get that then tough luck with it.\n \t */\n \tif (read_in_full(ip_out, packname, 46) == 46 && packname[45] == '\\n' &&\n-\t    memcmp(packname, \"keep\\t\", 5) == 0) {\n+\t    starts_with(packname, \"keep\\t\") == 0) {\n \t\tchar path[PATH_MAX];\n \t\tpackname[45] = 0;\n \t\tsnprintf(path, sizeof(path), \"%s/pack/pack-%s.keep\",\ndiff --git a/path.c b/path.c\nindex f9c5062..23f8437 100644\n--- a/path.c\n+++ b/path.c\n@@ -26,7 +26,7 @@ static char *get_pathname(void)\n static char *cleanup_path(char *path)\n {\n \t/* Clean it up */\n-\tif (!memcmp(path, \"./\", 2)) {\n+\tif (!starts_with(path, \"./\")) {\n \t\tpath += 2;\n \t\twhile (*path == '/')\n \t\t\tpath++;\ndiff --git a/refs.c b/refs.c\nindex 89228e2..b5a14e3 100644\n--- a/refs.c\n+++ b/refs.c\n@@ -63,7 +63,7 @@ static int check_refname_component(const char *refname, int flags)\n \t\tif (refname[1] == '\\0')\n \t\t\treturn -1; /* Component equals \".\". */\n \t}\n-\tif (cp - refname >= 5 && !memcmp(cp - 5, \".lock\", 5))\n+\tif (cp - refname >= 5 && !starts_with(cp - 5, \".lock\"))\n \t\treturn -1; /* Refname ends with \".lock\". */\n \treturn cp - refname;\n }\ndiff --git a/remote.c b/remote.c\nindex e41251e..0b8986a 100644\n--- a/remote.c\n+++ b/remote.c\n@@ -1144,7 +1144,7 @@ static int match_explicit(struct ref *src, struct ref *dst,\n \tcase 1:\n \t\tbreak;\n \tcase 0:\n-\t\tif (!memcmp(dst_value, \"refs/\", 5))\n+\t\tif (!starts_with(dst_value, \"refs/\"))\n \t\t\tmatched_dst = make_linked_ref(dst_value, dst_tail);\n \t\telse if (is_null_sha1(matched_src->new_sha1))\n \t\t\terror(\"unable to delete '%s': remote ref does not exist\",\ndiff --git a/submodule.c b/submodule.c\nindex b80ecac..1edebc1 100644\n--- a/submodule.c\n+++ b/submodule.c\n@@ -203,7 +203,7 @@ void gitmodules_config(void)\n \t\t\tif (active_nr > pos) {  /* there is a .gitmodules */\n \t\t\t\tconst struct cache_entry *ce = active_cache[pos];\n \t\t\t\tif (ce_namelen(ce) == 11 &&\n-\t\t\t\t    !memcmp(ce->name, \".gitmodules\", 11))\n+\t\t\t\t    !starts_with(ce->name, \".gitmodules\"))\n \t\t\t\t\tgitmodules_is_unmerged = 1;\n \t\t\t}\n \t\t} else if (pos < active_nr) {\ndiff --git a/transport.c b/transport.c\nindex ca7bb44..c4b3ac9 100644\n--- a/transport.c\n+++ b/transport.c\n@@ -1364,7 +1364,7 @@ static int refs_from_alternate_cb(struct alternate_object_database *e,\n \n \twhile (other[len-1] == '/')\n \t\tother[--len] = '\\0';\n-\tif (len < 8 || memcmp(other + len - 8, \"/objects\", 8))\n+\tif (len < 8 || starts_with(other + len - 8, \"/objects\"))\n \t\treturn 0;\n \t/* Is this a git repository with refs? */\n \tmemcpy(other + len - 8, \"/refs\", 6);\ndiff --git a/xdiff-interface.c b/xdiff-interface.c\nindex ecfa05f..4be401d 100644\n--- a/xdiff-interface.c\n+++ b/xdiff-interface.c\n@@ -53,7 +53,7 @@ int parse_hunk_header(char *line, int len,\n \t}\n \telse\n \t\t*nn = 1;\n-\treturn -!!memcmp(cp, \" @@\", 3);\n+\treturn -!!starts_with(cp, \" @@\");\n }\n \n static void consume_one(void *priv_, char *s, unsigned long size)\n-- \n1.9.0\n"},{"id":"236577","messageId":"CACsJy8DUhqn_ESzT-KpAdrWvWcLbPUiXDmBZXu7UtHU+M0GLgw@mail.gmail.com","threadId":"36139","inReplyTo":"1394631854-11208-1-git-send-email-quintus.public@gmail.com","subject":"Re: [PATCH] general style: replaces memcmp() with starts_with()","fromName":"Duy Nguyen","fromEmail":"pclouds@gmail.com","sentAt":"2014-03-12T13:51:37Z","receivedAt":"2014-03-12T13:51:37Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"On Wed, Mar 12, 2014 at 8:44 PM, Quint Guvernator\n<quintus.public@gmail.com> wrote:\n> diff --git a/builtin/apply.c b/builtin/apply.c\n> index a7e72d5..8f21957 100644\n> --- a/builtin/apply.c\n> +++ b/builtin/apply.c\n> @@ -846,8 +846,8 @@ static int has_epoch_timestamp(const char *nameline)\n>          * YYYY-MM-DD hh:mm:ss must be from either 1969-12-31\n>          * (west of GMT) or 1970-01-01 (east of GMT)\n>          */\n> -       if ((zoneoffset < 0 && memcmp(timestamp, \"1969-12-31\", 10)) ||\n> -           (0 <= zoneoffset && memcmp(timestamp, \"1970-01-01\", 10)))\n> +       if ((zoneoffset < 0 && starts_with(timestamp, \"1969-12-31\")) ||\n> +           (0 <= zoneoffset && starts_with(timestamp, \"1970-01-01\")))\n>                 return 0;\n\nIt is not a plain search/replace. starts_with(..) == !memcmp(...). So\nyou need to negate every replacement.\n-- \nDuy\n"},{"id":"236578","messageId":"CALs4jVFM58Yiku4B8NrVeac0Hmt5YsPNYb_EjY6bOr=JO6pP+A@mail.gmail.com","threadId":"36139","inReplyTo":"CACsJy8DUhqn_ESzT-KpAdrWvWcLbPUiXDmBZXu7UtHU+M0GLgw@mail.gmail.com","subject":"Re: [PATCH] general style: replaces memcmp() with starts_with()","fromName":"Quint Guvernator","fromEmail":"quintus.public@gmail.com","sentAt":"2014-03-12T14:06:10Z","receivedAt":"2014-03-12T14:06:10Z","isPatch":true,"sender":{"key":"quintus.public@gmail.com","avatar":"https://gravatar.com/avatar/0805695585d6191e00badd5057b262b501047d9fb2b22dd2495009ffb25d85fd?d=mp&s=160"},"body":"2014-03-12 9:51 GMT-04:00 Duy Nguyen <pclouds@gmail.com>:\n> starts_with(..) == !memcmp(...). So\n> you need to negate every replacement.\n\nMy apologies--it doesn't look like the tests caught it either. I will\nfix this and submit a new patch.\n"},{"id":"236580","messageId":"5320818C.8070200@web.de","threadId":"36139","inReplyTo":"1394631854-11208-1-git-send-email-quintus.public@gmail.com","subject":"Re: [PATCH] general style: replaces memcmp() with starts_with()","fromName":"Jens Lehmann","fromEmail":"jens.lehmann@web.de","sentAt":"2014-03-12T15:47:24Z","receivedAt":"2014-03-12T15:47:24Z","isPatch":true,"sender":{"key":"jens.lehmann@web.de","avatar":"https://avatars.githubusercontent.com/u/135220?v=4"},"body":"Am 12.03.2014 14:44, schrieb Quint Guvernator:\n> memcmp() is replaced with starts_with() when comparing strings from the\n> beginning. starts_with() looks nicer and it saves the extra argument of\n> the length of the comparing string.\n> \n> Signed-off-by: Quint Guvernator <quintus.public@gmail.com>\n> ---\n\n...\n\n> diff --git a/submodule.c b/submodule.c\n> index b80ecac..1edebc1 100644\n> --- a/submodule.c\n> +++ b/submodule.c\n> @@ -203,7 +203,7 @@ void gitmodules_config(void)\n>  \t\t\tif (active_nr > pos) {  /* there is a .gitmodules */\n>  \t\t\t\tconst struct cache_entry *ce = active_cache[pos];\n>  \t\t\t\tif (ce_namelen(ce) == 11 &&\n> -\t\t\t\t    !memcmp(ce->name, \".gitmodules\", 11))\n> +\t\t\t\t    !starts_with(ce->name, \".gitmodules\"))\n>  \t\t\t\t\tgitmodules_is_unmerged = 1;\n>  \t\t\t}\n>  \t\t} else if (pos < active_nr) {\n\nI think this hunk should be dropped as the memcmp() here doesn't mean\n\"starts with\" but \"is identical\" (due to the \"ce_namelen(ce) == 11\" in\nthe line above).\n"},{"id":"236582","messageId":"CALs4jVFpr=YVAagJSEkAJ6qGJmYWNdu4ZXXvMYQRd0KYQXcVQA@mail.gmail.com","threadId":"36139","inReplyTo":"5320818C.8070200@web.de","subject":"Re: [PATCH] general style: replaces memcmp() with starts_with()","fromName":"Quint Guvernator","fromEmail":"quintus.public@gmail.com","sentAt":"2014-03-12T16:46:32Z","receivedAt":"2014-03-12T16:46:32Z","isPatch":true,"sender":{"key":"quintus.public@gmail.com","avatar":"https://gravatar.com/avatar/0805695585d6191e00badd5057b262b501047d9fb2b22dd2495009ffb25d85fd?d=mp&s=160"},"body":"2014-03-12 11:47 GMT-04:00 Jens Lehmann <Jens.Lehmann@web.de>:\n> I think this hunk should be dropped as the memcmp() here doesn't mean\n> \"starts with\" but \"is identical\" (due to the \"ce_namelen(ce) == 11\" in\n> the line above).\n\nThere is an issue with negation in this patch. I've submitted a new\none [1] to the mailing list. The subject line of the new patch is\n\"[PATCH] general style: replaces memcmp() with proper starts_with()\".\n\nLet me know if you still think the hunk should be dropped there.\n\n[1]: http://thread.gmane.org/gmane.comp.version-control.git/243940\n"},{"id":"236586","messageId":"532097D0.4070909@web.de","threadId":"36139","inReplyTo":"CALs4jVFpr=YVAagJSEkAJ6qGJmYWNdu4ZXXvMYQRd0KYQXcVQA@mail.gmail.com","subject":"Re: [PATCH] general style: replaces memcmp() with starts_with()","fromName":"Jens Lehmann","fromEmail":"jens.lehmann@web.de","sentAt":"2014-03-12T17:22:24Z","receivedAt":"2014-03-12T17:22:24Z","isPatch":true,"sender":{"key":"jens.lehmann@web.de","avatar":"https://avatars.githubusercontent.com/u/135220?v=4"},"body":"Am 12.03.2014 17:46, schrieb Quint Guvernator:\n> 2014-03-12 11:47 GMT-04:00 Jens Lehmann <Jens.Lehmann@web.de>:\n>> I think this hunk should be dropped as the memcmp() here doesn't mean\n>> \"starts with\" but \"is identical\" (due to the \"ce_namelen(ce) == 11\" in\n>> the line above).\n> \n> There is an issue with negation in this patch. I've submitted a new\n> one [1] to the mailing list. The subject line of the new patch is\n> \"[PATCH] general style: replaces memcmp() with proper starts_with()\".\n\nThanks, I missed that one (please use \"[PATCH v2]\" in the subject\nline of a second patch to make follow-ups easily distinguishable\nfrom the initial one ;-).\n\n> Let me know if you still think the hunk should be dropped there.\n\nYes, I think so. That spot uses memcmp() because ce->name may\nnot be 0-terminated. If that assumption isn't correct, it should\nbe replaced with a plain strcmp() instead (while also dropping\nthe ce_namelen() comparison in the line above). But starts_with()\npoints into the wrong direction there.\n\n> [1]: http://thread.gmane.org/gmane.comp.version-control.git/243940\n"},{"id":"236589","messageId":"20140312180026.GB7982@sigill.intra.peff.net","threadId":"36139","inReplyTo":"532097D0.4070909@web.de","subject":"Re: [PATCH] general style: replaces memcmp() with starts_with()","fromName":"Jeff King","fromEmail":"peff@peff.net","sentAt":"2014-03-12T18:00:26Z","receivedAt":"2014-03-12T18:00:26Z","isPatch":true,"sender":{"key":"peff@peff.net","avatar":"https://avatars.githubusercontent.com/u/45925?v=4"},"body":"On Wed, Mar 12, 2014 at 06:22:24PM +0100, Jens Lehmann wrote:\n\n> > Let me know if you still think the hunk should be dropped there.\n> \n> Yes, I think so. That spot uses memcmp() because ce->name may\n> not be 0-terminated. If that assumption isn't correct, it should\n> be replaced with a plain strcmp() instead (while also dropping\n> the ce_namelen() comparison in the line above). But starts_with()\n> points into the wrong direction there.\n\nI think the length-check and memcmp is an optimization[1] here. But we\nshould be able to encapsulate that pattern and avoid magic numbers\nentirely with something like mem_equals(). See my other response for\nmore details.\n\n-Peff\n\n[1] Getting rid of the magic number entirely means we have to call\n    strlen(\".gitmodules\"), which seems like it is working against this\n    optimization. But I think past experiments have shown that decent\n    compilers will optimize strlen on a string literal to a constant, so\n    as long as mem_equals is an inline, it should be equivalent.\n"},{"id":"236651","messageId":"CACsJy8D-GpuepvoUfTzAVgd=Uo6U90V9=kYnfUD-0SOsYK7e9Q@mail.gmail.com","threadId":"36139","inReplyTo":"532097D0.4070909@web.de","subject":"Re: [PATCH] general style: replaces memcmp() with starts_with()","fromName":"Duy Nguyen","fromEmail":"pclouds@gmail.com","sentAt":"2014-03-12T23:26:27Z","receivedAt":"2014-03-12T23:26:27Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"On Thu, Mar 13, 2014 at 12:22 AM, Jens Lehmann <Jens.Lehmann@web.de> wrote:\n> That spot uses memcmp() because ce->name may\n> not be 0-terminated.\n\nce->name is 0-terminated (at least if it's created the normal way, I\nhaven't checked where this \"ce\" in submodule.c comes from).\nce_namelen() is just an optimization because we happen to store name's\nlength if it's shorter than 4096, so there's no need to\nstrlen(ce->name) again.\n-- \nDuy\n"},{"id":"236671","messageId":"5321D75B.5020600@alum.mit.edu","threadId":"36139","inReplyTo":"CALs4jVFM58Yiku4B8NrVeac0Hmt5YsPNYb_EjY6bOr=JO6pP+A@mail.gmail.com","subject":"Re: [PATCH] general style: replaces memcmp() with starts_with()","fromName":"Michael Haggerty","fromEmail":"mhagger@alum.mit.edu","sentAt":"2014-03-13T16:05:47Z","receivedAt":"2014-03-13T16:05:47Z","isPatch":true,"sender":{"key":"mhagger@alum.mit.edu","avatar":"https://avatars.githubusercontent.com/u/119718?v=4"},"body":"On 03/12/2014 03:06 PM, Quint Guvernator wrote:\n> 2014-03-12 9:51 GMT-04:00 Duy Nguyen <pclouds@gmail.com>:\n>> starts_with(..) == !memcmp(...). So\n>> you need to negate every replacement.\n> \n> My apologies--it doesn't look like the tests caught it either. I will\n> fix this and submit a new patch.\n\nIt is very, very unlikely that you inverted the sense of dozens of tests\nthroughout the Git code base and the tests ran correctly.  I rather\nthink that you made a mistake when testing.  You should double- and\ntriple-check that you really ran the tests and ran them correctly.\n\nMichael\n\n-- \nMichael Haggerty\nmhagger@alum.mit.edu\nhttp://softwareswirl.blogspot.com/\n"},{"id":"236729","messageId":"CALs4jVGezrktbhhzk4E-C5-xDwyGAF9_1XbzHR4mdsou9GhDkA@mail.gmail.com","threadId":"36139","inReplyTo":"5321D75B.5020600@alum.mit.edu","subject":"Re: [PATCH] general style: replaces memcmp() with starts_with()","fromName":"Quint Guvernator","fromEmail":"quintus.public@gmail.com","sentAt":"2014-03-14T16:32:05Z","receivedAt":"2014-03-14T16:32:05Z","isPatch":true,"sender":{"key":"quintus.public@gmail.com","avatar":"https://gravatar.com/avatar/0805695585d6191e00badd5057b262b501047d9fb2b22dd2495009ffb25d85fd?d=mp&s=160"},"body":"2014-03-13 12:05 GMT-04:00 Michael Haggerty <mhagger@alum.mit.edu>:\n> It is very, very unlikely that you inverted the sense of dozens of tests\n> throughout the Git code base and the tests ran correctly.  I rather\n> think that you made a mistake when testing.  You should double- and\n> triple-check that you really ran the tests and ran them correctly.\n\nIt looks like HEAD was in the wrong place when I ran the tests. They\ndo not in fact pass.\n\nApologies,\nQuint\n"}]}