Skip to content

Commit ce99bfd

Browse files
committed
DAOS-18929 cart: add crt_bulk_free_common() and fix refcounting
Signed-off-by: Jerome Soumagne <jerome.soumagne@hpe.com>
1 parent e38a944 commit ce99bfd

3 files changed

Lines changed: 46 additions & 47 deletions

File tree

src/cart/crt_bulk.c

Lines changed: 27 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -184,19 +184,12 @@ crt_bulk_addref(crt_bulk_t crt_bulk)
184184
{
185185
struct crt_bulk *bulk = crt_bulk;
186186
int rc = -DER_SUCCESS;
187-
hg_return_t hg_ret;
188187

189188
if (bulk == NULL) {
190189
D_ERROR("invalid parameter, NULL bulk\n");
191190
D_GOTO(out, rc = -DER_INVAL);
192191
}
193192

194-
hg_ret = HG_Bulk_ref_incr(bulk->hg_bulk_hdl);
195-
if (hg_ret != HG_SUCCESS) {
196-
D_ERROR("HG_Bulk_ref_incr failed, hg_ret: %d.\n", hg_ret);
197-
rc = crt_hgret_2_der(hg_ret);
198-
}
199-
200193
atomic_fetch_add(&bulk->refcount, 1);
201194
out:
202195
return rc;
@@ -206,43 +199,43 @@ int
206199
crt_bulk_free(crt_bulk_t crt_bulk)
207200
{
208201
struct crt_bulk *bulk = crt_bulk;
209-
int rc = -DER_SUCCESS;
210-
hg_return_t hg_ret;
211202

212203
if (bulk == NULL) {
213204
D_ERROR("invalid parameter, NULL bulk\n");
214-
D_GOTO(out, rc = -DER_INVAL);
215-
}
216-
217-
/* This can happen if D_QUOTA_BULKS is enabled on a client */
218-
if (bulk->hg_bulk_hdl == HG_BULK_NULL) {
219-
if (bulk->deferred) {
220-
/* Treat as success */
221-
D_GOTO(out, rc = DER_SUCCESS);
222-
} else {
223-
D_ASSERTF(0, "Bulk handle should not be NULL\n");
224-
}
225-
}
226-
227-
hg_ret = HG_Bulk_free(bulk->hg_bulk_hdl);
228-
if (hg_ret != HG_SUCCESS) {
229-
D_ERROR("HG_Bulk_free failed, hg_ret: %d.\n", hg_ret);
230-
rc = crt_hgret_2_der(hg_ret);
205+
return -DER_INVAL;
231206
}
232207

233208
if (atomic_fetch_sub(&bulk->refcount, 1) > 1)
234209
return DER_SUCCESS;
235210

211+
crt_bulk_free_common(bulk);
212+
213+
return DER_SUCCESS;
214+
}
215+
216+
void
217+
crt_bulk_free_common(struct crt_bulk *bulk)
218+
{
219+
hg_return_t hg_ret;
220+
221+
D_ASSERT(bulk != NULL);
222+
223+
/* Decrement refcount on bulk handle itself */
224+
if (bulk->hg_bulk_hdl != HG_BULK_NULL) {
225+
hg_ret = HG_Bulk_free(bulk->hg_bulk_hdl);
226+
if (hg_ret != HG_SUCCESS) {
227+
D_ERROR("HG_Bulk_free() failed (%s)\n", HG_Error_to_string(hg_ret));
228+
/* Ignore the error, as we are already in a cleanup path */
229+
}
230+
}
231+
236232
/* decoded bulks are not counted towards quota; such bulks have crt_ctx set to NULL */
237-
if (bulk->crt_ctx)
233+
if (!bulk->deferred && bulk->crt_ctx != NULL)
238234
put_quota_resource(bulk->crt_ctx, CRT_QUOTA_BULKS);
239-
out:
240-
if (bulk != NULL) {
241-
if (bulk->iovs)
242-
D_FREE(bulk->iovs);
243-
D_FREE(bulk);
244-
}
245-
return rc;
235+
236+
if (bulk->iovs != NULL)
237+
D_FREE(bulk->iovs);
238+
D_FREE(bulk);
246239
}
247240

248241
/* Helper function to check for bulk expiration */

src/cart/crt_hg_proc.c

Lines changed: 15 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -134,12 +134,13 @@ crt_proc_crt_bulk_t_deffered(struct crt_bulk *bulk)
134134
if (bulk->bound) {
135135
rc = crt_hg_bulk_bind(bulk->hg_bulk_hdl, &ctx->cc_hg_ctx);
136136
if (rc != 0) {
137-
D_ERROR("Failed to bind bulk during proc\n");
137+
DL_ERROR(rc, "Failed to bind bulk during proc");
138138
/* free will return quota resource */
139139
crt_bulk_free(bulk->hg_bulk_hdl);
140140
return rc;
141141
}
142142
}
143+
/* Mark as no longer deferred once allocation is complete */
143144
bulk->deferred = false;
144145

145146
return 0;
@@ -165,7 +166,7 @@ crt_proc_crt_bulk_t(crt_proc_t proc, crt_proc_op_t proc_op, crt_bulk_t *pcrt_bul
165166
/* Deferred allocation as a result of D_QUOTA_BULKS limit */
166167
if (bulk != CRT_BULK_NULL) {
167168
if (bulk->deferred && (rc = crt_proc_crt_bulk_t_deffered(bulk)) != 0) {
168-
D_ERROR("Failed to do deferred bulk allocation during proc\n");
169+
DL_ERROR(rc, "Failed to do deferred bulk allocation during proc");
169170
return rc;
170171
}
171172
hg_bulk = bulk->hg_bulk_hdl;
@@ -192,12 +193,10 @@ crt_proc_crt_bulk_t(crt_proc_t proc, crt_proc_op_t proc_op, crt_bulk_t *pcrt_bul
192193

193194
/* Allocate space for a wrapper struct */
194195
D_ALLOC_PTR(bulk);
195-
if (!bulk)
196+
if (bulk == NULL)
196197
return -DER_NOMEM;
197198

198199
bulk->hg_bulk_hdl = hg_bulk;
199-
bulk->deferred = false;
200-
bulk->crt_ctx = NULL;
201200
bulk->refcount = 1;
202201

203202
*pcrt_bulk = bulk;
@@ -209,21 +208,25 @@ crt_proc_crt_bulk_t(crt_proc_t proc, crt_proc_op_t proc_op, crt_bulk_t *pcrt_bul
209208
if (bulk == NULL)
210209
return 0;
211210

212-
/* Prevent HG proc from assigning NULL if recount is not zero */
211+
/**
212+
* Prevent HG proc from assigning NULL if refcount is not zero and keep reference on
213+
* HG bulk, we'll free it ourselves. hg_proc_hg_bulk_t() will decrement refcount on
214+
* the HG bulk.
215+
*/
213216
hg_bulk = bulk->hg_bulk_hdl;
214-
hg_ret = hg_proc_hg_bulk_t(proc, &hg_bulk);
217+
HG_Bulk_ref_incr(hg_bulk);
218+
hg_ret = hg_proc_hg_bulk_t(proc, &hg_bulk);
215219
if (hg_ret != HG_SUCCESS) {
216-
D_ERROR("Failed to free bulk during proc\n");
220+
D_ERROR("Failed to free bulk during proc (%s)\n",
221+
HG_Error_to_string(hg_ret));
217222
return -DER_HG;
218223
}
219224

220225
if (atomic_fetch_sub(&bulk->refcount, 1) > 1)
221226
return 0;
222227

223-
/* Free the wrapper struct */
224-
if (bulk->iovs)
225-
D_FREE(bulk->iovs);
226-
D_FREE(bulk);
228+
/* This is the real free */
229+
crt_bulk_free_common(bulk);
227230
*pcrt_bulk = NULL;
228231
return 0;
229232
}

src/cart/crt_internal_fns.h

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
/*
22
* (C) Copyright 2016-2024 Intel Corporation.
3-
* (C) Copyright 2025 Hewlett Packard Enterprise Development LP
3+
* (C) Copyright 2025-2026 Hewlett Packard Enterprise Development LP
44
*
55
* SPDX-License-Identifier: BSD-2-Clause-Patent
66
*/
@@ -62,6 +62,9 @@ crt_bulk_desc_dup(struct crt_bulk_desc *bulk_desc_new,
6262
*bulk_desc_new = *bulk_desc;
6363
}
6464

65+
void
66+
crt_bulk_free_common(struct crt_bulk *bulk);
67+
6568
void
6669
crt_hdlr_proto_query(crt_rpc_t *rpc_req);
6770

0 commit comments

Comments
 (0)