Closed GoogleCodeExporter closed 9 years ago
The textual protocol does not allow stale data to persist in the cache in case of memory allocation errors. The binary protocol allows it. e.g: Textual protocol: //////////////////////// static void process_update_command(conn *c, token_t *tokens, const size_t ntokens, int comm, bool handle_cas) { . . . it = item_alloc(key, nkey, flags, realtime(exptime), vlen+2); if (it == 0) { if (! item_size_ok(nkey, flags, vlen + 2)) out_string(c, "SERVER_ERROR object too large for cache"); else out_string(c, "SERVER_ERROR out of memory storing object"); /* swallow the data line */ c->write_and_go = conn_swallow; c->sbytes = vlen + 2; /* Avoid stale data persisting in cache because we failed alloc. * Unacceptable for SET. Anywhere else too? */ if (comm == NREAD_SET) { it = item_get(key, nkey); if (it) { item_unlink(it); item_remove(it); } } return; } . . . } Textual protocol: //////////////////////// int do_store_item(item *it, int comm, conn *c) { . . . if (comm == NREAD_APPEND || comm == NREAD_PREPEND) { . . new_it = do_item_alloc(key, it->nkey, flags, old_it->exptime, it->nbytes + old_it->nbytes - 2 /* CRLF */); if (new_it == NULL) { /* SERVER_ERROR out of memory */ if (old_it != NULL) do_item_remove(old_it); return 0; } . . . } Binary protocol: //////////////////////// static void process_bin_update(conn *c) { . . . it = item_alloc(key, nkey, req->message.body.flags, realtime(req->message.body.expiration), vlen+2); if (it == 0) { if (! item_size_ok(nkey, req->message.body.flags, vlen + 2)) { write_bin_error(c, PROTOCOL_BINARY_RESPONSE_E2BIG, vlen); } else { write_bin_error(c, PROTOCOL_BINARY_RESPONSE_ENOMEM, vlen); } /* swallow the data line */ c->write_and_go = conn_swallow; return; } . . . } Binary protocol: //////////////////////// static void process_bin_append_prepend(conn *c) { . . . it = item_alloc(key, nkey, 0, 0, vlen+2); if (it == 0) { if (! item_size_ok(nkey, 0, vlen + 2)) { write_bin_error(c, PROTOCOL_BINARY_RESPONSE_E2BIG, vlen); } else { write_bin_error(c, PROTOCOL_BINARY_RESPONSE_ENOMEM, vlen); } /* swallow the data line */ c->write_and_go = conn_swallow; return; } . . . }
Original issue reported on code.google.com by Victor.K...@gmail.com on 17 Dec 2008 at 6:48
Victor.K...@gmail.com
Fixed (with test) in http://github.com/dustin/memcached/commit/8ff14453be52fb43a1ba5d3fb372847db92753 0f
Original comment by dsalli...@gmail.com on 22 Jan 2009 at 12:58
dsalli...@gmail.com
Original issue reported on code.google.com by
Victor.K...@gmail.com
on 17 Dec 2008 at 6:48