Skip to content

Commit

Permalink
server_supports(): parse feature list more carefully
Browse files Browse the repository at this point in the history
We have been carefully choosing feature names used in the protocol
extensions so that the vocabulary does not contain a word that is a
substring of another word, so it is not a real problem, but we have
recently added "quiet" feature word, which would mean we cannot later
add some other word with "quiet" (e.g. "quiet-push"), which is awkward.

Let's make sure that we can eventually be able to do so by teaching the
clients and servers that feature words consist of non whitespace
letters. This parser also allows us to later add features with parameters
e.g. "feature=1.5" (parameter values need to be quoted for whitespaces,
but we will worry about the detauls when we do introduce them).

Signed-off-by: Junio C Hamano <gitster@pobox.com>
Signed-off-by: Clemens Buchacher <drizzd@aon.at>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
  • Loading branch information
Junio C Hamano committed Jan 8, 2012
1 parent eac2d83 commit f47182c
Show file tree
Hide file tree
Showing 4 changed files with 38 additions and 13 deletions.
5 changes: 3 additions & 2 deletions builtin/receive-pack.c
Original file line number Diff line number Diff line change
Expand Up @@ -731,9 +731,10 @@ static struct command *read_head_info(void)
refname = line + 82;
reflen = strlen(refname);
if (reflen + 82 < len) {
if (strstr(refname + reflen + 1, "report-status"))
const char *feature_list = refname + reflen + 1;
if (parse_feature_request(feature_list, "report-status"))
report_status = 1;
if (strstr(refname + reflen + 1, "side-band-64k"))
if (parse_feature_request(feature_list, "side-band-64k"))
use_sideband = LARGE_PACKET_MAX;
}
cmd = xcalloc(1, sizeof(struct command) + len - 80);
Expand Down
1 change: 1 addition & 0 deletions cache.h
Original file line number Diff line number Diff line change
Expand Up @@ -1037,6 +1037,7 @@ struct extra_have_objects {
};
extern struct ref **get_remote_heads(int in, struct ref **list, unsigned int flags, struct extra_have_objects *);
extern int server_supports(const char *feature);
extern const char *parse_feature_request(const char *features, const char *feature);

extern struct packed_git *parse_pack_index(unsigned char *sha1, const char *idx_path);

Expand Down
23 changes: 21 additions & 2 deletions connect.c
Original file line number Diff line number Diff line change
Expand Up @@ -101,8 +101,27 @@ struct ref **get_remote_heads(int in, struct ref **list,

int server_supports(const char *feature)
{
return server_capabilities &&
strstr(server_capabilities, feature) != NULL;
return !!parse_feature_request(server_capabilities, feature);
}

const char *parse_feature_request(const char *feature_list, const char *feature)
{
int len;

if (!feature_list)
return NULL;

len = strlen(feature);
while (*feature_list) {
const char *found = strstr(feature_list, feature);
if (!found)
return NULL;
if ((feature_list == found || isspace(found[-1])) &&
(!found[len] || isspace(found[len]) || found[len] == '='))
return found;
feature_list = found + 1;
}
return NULL;
}

enum protocol {
Expand Down
22 changes: 13 additions & 9 deletions upload-pack.c
Original file line number Diff line number Diff line change
Expand Up @@ -585,6 +585,7 @@ static void receive_needs(void)
write_str_in_full(debug_fd, "#S\n");
for (;;) {
struct object *o;
const char *features;
unsigned char sha1_buf[20];
len = packet_read_line(0, line, sizeof(line));
reset_timeout();
Expand Down Expand Up @@ -616,23 +617,26 @@ static void receive_needs(void)
get_sha1_hex(line+5, sha1_buf))
die("git upload-pack: protocol error, "
"expected to get sha, not '%s'", line);
if (strstr(line+45, "multi_ack_detailed"))

features = line + 45;

if (parse_feature_request(features, "multi_ack_detailed"))
multi_ack = 2;
else if (strstr(line+45, "multi_ack"))
else if (parse_feature_request(features, "multi_ack"))
multi_ack = 1;
if (strstr(line+45, "no-done"))
if (parse_feature_request(features, "no-done"))
no_done = 1;
if (strstr(line+45, "thin-pack"))
if (parse_feature_request(features, "thin-pack"))
use_thin_pack = 1;
if (strstr(line+45, "ofs-delta"))
if (parse_feature_request(features, "ofs-delta"))
use_ofs_delta = 1;
if (strstr(line+45, "side-band-64k"))
if (parse_feature_request(features, "side-band-64k"))
use_sideband = LARGE_PACKET_MAX;
else if (strstr(line+45, "side-band"))
else if (parse_feature_request(features, "side-band"))
use_sideband = DEFAULT_PACKET_MAX;
if (strstr(line+45, "no-progress"))
if (parse_feature_request(features, "no-progress"))
no_progress = 1;
if (strstr(line+45, "include-tag"))
if (parse_feature_request(features, "include-tag"))
use_include_tag = 1;

o = lookup_object(sha1_buf);
Expand Down

0 comments on commit f47182c

Please sign in to comment.