From 5bda06877303b4ac01081b12f889db1409c0a6f6 Mon Sep 17 00:00:00 2001 From: Rusty Russell Date: Fri, 3 Feb 2012 11:00:54 +1100 Subject: [PATCH] dbwrap_ctdb: only fetch a read-only copy if we had a record already. Because revoking read-only copies of records is expensive, we only want ctdbd to do it for high-turnover records. A basic heuristic is that if we don't find a local copy of the record, don't ask for a read-only copy. The fetch itself will cause ctdbd to migrate the record, so eventually we will have a local copy. Next time it gets migrated away, we'll call ctdbd_fetch() with local_copy = true. Signed-off-by: Rusty Russell --- source3/include/ctdbd_conn.h | 3 ++- source3/lib/ctdbd_conn.c | 5 +++-- source3/lib/dbwrap/dbwrap_ctdb.c | 9 +++++++-- 3 files changed, 12 insertions(+), 5 deletions(-) diff --git a/source3/include/ctdbd_conn.h b/source3/include/ctdbd_conn.h index 9a3c27cdb99..2035e8ddfc3 100644 --- a/source3/include/ctdbd_conn.h +++ b/source3/include/ctdbd_conn.h @@ -60,7 +60,8 @@ NTSTATUS ctdbd_migrate(struct ctdbd_connection *conn, uint32 db_id, TDB_DATA key); NTSTATUS ctdbd_fetch(struct ctdbd_connection *conn, uint32 db_id, - TDB_DATA key, TALLOC_CTX *mem_ctx, TDB_DATA *data); + TDB_DATA key, TALLOC_CTX *mem_ctx, TDB_DATA *data, + bool local_copy); NTSTATUS ctdbd_traverse(uint32 db_id, void (*fn)(TDB_DATA key, TDB_DATA data, diff --git a/source3/lib/ctdbd_conn.c b/source3/lib/ctdbd_conn.c index f160fd61512..47090a5412c 100644 --- a/source3/lib/ctdbd_conn.c +++ b/source3/lib/ctdbd_conn.c @@ -1394,7 +1394,8 @@ NTSTATUS ctdbd_migrate(struct ctdbd_connection *conn, uint32 db_id, * remotely fetch a record (read-only) */ NTSTATUS ctdbd_fetch(struct ctdbd_connection *conn, uint32 db_id, - TDB_DATA key, TALLOC_CTX *mem_ctx, TDB_DATA *data) + TDB_DATA key, TALLOC_CTX *mem_ctx, TDB_DATA *data, + bool local_copy) { struct ctdb_req_call req; struct ctdb_reply_call *reply; @@ -1407,7 +1408,7 @@ NTSTATUS ctdbd_fetch(struct ctdbd_connection *conn, uint32 db_id, req.hdr.ctdb_version = CTDB_VERSION; req.hdr.operation = CTDB_REQ_CALL; req.hdr.reqid = ctdbd_next_reqid(conn); - req.flags = CTDB_WANT_READONLY; + req.flags = local_copy ? CTDB_WANT_READONLY : 0; req.callid = CTDB_FETCH_FUNC; req.db_id = db_id; req.keylen = key.dsize; diff --git a/source3/lib/dbwrap/dbwrap_ctdb.c b/source3/lib/dbwrap/dbwrap_ctdb.c index 0f4efa359cc..a05f9554b76 100644 --- a/source3/lib/dbwrap/dbwrap_ctdb.c +++ b/source3/lib/dbwrap/dbwrap_ctdb.c @@ -1203,9 +1203,14 @@ static NTSTATUS db_ctdb_fetch(struct db_context *db, TALLOC_CTX *mem_ctx, SAFE_FREE(ctdb_data.dptr); - /* we weren't able to get it locally - ask ctdb to fetch it for us */ + /* + * We weren't able to get it locally - ask ctdb to fetch it for us. + * If we already had *something*, it's probably worth making a local + * read-only copy. + */ status = ctdbd_fetch(messaging_ctdbd_connection(), ctx->db_id, key, - mem_ctx, data); + mem_ctx, data, + ctdb_data.dsize >= sizeof(struct ctdb_ltdb_header)); if (!NT_STATUS_IS_OK(status)) { DEBUG(5, ("ctdbd_fetch failed: %s\n", nt_errstr(status))); } -- 2.11.4.GIT