[Sheepdog] [PATCH] accord: Added acrd_tx_atomic_inc
OZAWA Tsuyoshi
ozawa.tsuyoshi at gmail.com
Thu Nov 10 10:24:15 CET 2011
(11/11/10 16:34), MORITA Kazutaka wrote:
> At Wed, 09 Nov 2011 18:06:32 +0900,
> OZAWA Tsuyoshi wrote:
>>
>> The combination of cmp() and the other operations can simulate
>> atomic increment operations, however it can occur performance problem.
>> The new operation, atomic_inc(), can solve it.
>>
>> Signed-off-by: OZAWA Tsuyoshi<ozawa.tsuyoshi at lab.ntt.co.jp>
>> ---
>> conductor/acrdops.c | 48
>> ++++++++++++++++++++++++++++++++++++++++++++++++
>> include/accord.h | 3 +++
>> include/accord_proto.h | 1 +
>> libacrd/libacrd.c | 7 +++++++
>> test/test-txn.c | 39 +++++++++++++++++++++++++++++++++++++++
>> 5 files changed, 98 insertions(+), 0 deletions(-)
>
> This patch is malformed. Try using git send-email next time.
Okey, thank you for your pointing out my mistake.
Thanks,
Tsuyoshi
> Thanks,
>
> Kazutaka
>
>>
>> diff --git a/conductor/acrdops.c b/conductor/acrdops.c
>> index 8ec950d..ecfa04e 100644
>> --- a/conductor/acrdops.c
>> +++ b/conductor/acrdops.c
>> @@ -155,6 +155,50 @@ static int exec_del_req(const struct acrd_req *req,
>> struct acrd_rsp **rsp,
>> return ret;
>> }
>>
>> +static int exec_atomic_inc_req(const struct acrd_req *req, struct
>> acrd_rsp **rsp,
>> + struct acrd_txid *txid, struct client_info *from)
>> +{
>> + int ret = 0;
>> + void *data;
>> + const void *adddata;
>> + const char *path;
>> + uint32_t size;
>> + uint32_t d32, v;
>> +
>> + path = get_arg(req, 0)->data;
>> + adddata = get_arg(req, 1)->data;
>> + size = get_arg(req, 1)->size;
>> + dprintf("hogehoge %s %d\n", path, size);
>> +
>> + if (size != sizeof(uint32_t))
>> + goto err;
>> +
>> + if (likely(path))
>> + ret = store_read(path,&data,&size, req->offset, txid);
>> + else
>> + ret = ACRD_ERR_UNKNOWN;
>> +
>> + if (ret != ACRD_SUCCESS)
>> + goto err;
>> +
>> + if (size != sizeof(uint32_t))
>> + goto err;
>> +
>> + v = *(uint32_t *) adddata;
>> + d32 = *(uint32_t *)data;
>> + d32 += v;
>> + ret = store_write(path,&d32, size, req->offset, req->flags, txid);
>> +
>> + if (rsp)
>> + (*rsp)->result = ret;
>> +
>> + return ret;
>> +err:
>> + if (rsp)
>> + (*rsp)->result = ret;
>> + return ret;
>> +}
>> +
>> static int exec_cmp_req(const struct acrd_req *req, struct acrd_rsp **rsp,
>> struct acrd_txid *txid, struct client_info *from)
>> {
>> @@ -536,6 +580,10 @@ static struct acrd_op_tmpl acrd_ops[] = {
>> .exec_req = exec_copy_req,
>> .notify_event = notify_copy_event,
>> }, {
>> + .opcode = ACRD_OP_ATOMIC_INC,
>> + .need_mcast = 1,
>> + .exec_req = exec_atomic_inc_req,
>> + }, {
>> .opcode = ACRD_OP_TX,
>> .need_mcast = 1,
>> .exec_req = exec_tx_req,
>> diff --git a/include/accord.h b/include/accord.h
>> index 9a040f1..3fff476 100644
>> --- a/include/accord.h
>> +++ b/include/accord.h
>> @@ -375,6 +375,9 @@ int acrd_tx_scmp(struct acrd_tx *tx, const char
>> *path1, const char *path2,
>> int acrd_tx_copy(struct acrd_tx *tx, const char *src, const char *dst,
>> uint32_t flags);
>>
>> +int acrd_tx_atomic_inc(struct acrd_tx *tx, const char *path, const void
>> *buf,
>> + uint32_t count, uint32_t offset, uint32_t flags);
>> +
>> /**
>> * Commit a transaction
>> *
>> diff --git a/include/accord_proto.h b/include/accord_proto.h
>> index 455b2e8..861d623 100644
>> --- a/include/accord_proto.h
>> +++ b/include/accord_proto.h
>> @@ -18,6 +18,7 @@ enum OPERATION {
>> ACRD_OP_CMP,
>> ACRD_OP_SCMP,
>> ACRD_OP_COPY,
>> + ACRD_OP_ATOMIC_INC,
>> ACRD_OP_LIST,
>> ACRD_OP_ADD_WATCH,
>> ACRD_OP_RM_WATCH,
>> diff --git a/libacrd/libacrd.c b/libacrd/libacrd.c
>> index a99c680..4249a86 100644
>> --- a/libacrd/libacrd.c
>> +++ b/libacrd/libacrd.c
>> @@ -610,6 +610,13 @@ int acrd_tx_copy(struct acrd_tx *tx, const char
>> *src, const char *dst,
>> strlen(dst) + 1, 0, 0, flags, NULL, NULL, NULL);
>> }
>>
>> +int acrd_tx_atomic_inc(struct acrd_tx *tx, const char *path, const void
>> *buf,
>> + uint32_t count, uint32_t offset, uint32_t flags)
>> +{
>> + return acrd_op(tx->handle, tx, ACRD_OP_ATOMIC_INC, path, strlen(path)
>> + 1, buf,
>> + count, 0, offset, flags, NULL, NULL, NULL);
>> +}
>> +
>> int acrd_tx_commit(struct acrd_tx *tx, uint32_t flags)
>> {
>> struct acrd_aiocb *aiocb;
>> diff --git a/test/test-txn.c b/test/test-txn.c
>> index 562befd..57e3bdd 100644
>> --- a/test/test-txn.c
>> +++ b/test/test-txn.c
>> @@ -281,6 +281,43 @@ static void test_txn_increment(struct acrd_fixture
>> *fixture, gconstpointer p)
>> acrd_tx_close(tx);
>> }
>>
>> +static void test_txn_ainc(struct acrd_fixture *fixture, gconstpointer p)
>> +{
>> + struct acrd_handle *h = fixture->handle;
>> + uint32_t data = 5555;
>> + uint32_t newdata = 5556;
>> + uint32_t *readdata;
>> + uint32_t delta = 1;
>> + char retdata[32];
>> + uint32_t retdata_len = sizeof(data);
>> + int ret;
>> + struct acrd_tx *tx;
>> +
>> + tx = acrd_tx_init(h);
>> + g_assert(tx != NULL);
>> + ret = acrd_tx_atomic_inc(tx, "/tmp/0",&delta, sizeof(uint32_t), 0, 0);
>> + g_assert(ret == ACRD_SUCCESS);
>> + ret = acrd_tx_commit(tx, 0);
>> + g_assert(ret == ACRD_ERR_NOTFOUND);
>> + acrd_tx_close(tx);
>> +
>> + ret = acrd_write(h, "/tmp/0",&data, sizeof(uint32_t), 0,
>> ACRD_FLAG_CREATE);
>> + g_assert(ret == ACRD_SUCCESS);
>> +
>> + tx = acrd_tx_init(h);
>> + g_assert(tx != NULL);
>> + ret = acrd_tx_atomic_inc(tx, "/tmp/0",&delta, sizeof(uint32_t), 0, 0);
>> + g_assert(ret == ACRD_SUCCESS);
>> + ret = acrd_tx_commit(tx, 0);
>> + g_assert(ret == ACRD_SUCCESS);
>> + acrd_tx_close(tx);
>> +
>> + ret = acrd_read(h, "/tmp/0",&retdata,&retdata_len, 0, ACRD_FLAG_CREATE);
>> + g_assert(ret == ACRD_SUCCESS);
>> + readdata = (uint32_t *)retdata;
>> + g_assert(*readdata == newdata);
>> +}
>> +
>> static void test_txn_merge(struct acrd_fixture *fixture, gconstpointer p)
>> {
>> struct acrd_handle *h = fixture->handle;
>> @@ -406,6 +443,8 @@ int main(int argc, char **argv)
>> test_txn_setup, test_txn_merge, test_txn_teardown);
>> g_test_add("/txn/swap", struct acrd_fixture, NULL,
>> test_txn_setup, test_txn_swap, test_txn_teardown);
>> + g_test_add("/txn/ainc", struct acrd_fixture, NULL,
>> + test_txn_setup, test_txn_ainc, test_txn_teardown);
>>
>> return g_test_run();
>> }
>> --
>> 1.7.2.5
>>
>> --
>> sheepdog mailing list
>> sheepdog at lists.wpkg.org
>> http://lists.wpkg.org/mailman/listinfo/sheepdog
More information about the sheepdog
mailing list