summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authordormando <dormando@rydia.net>2011-09-30 01:22:16 -0700
committerdormando <dormando@rydia.net>2011-10-05 00:34:18 -0700
commit444b72d40a205f3dfcac9babfa8a77712d9bd85c (patch)
treed97bf2a2bb345792c1a2645baf66594bd5efe213
parent32cb494970d00324ebe50f48b90e76faed749986 (diff)
downloadmemcached-444b72d40a205f3dfcac9babfa8a77712d9bd85c.tar.gz
remove uncommon branch from asciiprot hot path
The \0 test in the loop was accounting for 2% of memcached's CPU usage according to callgrind. strlen is an SSE4 instruction and can sniff out that null byte quickly.
-rw-r--r--memcached.c24
1 files changed, 15 insertions, 9 deletions
diff --git a/memcached.c b/memcached.c
index f8c16f1..8f15d8d 100644
--- a/memcached.c
+++ b/memcached.c
@@ -2390,28 +2390,34 @@ typedef struct token_s {
static size_t tokenize_command(char *command, token_t *tokens, const size_t max_tokens) {
char *s, *e;
size_t ntokens = 0;
+ size_t len = strlen(command);
+ unsigned int i = 0;
assert(command != NULL && tokens != NULL && max_tokens > 1);
- for (s = e = command; ntokens < max_tokens - 1; ++e) {
+ s = e = command;
+ for (i = 0; i < len; i++) {
if (*e == ' ') {
if (s != e) {
tokens[ntokens].value = s;
tokens[ntokens].length = e - s;
ntokens++;
*e = '\0';
+ if (ntokens == max_tokens - 1) {
+ e++;
+ s = e; /* so we don't add an extra token */
+ break;
+ }
}
s = e + 1;
}
- else if (*e == '\0') {
- if (s != e) {
- tokens[ntokens].value = s;
- tokens[ntokens].length = e - s;
- ntokens++;
- }
+ e++;
+ }
- break; /* string end */
- }
+ if (s != e) {
+ tokens[ntokens].value = s;
+ tokens[ntokens].length = e - s;
+ ntokens++;
}
/*