1 // -*- mode:C++; tab-width:8; c-basic-offset:2; indent-tabs-mode:t -*-
2 // vim: ts=8 sw=2 smarttab
4 * Ceph - scalable distributed file system
6 * Copyright (C) 2011 New Dream Network
8 * This is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Lesser General Public
10 * License version 2.1, as published by the Free Software
11 * Foundation. See file COPYING.
14 #include "include/int_types.h"
18 #include "common/dout.h"
19 #include "common/errno.h"
20 #include "common/TracepointProvider.h"
21 #include "include/Context.h"
23 #include "cls/rbd/cls_rbd_client.h"
24 #include "cls/rbd/cls_rbd_types.h"
25 #include "librbd/ImageCtx.h"
26 #include "librbd/ImageState.h"
27 #include "librbd/internal.h"
28 #include "librbd/Operations.h"
29 #include "librbd/api/Config.h"
30 #include "librbd/api/DiffIterate.h"
31 #include "librbd/api/Group.h"
32 #include "librbd/api/Image.h"
33 #include "librbd/api/Migration.h"
34 #include "librbd/api/Mirror.h"
35 #include "librbd/api/Namespace.h"
36 #include "librbd/api/Pool.h"
37 #include "librbd/api/PoolMetadata.h"
38 #include "librbd/api/Snapshot.h"
39 #include "librbd/api/Trash.h"
40 #include "librbd/io/AioCompletion.h"
41 #include "librbd/io/ImageRequestWQ.h"
42 #include "librbd/io/ReadResult.h"
48 #define TRACEPOINT_DEFINE
49 #define TRACEPOINT_PROBE_DYNAMIC_LINKAGE
50 #include "tracing/librbd.h"
51 #undef TRACEPOINT_PROBE_DYNAMIC_LINKAGE
52 #undef TRACEPOINT_DEFINE
54 #define tracepoint(...)
57 #define dout_subsys ceph_subsys_rbd
59 #define dout_prefix *_dout << "librbd: "
64 using ceph::bufferlist
;
65 using librados::snap_t
;
66 using librados::IoCtx
;
70 TracepointProvider::Traits
tracepoint_traits("librbd_tp.so", "rbd_tracing");
72 static auto create_write_raw(librbd::ImageCtx
*ictx
, const char *buf
,
74 // TODO: until librados can guarantee memory won't be referenced after
75 // it ACKs a request, always make a copy of the user-provided memory
76 return buffer::copy(buf
, len
);
79 CephContext
* get_cct(IoCtx
&io_ctx
) {
80 return reinterpret_cast<CephContext
*>(io_ctx
.cct());
83 librbd::io::AioCompletion
* get_aio_completion(librbd::RBD::AioCompletion
*comp
) {
84 return reinterpret_cast<librbd::io::AioCompletion
*>(comp
->pc
);
87 struct C_AioCompletion
: public Context
{
89 librbd::io::aio_type_t aio_type
;
90 librbd::io::AioCompletion
* aio_comp
;
92 C_AioCompletion(librbd::ImageCtx
*ictx
, librbd::io::aio_type_t aio_type
,
93 librbd::io::AioCompletion
* aio_comp
)
94 : cct(ictx
->cct
), aio_type(aio_type
), aio_comp(aio_comp
) {
95 aio_comp
->init_time(ictx
, aio_type
);
99 void finish(int r
) override
{
100 ldout(cct
, 20) << "C_AioComplete::finish: r=" << r
<< dendl
;
104 aio_comp
->lock
.Lock();
105 aio_comp
->complete();
106 aio_comp
->put_unlock();
111 struct C_OpenComplete
: public C_AioCompletion
{
112 librbd::ImageCtx
*ictx
;
114 C_OpenComplete(librbd::ImageCtx
*ictx
, librbd::io::AioCompletion
* comp
,
116 : C_AioCompletion(ictx
, librbd::io::AIO_TYPE_OPEN
, comp
),
117 ictx(ictx
), ictxp(ictxp
) {
119 void finish(int r
) override
{
120 ldout(ictx
->cct
, 20) << "C_OpenComplete::finish: r=" << r
<< dendl
;
127 C_AioCompletion::finish(r
);
131 struct C_OpenAfterCloseComplete
: public Context
{
132 librbd::ImageCtx
*ictx
;
133 librbd::io::AioCompletion
* comp
;
135 C_OpenAfterCloseComplete(librbd::ImageCtx
*ictx
,
136 librbd::io::AioCompletion
* comp
,
138 : ictx(ictx
), comp(comp
), ictxp(ictxp
) {
140 void finish(int r
) override
{
141 ldout(ictx
->cct
, 20) << "C_OpenAfterCloseComplete::finish: r=" << r
143 delete reinterpret_cast<librbd::ImageCtx
*>(*ictxp
);
146 ictx
->state
->open(0, new C_OpenComplete(ictx
, comp
, ictxp
));
150 struct C_UpdateWatchCB
: public librbd::UpdateWatchCtx
{
151 rbd_update_callback_t watch_cb
;
155 C_UpdateWatchCB(rbd_update_callback_t watch_cb
, void *arg
) :
156 watch_cb(watch_cb
), arg(arg
) {
158 void handle_notify() override
{
163 void group_image_status_cpp_to_c(const librbd::group_image_info_t
&cpp_info
,
164 rbd_group_image_info_t
*c_info
) {
165 c_info
->name
= strdup(cpp_info
.name
.c_str());
166 c_info
->pool
= cpp_info
.pool
;
167 c_info
->state
= cpp_info
.state
;
170 void group_info_cpp_to_c(const librbd::group_info_t
&cpp_info
,
171 rbd_group_info_t
*c_info
) {
172 c_info
->name
= strdup(cpp_info
.name
.c_str());
173 c_info
->pool
= cpp_info
.pool
;
176 void group_snap_info_cpp_to_c(const librbd::group_snap_info_t
&cpp_info
,
177 rbd_group_snap_info_t
*c_info
) {
178 c_info
->name
= strdup(cpp_info
.name
.c_str());
179 c_info
->state
= cpp_info
.state
;
182 void mirror_image_info_cpp_to_c(const librbd::mirror_image_info_t
&cpp_info
,
183 rbd_mirror_image_info_t
*c_info
) {
184 c_info
->global_id
= strdup(cpp_info
.global_id
.c_str());
185 c_info
->state
= cpp_info
.state
;
186 c_info
->primary
= cpp_info
.primary
;
189 void mirror_image_status_cpp_to_c(const librbd::mirror_image_status_t
&cpp_status
,
190 rbd_mirror_image_status_t
*c_status
) {
191 c_status
->name
= strdup(cpp_status
.name
.c_str());
192 mirror_image_info_cpp_to_c(cpp_status
.info
, &c_status
->info
);
193 c_status
->state
= cpp_status
.state
;
194 c_status
->description
= strdup(cpp_status
.description
.c_str());
195 c_status
->last_update
= cpp_status
.last_update
;
196 c_status
->up
= cpp_status
.up
;
199 void trash_image_info_cpp_to_c(const librbd::trash_image_info_t
&cpp_info
,
200 rbd_trash_image_info_t
*c_info
) {
201 c_info
->id
= strdup(cpp_info
.id
.c_str());
202 c_info
->name
= strdup(cpp_info
.name
.c_str());
203 c_info
->source
= cpp_info
.source
;
204 c_info
->deletion_time
= cpp_info
.deletion_time
;
205 c_info
->deferment_end_time
= cpp_info
.deferment_end_time
;
208 void config_option_cpp_to_c(const librbd::config_option_t
&cpp_option
,
209 rbd_config_option_t
*c_option
) {
210 c_option
->name
= strdup(cpp_option
.name
.c_str());
211 c_option
->value
= strdup(cpp_option
.value
.c_str());
212 c_option
->source
= cpp_option
.source
;
215 void config_option_cleanup(rbd_config_option_t
&option
) {
220 struct C_MirrorImageGetInfo
: public Context
{
221 rbd_mirror_image_info_t
*mirror_image_info
;
224 librbd::mirror_image_info_t cpp_mirror_image_info
;
226 C_MirrorImageGetInfo(rbd_mirror_image_info_t
*mirror_image_info
,
228 : mirror_image_info(mirror_image_info
), on_finish(on_finish
) {
231 void finish(int r
) override
{
233 on_finish
->complete(r
);
237 mirror_image_info_cpp_to_c(cpp_mirror_image_info
, mirror_image_info
);
238 on_finish
->complete(0);
242 struct C_MirrorImageGetStatus
: public Context
{
243 rbd_mirror_image_status_t
*mirror_image_status
;
246 librbd::mirror_image_status_t cpp_mirror_image_status
;
248 C_MirrorImageGetStatus(rbd_mirror_image_status_t
*mirror_image_status
,
250 : mirror_image_status(mirror_image_status
), on_finish(on_finish
) {
253 void finish(int r
) override
{
255 on_finish
->complete(r
);
259 mirror_image_status_cpp_to_c(cpp_mirror_image_status
, mirror_image_status
);
260 on_finish
->complete(0);
264 } // anonymous namespace
267 ProgressContext::~ProgressContext()
271 class CProgressContext
: public ProgressContext
274 CProgressContext(librbd_progress_fn_t fn
, void *data
)
275 : m_fn(fn
), m_data(data
)
278 int update_progress(uint64_t offset
, uint64_t src_size
) override
280 return m_fn(offset
, src_size
, m_data
);
283 librbd_progress_fn_t m_fn
;
290 PoolStats::PoolStats() {
291 rbd_pool_stats_create(&pool_stats
);
294 PoolStats::~PoolStats() {
295 rbd_pool_stats_destroy(pool_stats
);
298 int PoolStats::add(rbd_pool_stat_option_t option
, uint64_t* opt_val
) {
299 return rbd_pool_stats_option_add_uint64(pool_stats
, option
, opt_val
);
313 void RBD::version(int *major
, int *minor
, int *extra
)
315 rbd_version(major
, minor
, extra
);
318 int RBD::open(IoCtx
& io_ctx
, Image
& image
, const char *name
)
320 return open(io_ctx
, image
, name
, NULL
);
323 int RBD::open_by_id(IoCtx
& io_ctx
, Image
& image
, const char *id
)
325 return open_by_id(io_ctx
, image
, id
, nullptr);
328 int RBD::open(IoCtx
& io_ctx
, Image
& image
, const char *name
,
329 const char *snap_name
)
331 ImageCtx
*ictx
= new ImageCtx(name
, "", snap_name
, io_ctx
, false);
332 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
333 tracepoint(librbd
, open_image_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
335 if (image
.ctx
!= NULL
) {
336 reinterpret_cast<ImageCtx
*>(image
.ctx
)->state
->close();
340 int r
= ictx
->state
->open(0);
342 tracepoint(librbd
, open_image_exit
, r
);
346 image
.ctx
= (image_ctx_t
) ictx
;
347 tracepoint(librbd
, open_image_exit
, 0);
351 int RBD::open_by_id(IoCtx
& io_ctx
, Image
& image
, const char *id
,
352 const char *snap_name
)
354 ImageCtx
*ictx
= new ImageCtx("", id
, snap_name
, io_ctx
, false);
355 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
356 tracepoint(librbd
, open_image_by_id_enter
, ictx
, ictx
->id
.c_str(),
357 ictx
->snap_name
.c_str(), ictx
->read_only
);
359 if (image
.ctx
!= nullptr) {
360 reinterpret_cast<ImageCtx
*>(image
.ctx
)->state
->close();
364 int r
= ictx
->state
->open(0);
366 tracepoint(librbd
, open_image_by_id_exit
, r
);
370 image
.ctx
= (image_ctx_t
) ictx
;
371 tracepoint(librbd
, open_image_by_id_exit
, 0);
375 int RBD::aio_open(IoCtx
& io_ctx
, Image
& image
, const char *name
,
376 const char *snap_name
, RBD::AioCompletion
*c
)
378 ImageCtx
*ictx
= new ImageCtx(name
, "", snap_name
, io_ctx
, false);
379 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
380 tracepoint(librbd
, aio_open_image_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, c
->pc
);
382 if (image
.ctx
!= NULL
) {
383 reinterpret_cast<ImageCtx
*>(image
.ctx
)->state
->close(
384 new C_OpenAfterCloseComplete(ictx
, get_aio_completion(c
), &image
.ctx
));
386 ictx
->state
->open(0, new C_OpenComplete(ictx
, get_aio_completion(c
),
389 tracepoint(librbd
, aio_open_image_exit
, 0);
393 int RBD::aio_open_by_id(IoCtx
& io_ctx
, Image
& image
, const char *id
,
394 const char *snap_name
, RBD::AioCompletion
*c
)
396 ImageCtx
*ictx
= new ImageCtx("", id
, snap_name
, io_ctx
, false);
397 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
398 tracepoint(librbd
, aio_open_image_by_id_enter
, ictx
, ictx
->id
.c_str(),
399 ictx
->snap_name
.c_str(), ictx
->read_only
, c
->pc
);
401 if (image
.ctx
!= nullptr) {
402 reinterpret_cast<ImageCtx
*>(image
.ctx
)->state
->close(
403 new C_OpenAfterCloseComplete(ictx
, get_aio_completion(c
), &image
.ctx
));
405 ictx
->state
->open(0, new C_OpenComplete(ictx
, get_aio_completion(c
),
408 tracepoint(librbd
, aio_open_image_by_id_exit
, 0);
412 int RBD::open_read_only(IoCtx
& io_ctx
, Image
& image
, const char *name
,
413 const char *snap_name
)
415 ImageCtx
*ictx
= new ImageCtx(name
, "", snap_name
, io_ctx
, true);
416 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
417 tracepoint(librbd
, open_image_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
419 if (image
.ctx
!= NULL
) {
420 reinterpret_cast<ImageCtx
*>(image
.ctx
)->state
->close();
424 int r
= ictx
->state
->open(0);
426 tracepoint(librbd
, open_image_exit
, r
);
430 image
.ctx
= (image_ctx_t
) ictx
;
431 tracepoint(librbd
, open_image_exit
, 0);
435 int RBD::open_by_id_read_only(IoCtx
& io_ctx
, Image
& image
, const char *id
,
436 const char *snap_name
)
438 ImageCtx
*ictx
= new ImageCtx("", id
, snap_name
, io_ctx
, true);
439 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
440 tracepoint(librbd
, open_image_by_id_enter
, ictx
, ictx
->id
.c_str(),
441 ictx
->snap_name
.c_str(), ictx
->read_only
);
443 if (image
.ctx
!= nullptr) {
444 reinterpret_cast<ImageCtx
*>(image
.ctx
)->state
->close();
448 int r
= ictx
->state
->open(0);
450 tracepoint(librbd
, open_image_by_id_exit
, r
);
454 image
.ctx
= (image_ctx_t
) ictx
;
455 tracepoint(librbd
, open_image_by_id_exit
, 0);
459 int RBD::aio_open_read_only(IoCtx
& io_ctx
, Image
& image
, const char *name
,
460 const char *snap_name
, RBD::AioCompletion
*c
)
462 ImageCtx
*ictx
= new ImageCtx(name
, "", snap_name
, io_ctx
, true);
463 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
464 tracepoint(librbd
, aio_open_image_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, c
->pc
);
466 if (image
.ctx
!= NULL
) {
467 reinterpret_cast<ImageCtx
*>(image
.ctx
)->state
->close(
468 new C_OpenAfterCloseComplete(ictx
, get_aio_completion(c
), &image
.ctx
));
470 ictx
->state
->open(0, new C_OpenComplete(ictx
, get_aio_completion(c
),
473 tracepoint(librbd
, aio_open_image_exit
, 0);
477 int RBD::aio_open_by_id_read_only(IoCtx
& io_ctx
, Image
& image
, const char *id
,
478 const char *snap_name
, RBD::AioCompletion
*c
)
480 ImageCtx
*ictx
= new ImageCtx("", id
, snap_name
, io_ctx
, true);
481 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
482 tracepoint(librbd
, aio_open_image_by_id_enter
, ictx
, ictx
->id
.c_str(),
483 ictx
->snap_name
.c_str(), ictx
->read_only
, c
->pc
);
485 if (image
.ctx
!= nullptr) {
486 reinterpret_cast<ImageCtx
*>(image
.ctx
)->state
->close(
487 new C_OpenAfterCloseComplete(ictx
, get_aio_completion(c
), &image
.ctx
));
489 ictx
->state
->open(0, new C_OpenComplete(ictx
, get_aio_completion(c
),
492 tracepoint(librbd
, aio_open_image_by_id_exit
, 0);
496 int RBD::create(IoCtx
& io_ctx
, const char *name
, uint64_t size
, int *order
)
498 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
499 tracepoint(librbd
, create_enter
, io_ctx
.get_pool_name().c_str(), io_ctx
.get_id(), name
, size
, *order
);
500 int r
= librbd::create(io_ctx
, name
, size
, order
);
501 tracepoint(librbd
, create_exit
, r
, *order
);
505 int RBD::create2(IoCtx
& io_ctx
, const char *name
, uint64_t size
,
506 uint64_t features
, int *order
)
508 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
509 tracepoint(librbd
, create2_enter
, io_ctx
.get_pool_name().c_str(), io_ctx
.get_id(), name
, size
, features
, *order
);
510 int r
= librbd::create(io_ctx
, name
, size
, false, features
, order
, 0, 0);
511 tracepoint(librbd
, create2_exit
, r
, *order
);
515 int RBD::create3(IoCtx
& io_ctx
, const char *name
, uint64_t size
,
516 uint64_t features
, int *order
, uint64_t stripe_unit
,
517 uint64_t stripe_count
)
519 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
520 tracepoint(librbd
, create3_enter
, io_ctx
.get_pool_name().c_str(), io_ctx
.get_id(), name
, size
, features
, *order
, stripe_unit
, stripe_count
);
521 int r
= librbd::create(io_ctx
, name
, size
, false, features
, order
,
522 stripe_unit
, stripe_count
);
523 tracepoint(librbd
, create3_exit
, r
, *order
);
527 int RBD::create4(IoCtx
& io_ctx
, const char *name
, uint64_t size
,
530 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
531 tracepoint(librbd
, create4_enter
, io_ctx
.get_pool_name().c_str(), io_ctx
.get_id(), name
, size
, opts
.opts
);
532 int r
= librbd::create(io_ctx
, name
, "", size
, opts
, "", "", false);
533 tracepoint(librbd
, create4_exit
, r
);
537 int RBD::clone(IoCtx
& p_ioctx
, const char *p_name
, const char *p_snap_name
,
538 IoCtx
& c_ioctx
, const char *c_name
, uint64_t features
,
541 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(p_ioctx
));
542 tracepoint(librbd
, clone_enter
, p_ioctx
.get_pool_name().c_str(), p_ioctx
.get_id(), p_name
, p_snap_name
, c_ioctx
.get_pool_name().c_str(), c_ioctx
.get_id(), c_name
, features
);
543 int r
= librbd::clone(p_ioctx
, p_name
, p_snap_name
, c_ioctx
, c_name
,
544 features
, c_order
, 0, 0);
545 tracepoint(librbd
, clone_exit
, r
, *c_order
);
549 int RBD::clone2(IoCtx
& p_ioctx
, const char *p_name
, const char *p_snap_name
,
550 IoCtx
& c_ioctx
, const char *c_name
, uint64_t features
,
551 int *c_order
, uint64_t stripe_unit
, int stripe_count
)
553 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(p_ioctx
));
554 tracepoint(librbd
, clone2_enter
, p_ioctx
.get_pool_name().c_str(), p_ioctx
.get_id(), p_name
, p_snap_name
, c_ioctx
.get_pool_name().c_str(), c_ioctx
.get_id(), c_name
, features
, stripe_unit
, stripe_count
);
555 int r
= librbd::clone(p_ioctx
, p_name
, p_snap_name
, c_ioctx
, c_name
,
556 features
, c_order
, stripe_unit
, stripe_count
);
557 tracepoint(librbd
, clone2_exit
, r
, *c_order
);
561 int RBD::clone3(IoCtx
& p_ioctx
, const char *p_name
, const char *p_snap_name
,
562 IoCtx
& c_ioctx
, const char *c_name
, ImageOptions
& c_opts
)
564 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(p_ioctx
));
565 tracepoint(librbd
, clone3_enter
, p_ioctx
.get_pool_name().c_str(), p_ioctx
.get_id(), p_name
, p_snap_name
, c_ioctx
.get_pool_name().c_str(), c_ioctx
.get_id(), c_name
, c_opts
.opts
);
566 int r
= librbd::clone(p_ioctx
, nullptr, p_name
, p_snap_name
, c_ioctx
,
567 nullptr, c_name
, c_opts
, "", "");
568 tracepoint(librbd
, clone3_exit
, r
);
572 int RBD::remove(IoCtx
& io_ctx
, const char *name
)
574 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
575 tracepoint(librbd
, remove_enter
, io_ctx
.get_pool_name().c_str(), io_ctx
.get_id(), name
);
576 librbd::NoOpProgressContext prog_ctx
;
577 int r
= librbd::api::Image
<>::remove(io_ctx
, name
, prog_ctx
);
578 tracepoint(librbd
, remove_exit
, r
);
582 int RBD::remove_with_progress(IoCtx
& io_ctx
, const char *name
,
583 ProgressContext
& pctx
)
585 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
586 tracepoint(librbd
, remove_enter
, io_ctx
.get_pool_name().c_str(), io_ctx
.get_id(), name
);
587 int r
= librbd::api::Image
<>::remove(io_ctx
, name
, pctx
);
588 tracepoint(librbd
, remove_exit
, r
);
592 int RBD::trash_move(IoCtx
&io_ctx
, const char *name
, uint64_t delay
) {
593 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
594 tracepoint(librbd
, trash_move_enter
, io_ctx
.get_pool_name().c_str(),
595 io_ctx
.get_id(), name
);
596 int r
= librbd::api::Trash
<>::move(io_ctx
, RBD_TRASH_IMAGE_SOURCE_USER
,
598 tracepoint(librbd
, trash_move_exit
, r
);
602 int RBD::trash_get(IoCtx
&io_ctx
, const char *id
, trash_image_info_t
*info
) {
603 return librbd::api::Trash
<>::get(io_ctx
, id
, info
);
606 int RBD::trash_list(IoCtx
&io_ctx
, vector
<trash_image_info_t
> &entries
) {
607 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
608 tracepoint(librbd
, trash_list_enter
,
609 io_ctx
.get_pool_name().c_str(), io_ctx
.get_id());
610 int r
= librbd::api::Trash
<>::list(io_ctx
, entries
, true);
613 for (const auto& entry
: entries
) {
614 tracepoint(librbd
, trash_list_entry
, entry
.id
.c_str());
618 tracepoint(librbd
, trash_list_exit
, r
, r
);
622 int RBD::trash_remove(IoCtx
&io_ctx
, const char *image_id
, bool force
) {
623 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
624 tracepoint(librbd
, trash_remove_enter
, io_ctx
.get_pool_name().c_str(),
625 io_ctx
.get_id(), image_id
, force
);
626 librbd::NoOpProgressContext prog_ctx
;
627 int r
= librbd::api::Trash
<>::remove(io_ctx
, image_id
, force
, prog_ctx
);
628 tracepoint(librbd
, trash_remove_exit
, r
);
632 int RBD::trash_remove_with_progress(IoCtx
&io_ctx
, const char *image_id
,
633 bool force
, ProgressContext
&pctx
) {
634 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
635 tracepoint(librbd
, trash_remove_enter
, io_ctx
.get_pool_name().c_str(),
636 io_ctx
.get_id(), image_id
, force
);
637 int r
= librbd::api::Trash
<>::remove(io_ctx
, image_id
, force
, pctx
);
638 tracepoint(librbd
, trash_remove_exit
, r
);
642 int RBD::trash_restore(IoCtx
&io_ctx
, const char *id
, const char *name
) {
643 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
644 tracepoint(librbd
, trash_undelete_enter
, io_ctx
.get_pool_name().c_str(),
645 io_ctx
.get_id(), id
, name
);
646 int r
= librbd::api::Trash
<>::restore(io_ctx
, RBD_TRASH_IMAGE_SOURCE_USER
,
648 tracepoint(librbd
, trash_undelete_exit
, r
);
652 int RBD::trash_purge(IoCtx
&io_ctx
, time_t expire_ts
, float threshold
) {
653 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
654 tracepoint(librbd
, trash_purge_enter
, io_ctx
.get_pool_name().c_str(),
655 io_ctx
.get_id(), expire_ts
, threshold
);
656 NoOpProgressContext nop_pctx
;
657 int r
= librbd::api::Trash
<>::purge(io_ctx
, expire_ts
, threshold
, nop_pctx
);
658 tracepoint(librbd
, trash_purge_exit
, r
);
662 int RBD::trash_purge_with_progress(IoCtx
&io_ctx
, time_t expire_ts
,
663 float threshold
, ProgressContext
&pctx
) {
664 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
665 tracepoint(librbd
, trash_purge_enter
, io_ctx
.get_pool_name().c_str(),
666 io_ctx
.get_id(), expire_ts
, threshold
);
667 int r
= librbd::api::Trash
<>::purge(io_ctx
, expire_ts
, threshold
, pctx
);
668 tracepoint(librbd
, trash_purge_exit
, r
);
672 int RBD::namespace_create(IoCtx
& io_ctx
, const char *namespace_name
) {
673 return librbd::api::Namespace
<>::create(io_ctx
, namespace_name
);
676 int RBD::namespace_remove(IoCtx
& io_ctx
, const char *namespace_name
) {
677 return librbd::api::Namespace
<>::remove(io_ctx
, namespace_name
);
680 int RBD::namespace_list(IoCtx
& io_ctx
,
681 std::vector
<std::string
>* namespace_names
) {
682 return librbd::api::Namespace
<>::list(io_ctx
, namespace_names
);
685 int RBD::namespace_exists(IoCtx
& io_ctx
, const char *namespace_name
,
687 return librbd::api::Namespace
<>::exists(io_ctx
, namespace_name
, exists
);
690 int RBD::pool_init(IoCtx
& io_ctx
, bool force
) {
691 return librbd::api::Pool
<>::init(io_ctx
, force
);
694 int RBD::pool_stats_get(IoCtx
& io_ctx
, PoolStats
* stats
) {
695 auto pool_stat_options
=
696 reinterpret_cast<librbd::api::Pool
<>::StatOptions
*>(stats
->pool_stats
);
697 return librbd::api::Pool
<>::get_stats(io_ctx
, pool_stat_options
);
700 int RBD::list(IoCtx
& io_ctx
, vector
<string
>& names
)
702 std::vector
<image_spec_t
> image_specs
;
703 int r
= list2(io_ctx
, &image_specs
);
709 for (auto& it
: image_specs
) {
710 names
.push_back(it
.name
);
715 int RBD::list2(IoCtx
& io_ctx
, std::vector
<image_spec_t
> *images
)
717 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
718 tracepoint(librbd
, list_enter
, io_ctx
.get_pool_name().c_str(),
721 int r
= librbd::api::Image
<>::list_images(io_ctx
, images
);
723 for (auto& it
: *images
) {
724 tracepoint(librbd
, list_entry
, it
.name
.c_str());
727 tracepoint(librbd
, list_exit
, r
, r
);
731 int RBD::rename(IoCtx
& src_io_ctx
, const char *srcname
, const char *destname
)
733 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(src_io_ctx
));
734 tracepoint(librbd
, rename_enter
, src_io_ctx
.get_pool_name().c_str(), src_io_ctx
.get_id(), srcname
, destname
);
735 int r
= librbd::rename(src_io_ctx
, srcname
, destname
);
736 tracepoint(librbd
, rename_exit
, r
);
740 int RBD::migration_prepare(IoCtx
& io_ctx
, const char *image_name
,
741 IoCtx
& dest_io_ctx
, const char *dest_image_name
,
744 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
745 tracepoint(librbd
, migration_prepare_enter
, io_ctx
.get_pool_name().c_str(),
746 io_ctx
.get_id(), image_name
, dest_io_ctx
.get_pool_name().c_str(),
747 dest_io_ctx
.get_id(), dest_image_name
, opts
.opts
);
748 int r
= librbd::api::Migration
<>::prepare(io_ctx
, image_name
, dest_io_ctx
,
749 dest_image_name
, opts
);
750 tracepoint(librbd
, migration_prepare_exit
, r
);
754 int RBD::migration_execute(IoCtx
& io_ctx
, const char *image_name
)
756 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
757 tracepoint(librbd
, migration_execute_enter
, io_ctx
.get_pool_name().c_str(),
758 io_ctx
.get_id(), image_name
);
759 librbd::NoOpProgressContext prog_ctx
;
760 int r
= librbd::api::Migration
<>::execute(io_ctx
, image_name
, prog_ctx
);
761 tracepoint(librbd
, migration_execute_exit
, r
);
765 int RBD::migration_execute_with_progress(IoCtx
& io_ctx
,
766 const char *image_name
,
767 librbd::ProgressContext
&prog_ctx
)
769 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
770 tracepoint(librbd
, migration_execute_enter
, io_ctx
.get_pool_name().c_str(),
771 io_ctx
.get_id(), image_name
);
772 int r
= librbd::api::Migration
<>::execute(io_ctx
, image_name
, prog_ctx
);
773 tracepoint(librbd
, migration_execute_exit
, r
);
777 int RBD::migration_abort(IoCtx
& io_ctx
, const char *image_name
)
779 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
780 tracepoint(librbd
, migration_abort_enter
, io_ctx
.get_pool_name().c_str(),
781 io_ctx
.get_id(), image_name
);
782 librbd::NoOpProgressContext prog_ctx
;
783 int r
= librbd::api::Migration
<>::abort(io_ctx
, image_name
, prog_ctx
);
784 tracepoint(librbd
, migration_abort_exit
, r
);
788 int RBD::migration_abort_with_progress(IoCtx
& io_ctx
, const char *image_name
,
789 librbd::ProgressContext
&prog_ctx
)
791 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
792 tracepoint(librbd
, migration_abort_enter
, io_ctx
.get_pool_name().c_str(),
793 io_ctx
.get_id(), image_name
);
794 int r
= librbd::api::Migration
<>::abort(io_ctx
, image_name
, prog_ctx
);
795 tracepoint(librbd
, migration_abort_exit
, r
);
799 int RBD::migration_commit(IoCtx
& io_ctx
, const char *image_name
)
801 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
802 tracepoint(librbd
, migration_commit_enter
, io_ctx
.get_pool_name().c_str(),
803 io_ctx
.get_id(), image_name
);
804 librbd::NoOpProgressContext prog_ctx
;
805 int r
= librbd::api::Migration
<>::commit(io_ctx
, image_name
, prog_ctx
);
806 tracepoint(librbd
, migration_commit_exit
, r
);
810 int RBD::migration_commit_with_progress(IoCtx
& io_ctx
, const char *image_name
,
811 librbd::ProgressContext
&prog_ctx
)
813 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
814 tracepoint(librbd
, migration_commit_enter
, io_ctx
.get_pool_name().c_str(),
815 io_ctx
.get_id(), image_name
);
816 int r
= librbd::api::Migration
<>::commit(io_ctx
, image_name
, prog_ctx
);
817 tracepoint(librbd
, migration_commit_exit
, r
);
821 int RBD::migration_status(IoCtx
& io_ctx
, const char *image_name
,
822 image_migration_status_t
*status
,
825 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
826 tracepoint(librbd
, migration_status_enter
, io_ctx
.get_pool_name().c_str(),
827 io_ctx
.get_id(), image_name
);
829 if (status_size
!= sizeof(image_migration_status_t
)) {
830 tracepoint(librbd
, migration_status_exit
, -ERANGE
);
834 int r
= librbd::api::Migration
<>::status(io_ctx
, image_name
, status
);
835 tracepoint(librbd
, migration_status_exit
, r
);
839 int RBD::mirror_mode_get(IoCtx
& io_ctx
, rbd_mirror_mode_t
*mirror_mode
) {
840 return librbd::api::Mirror
<>::mode_get(io_ctx
, mirror_mode
);
843 int RBD::mirror_mode_set(IoCtx
& io_ctx
, rbd_mirror_mode_t mirror_mode
) {
844 return librbd::api::Mirror
<>::mode_set(io_ctx
, mirror_mode
);
847 int RBD::mirror_peer_add(IoCtx
& io_ctx
, std::string
*uuid
,
848 const std::string
&cluster_name
,
849 const std::string
&client_name
) {
850 return librbd::api::Mirror
<>::peer_add(io_ctx
, uuid
, cluster_name
,
854 int RBD::mirror_peer_remove(IoCtx
& io_ctx
, const std::string
&uuid
) {
855 return librbd::api::Mirror
<>::peer_remove(io_ctx
, uuid
);
858 int RBD::mirror_peer_list(IoCtx
& io_ctx
, std::vector
<mirror_peer_t
> *peers
) {
859 return librbd::api::Mirror
<>::peer_list(io_ctx
, peers
);
862 int RBD::mirror_peer_set_client(IoCtx
& io_ctx
, const std::string
&uuid
,
863 const std::string
&client_name
) {
864 return librbd::api::Mirror
<>::peer_set_client(io_ctx
, uuid
, client_name
);
867 int RBD::mirror_peer_set_cluster(IoCtx
& io_ctx
, const std::string
&uuid
,
868 const std::string
&cluster_name
) {
869 return librbd::api::Mirror
<>::peer_set_cluster(io_ctx
, uuid
, cluster_name
);
872 int RBD::mirror_peer_get_attributes(
873 IoCtx
& io_ctx
, const std::string
&uuid
,
874 std::map
<std::string
, std::string
> *key_vals
) {
875 return librbd::api::Mirror
<>::peer_get_attributes(io_ctx
, uuid
, key_vals
);
878 int RBD::mirror_peer_set_attributes(
879 IoCtx
& io_ctx
, const std::string
&uuid
,
880 const std::map
<std::string
, std::string
>& key_vals
) {
881 return librbd::api::Mirror
<>::peer_set_attributes(io_ctx
, uuid
, key_vals
);
884 int RBD::mirror_image_status_list(IoCtx
& io_ctx
, const std::string
&start_id
,
885 size_t max
, std::map
<std::string
, mirror_image_status_t
> *images
) {
886 return librbd::api::Mirror
<>::image_status_list(io_ctx
, start_id
, max
,
890 int RBD::mirror_image_status_summary(IoCtx
& io_ctx
,
891 std::map
<mirror_image_status_state_t
, int> *states
) {
892 return librbd::api::Mirror
<>::image_status_summary(io_ctx
, states
);
895 int RBD::mirror_image_instance_id_list(IoCtx
& io_ctx
,
896 const std::string
&start_id
, size_t max
,
897 std::map
<std::string
, std::string
> *instance_ids
) {
898 return librbd::api::Mirror
<>::image_instance_id_list(io_ctx
, start_id
, max
,
902 int RBD::group_create(IoCtx
& io_ctx
, const char *group_name
)
904 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
905 tracepoint(librbd
, group_create_enter
, io_ctx
.get_pool_name().c_str(),
906 io_ctx
.get_id(), group_name
);
907 int r
= librbd::api::Group
<>::create(io_ctx
, group_name
);
908 tracepoint(librbd
, group_create_exit
, r
);
912 int RBD::group_remove(IoCtx
& io_ctx
, const char *group_name
)
914 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
915 tracepoint(librbd
, group_remove_enter
, io_ctx
.get_pool_name().c_str(),
916 io_ctx
.get_id(), group_name
);
917 int r
= librbd::api::Group
<>::remove(io_ctx
, group_name
);
918 tracepoint(librbd
, group_remove_exit
, r
);
922 int RBD::group_list(IoCtx
& io_ctx
, vector
<string
> *names
)
924 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
925 tracepoint(librbd
, group_list_enter
, io_ctx
.get_pool_name().c_str(),
928 int r
= librbd::api::Group
<>::list(io_ctx
, names
);
930 for (auto itr
: *names
) {
931 tracepoint(librbd
, group_list_entry
, itr
.c_str());
934 tracepoint(librbd
, group_list_exit
, r
);
938 int RBD::group_rename(IoCtx
& io_ctx
, const char *src_name
,
939 const char *dest_name
)
941 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
942 tracepoint(librbd
, group_rename_enter
, io_ctx
.get_pool_name().c_str(),
943 io_ctx
.get_id(), src_name
, dest_name
);
944 int r
= librbd::api::Group
<>::rename(io_ctx
, src_name
, dest_name
);
945 tracepoint(librbd
, group_rename_exit
, r
);
949 int RBD::group_image_add(IoCtx
& group_ioctx
, const char *group_name
,
950 IoCtx
& image_ioctx
, const char *image_name
)
952 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
953 tracepoint(librbd
, group_image_add_enter
,
954 group_ioctx
.get_pool_name().c_str(),
955 group_ioctx
.get_id(), group_name
,
956 image_ioctx
.get_pool_name().c_str(),
957 image_ioctx
.get_id(), image_name
);
958 int r
= librbd::api::Group
<>::image_add(group_ioctx
, group_name
,
959 image_ioctx
, image_name
);
960 tracepoint(librbd
, group_image_add_exit
, r
);
964 int RBD::group_image_remove(IoCtx
& group_ioctx
, const char *group_name
,
965 IoCtx
& image_ioctx
, const char *image_name
)
967 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
968 tracepoint(librbd
, group_image_remove_enter
,
969 group_ioctx
.get_pool_name().c_str(),
970 group_ioctx
.get_id(), group_name
,
971 image_ioctx
.get_pool_name().c_str(),
972 image_ioctx
.get_id(), image_name
);
973 int r
= librbd::api::Group
<>::image_remove(group_ioctx
, group_name
,
974 image_ioctx
, image_name
);
975 tracepoint(librbd
, group_image_remove_exit
, r
);
979 int RBD::group_image_remove_by_id(IoCtx
& group_ioctx
, const char *group_name
,
980 IoCtx
& image_ioctx
, const char *image_id
)
982 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
983 tracepoint(librbd
, group_image_remove_by_id_enter
,
984 group_ioctx
.get_pool_name().c_str(),
985 group_ioctx
.get_id(), group_name
,
986 image_ioctx
.get_pool_name().c_str(),
987 image_ioctx
.get_id(), image_id
);
988 int r
= librbd::api::Group
<>::image_remove_by_id(group_ioctx
, group_name
,
989 image_ioctx
, image_id
);
990 tracepoint(librbd
, group_image_remove_by_id_exit
, r
);
994 int RBD::group_image_list(IoCtx
& group_ioctx
, const char *group_name
,
995 std::vector
<group_image_info_t
> *images
,
996 size_t group_image_info_size
)
998 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
999 tracepoint(librbd
, group_image_list_enter
,
1000 group_ioctx
.get_pool_name().c_str(),
1001 group_ioctx
.get_id(), group_name
);
1003 if (group_image_info_size
!= sizeof(group_image_info_t
)) {
1004 tracepoint(librbd
, group_image_list_exit
, -ERANGE
);
1008 int r
= librbd::api::Group
<>::image_list(group_ioctx
, group_name
, images
);
1009 tracepoint(librbd
, group_image_list_exit
, r
);
1013 int RBD::group_snap_create(IoCtx
& group_ioctx
, const char *group_name
,
1014 const char *snap_name
) {
1015 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
1016 tracepoint(librbd
, group_snap_create_enter
,
1017 group_ioctx
.get_pool_name().c_str(),
1018 group_ioctx
.get_id(), group_name
, snap_name
);
1019 int r
= librbd::api::Group
<>::snap_create(group_ioctx
, group_name
,
1021 tracepoint(librbd
, group_snap_create_exit
, r
);
1025 int RBD::group_snap_remove(IoCtx
& group_ioctx
, const char *group_name
,
1026 const char *snap_name
) {
1027 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
1028 tracepoint(librbd
, group_snap_remove_enter
,
1029 group_ioctx
.get_pool_name().c_str(),
1030 group_ioctx
.get_id(), group_name
, snap_name
);
1031 int r
= librbd::api::Group
<>::snap_remove(group_ioctx
, group_name
,
1033 tracepoint(librbd
, group_snap_remove_exit
, r
);
1037 int RBD::group_snap_list(IoCtx
& group_ioctx
, const char *group_name
,
1038 std::vector
<group_snap_info_t
> *snaps
,
1039 size_t group_snap_info_size
)
1041 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
1042 tracepoint(librbd
, group_snap_list_enter
,
1043 group_ioctx
.get_pool_name().c_str(),
1044 group_ioctx
.get_id(), group_name
);
1046 if (group_snap_info_size
!= sizeof(group_snap_info_t
)) {
1047 tracepoint(librbd
, group_snap_list_exit
, -ERANGE
);
1051 int r
= librbd::api::Group
<>::snap_list(group_ioctx
, group_name
, snaps
);
1052 tracepoint(librbd
, group_snap_list_exit
, r
);
1056 int RBD::group_snap_rename(IoCtx
& group_ioctx
, const char *group_name
,
1057 const char *old_snap_name
,
1058 const char *new_snap_name
)
1060 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
1061 tracepoint(librbd
, group_snap_rename_enter
,
1062 group_ioctx
.get_pool_name().c_str(), group_ioctx
.get_id(),
1063 group_name
, old_snap_name
, new_snap_name
);
1064 int r
= librbd::api::Group
<>::snap_rename(group_ioctx
, group_name
,
1065 old_snap_name
, new_snap_name
);
1066 tracepoint(librbd
, group_snap_list_exit
, r
);
1070 int RBD::group_snap_rollback(IoCtx
& group_ioctx
, const char *group_name
,
1071 const char *snap_name
) {
1072 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
1073 tracepoint(librbd
, group_snap_rollback_enter
,
1074 group_ioctx
.get_pool_name().c_str(),
1075 group_ioctx
.get_id(), group_name
, snap_name
);
1076 librbd::NoOpProgressContext prog_ctx
;
1077 int r
= librbd::api::Group
<>::snap_rollback(group_ioctx
, group_name
,
1078 snap_name
, prog_ctx
);
1079 tracepoint(librbd
, group_snap_rollback_exit
, r
);
1083 int RBD::group_snap_rollback_with_progress(IoCtx
& group_ioctx
,
1084 const char *group_name
,
1085 const char *snap_name
,
1086 ProgressContext
& prog_ctx
) {
1087 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
1088 tracepoint(librbd
, group_snap_rollback_enter
,
1089 group_ioctx
.get_pool_name().c_str(),
1090 group_ioctx
.get_id(), group_name
, snap_name
);
1091 int r
= librbd::api::Group
<>::snap_rollback(group_ioctx
, group_name
,
1092 snap_name
, prog_ctx
);
1093 tracepoint(librbd
, group_snap_rollback_exit
, r
);
1097 int RBD::pool_metadata_get(IoCtx
& ioctx
, const std::string
&key
,
1100 int r
= librbd::api::PoolMetadata
<>::get(ioctx
, key
, value
);
1104 int RBD::pool_metadata_set(IoCtx
& ioctx
, const std::string
&key
,
1105 const std::string
&value
)
1107 int r
= librbd::api::PoolMetadata
<>::set(ioctx
, key
, value
);
1111 int RBD::pool_metadata_remove(IoCtx
& ioctx
, const std::string
&key
)
1113 int r
= librbd::api::PoolMetadata
<>::remove(ioctx
, key
);
1117 int RBD::pool_metadata_list(IoCtx
& ioctx
, const std::string
&start
,
1118 uint64_t max
, map
<string
, bufferlist
> *pairs
)
1120 int r
= librbd::api::PoolMetadata
<>::list(ioctx
, start
, max
, pairs
);
1124 int RBD::config_list(IoCtx
& io_ctx
, std::vector
<config_option_t
> *options
) {
1125 return librbd::api::Config
<>::list(io_ctx
, options
);
1128 RBD::AioCompletion::AioCompletion(void *cb_arg
, callback_t complete_cb
)
1130 pc
= reinterpret_cast<void*>(librbd::io::AioCompletion::create(
1131 cb_arg
, complete_cb
, this));
1134 bool RBD::AioCompletion::is_complete()
1136 librbd::io::AioCompletion
*c
= (librbd::io::AioCompletion
*)pc
;
1137 return c
->is_complete();
1140 int RBD::AioCompletion::wait_for_complete()
1142 librbd::io::AioCompletion
*c
= (librbd::io::AioCompletion
*)pc
;
1143 return c
->wait_for_complete();
1146 ssize_t
RBD::AioCompletion::get_return_value()
1148 librbd::io::AioCompletion
*c
= (librbd::io::AioCompletion
*)pc
;
1149 return c
->get_return_value();
1152 void *RBD::AioCompletion::get_arg()
1154 librbd::io::AioCompletion
*c
= (librbd::io::AioCompletion
*)pc
;
1155 return c
->get_arg();
1158 void RBD::AioCompletion::release()
1160 librbd::io::AioCompletion
*c
= (librbd::io::AioCompletion
*)pc
;
1169 ImageOptions::ImageOptions()
1171 librbd::image_options_create(&opts
);
1174 ImageOptions::ImageOptions(rbd_image_options_t opts_
)
1176 librbd::image_options_create_ref(&opts
, opts_
);
1179 ImageOptions::ImageOptions(const ImageOptions
&imgopts
)
1181 librbd::image_options_copy(&opts
, imgopts
);
1184 ImageOptions::~ImageOptions()
1186 librbd::image_options_destroy(opts
);
1189 int ImageOptions::set(int optname
, const std::string
& optval
)
1191 return librbd::image_options_set(opts
, optname
, optval
);
1194 int ImageOptions::set(int optname
, uint64_t optval
)
1196 return librbd::image_options_set(opts
, optname
, optval
);
1199 int ImageOptions::get(int optname
, std::string
* optval
) const
1201 return librbd::image_options_get(opts
, optname
, optval
);
1204 int ImageOptions::get(int optname
, uint64_t* optval
) const
1206 return librbd::image_options_get(opts
, optname
, optval
);
1209 int ImageOptions::is_set(int optname
, bool* is_set
)
1211 return librbd::image_options_is_set(opts
, optname
, is_set
);
1214 int ImageOptions::unset(int optname
)
1216 return librbd::image_options_unset(opts
, optname
);
1219 void ImageOptions::clear()
1221 librbd::image_options_clear(opts
);
1224 bool ImageOptions::empty() const
1226 return librbd::image_options_is_empty(opts
);
1233 Image::Image() : ctx(NULL
)
1246 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1247 tracepoint(librbd
, close_image_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str());
1249 r
= ictx
->state
->close();
1252 tracepoint(librbd
, close_image_exit
, r
);
1257 int Image::aio_close(RBD::AioCompletion
*c
)
1263 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1264 tracepoint(librbd
, aio_close_image_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str(), c
->pc
);
1266 ictx
->state
->close(new C_AioCompletion(ictx
, librbd::io::AIO_TYPE_CLOSE
,
1267 get_aio_completion(c
)));
1270 tracepoint(librbd
, aio_close_image_exit
, 0);
1274 int Image::resize(uint64_t size
)
1276 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1277 tracepoint(librbd
, resize_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, size
);
1278 librbd::NoOpProgressContext prog_ctx
;
1279 int r
= ictx
->operations
->resize(size
, true, prog_ctx
);
1280 tracepoint(librbd
, resize_exit
, r
);
1284 int Image::resize2(uint64_t size
, bool allow_shrink
, librbd::ProgressContext
& pctx
)
1286 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1287 tracepoint(librbd
, resize_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, size
);
1288 int r
= ictx
->operations
->resize(size
, allow_shrink
, pctx
);
1289 tracepoint(librbd
, resize_exit
, r
);
1293 int Image::resize_with_progress(uint64_t size
, librbd::ProgressContext
& pctx
)
1295 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1296 tracepoint(librbd
, resize_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, size
);
1297 int r
= ictx
->operations
->resize(size
, true, pctx
);
1298 tracepoint(librbd
, resize_exit
, r
);
1302 int Image::stat(image_info_t
& info
, size_t infosize
)
1304 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1305 tracepoint(librbd
, stat_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
1306 int r
= librbd::info(ictx
, info
, infosize
);
1307 tracepoint(librbd
, stat_exit
, r
, &info
);
1311 int Image::old_format(uint8_t *old
)
1313 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1314 tracepoint(librbd
, get_old_format_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
1315 int r
= librbd::get_old_format(ictx
, old
);
1316 tracepoint(librbd
, get_old_format_exit
, r
, *old
);
1320 int Image::size(uint64_t *size
)
1322 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1323 tracepoint(librbd
, get_size_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
1324 int r
= librbd::get_size(ictx
, size
);
1325 tracepoint(librbd
, get_size_exit
, r
, *size
);
1329 int Image::get_group(group_info_t
*group_info
, size_t group_info_size
)
1331 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1332 tracepoint(librbd
, image_get_group_enter
, ictx
->name
.c_str());
1334 if (group_info_size
!= sizeof(group_info_t
)) {
1335 tracepoint(librbd
, image_get_group_exit
, -ERANGE
);
1339 int r
= librbd::api::Group
<>::image_get_group(ictx
, group_info
);
1340 tracepoint(librbd
, image_get_group_exit
, r
);
1344 int Image::features(uint64_t *features
)
1346 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1347 tracepoint(librbd
, get_features_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
1348 int r
= librbd::get_features(ictx
, features
);
1349 tracepoint(librbd
, get_features_exit
, r
, *features
);
1353 int Image::update_features(uint64_t features
, bool enabled
)
1355 ImageCtx
*ictx
= reinterpret_cast<ImageCtx
*>(ctx
);
1356 tracepoint(librbd
, update_features_enter
, ictx
, features
, enabled
);
1357 int r
= ictx
->operations
->update_features(features
, enabled
);
1358 tracepoint(librbd
, update_features_exit
, r
);
1362 int Image::get_op_features(uint64_t *op_features
)
1364 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1365 return librbd::api::Image
<>::get_op_features(ictx
, op_features
);
1368 uint64_t Image::get_stripe_unit() const
1370 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1371 tracepoint(librbd
, get_stripe_unit_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
1372 uint64_t stripe_unit
= ictx
->get_stripe_unit();
1373 tracepoint(librbd
, get_stripe_unit_exit
, 0, stripe_unit
);
1377 uint64_t Image::get_stripe_count() const
1379 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1380 tracepoint(librbd
, get_stripe_count_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
1381 uint64_t stripe_count
= ictx
->get_stripe_count();
1382 tracepoint(librbd
, get_stripe_count_exit
, 0, stripe_count
);
1383 return stripe_count
;
1386 int Image::get_create_timestamp(struct timespec
*timestamp
)
1388 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1389 tracepoint(librbd
, get_create_timestamp_enter
, ictx
, ictx
->name
.c_str(),
1391 utime_t time
= ictx
->get_create_timestamp();
1392 time
.to_timespec(timestamp
);
1393 tracepoint(librbd
, get_create_timestamp_exit
, 0, timestamp
);
1397 int Image::get_access_timestamp(struct timespec
*timestamp
)
1399 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1400 tracepoint(librbd
, get_access_timestamp_enter
, ictx
, ictx
->name
.c_str(),
1403 RWLock::RLocker
timestamp_locker(ictx
->timestamp_lock
);
1404 utime_t time
= ictx
->get_access_timestamp();
1405 time
.to_timespec(timestamp
);
1407 tracepoint(librbd
, get_access_timestamp_exit
, 0, timestamp
);
1411 int Image::get_modify_timestamp(struct timespec
*timestamp
)
1413 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1414 tracepoint(librbd
, get_modify_timestamp_enter
, ictx
, ictx
->name
.c_str(),
1417 RWLock::RLocker
timestamp_locker(ictx
->timestamp_lock
);
1418 utime_t time
= ictx
->get_modify_timestamp();
1419 time
.to_timespec(timestamp
);
1421 tracepoint(librbd
, get_modify_timestamp_exit
, 0, timestamp
);
1425 int Image::overlap(uint64_t *overlap
)
1427 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1428 tracepoint(librbd
, get_overlap_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
1429 int r
= librbd::get_overlap(ictx
, overlap
);
1430 tracepoint(librbd
, get_overlap_exit
, r
, *overlap
);
1434 int Image::get_name(std::string
*name
)
1436 ImageCtx
*ictx
= reinterpret_cast<ImageCtx
*>(ctx
);
1441 int Image::get_id(std::string
*id
)
1443 ImageCtx
*ictx
= reinterpret_cast<ImageCtx
*>(ctx
);
1444 if (ictx
->old_format
) {
1451 std::string
Image::get_block_name_prefix()
1453 ImageCtx
*ictx
= reinterpret_cast<ImageCtx
*>(ctx
);
1454 return ictx
->object_prefix
;
1457 int64_t Image::get_data_pool_id()
1459 ImageCtx
*ictx
= reinterpret_cast<ImageCtx
*>(ctx
);
1460 return ictx
->data_ctx
.get_id();
1463 int Image::parent_info(string
*parent_pool_name
, string
*parent_name
,
1464 string
*parent_snap_name
)
1466 librbd::linked_image_spec_t parent_image
;
1467 librbd::snap_spec_t parent_snap
;
1468 int r
= get_parent(&parent_image
, &parent_snap
);
1470 if (parent_pool_name
!= nullptr) {
1471 *parent_pool_name
= parent_image
.pool_name
;
1473 if (parent_name
!= nullptr) {
1474 *parent_name
= parent_image
.image_name
;
1476 if (parent_snap_name
!= nullptr) {
1477 *parent_snap_name
= parent_snap
.name
;
1483 int Image::parent_info2(string
*parent_pool_name
, string
*parent_name
,
1484 string
*parent_id
, string
*parent_snap_name
)
1486 librbd::linked_image_spec_t parent_image
;
1487 librbd::snap_spec_t parent_snap
;
1488 int r
= get_parent(&parent_image
, &parent_snap
);
1490 if (parent_pool_name
!= nullptr) {
1491 *parent_pool_name
= parent_image
.pool_name
;
1493 if (parent_name
!= nullptr) {
1494 *parent_name
= parent_image
.image_name
;
1496 if (parent_id
!= nullptr) {
1497 *parent_id
= parent_image
.image_id
;
1499 if (parent_snap_name
!= nullptr) {
1500 *parent_snap_name
= parent_snap
.name
;
1506 int Image::get_parent(linked_image_spec_t
*parent_image
,
1507 snap_spec_t
*parent_snap
)
1509 auto ictx
= reinterpret_cast<ImageCtx
*>(ctx
);
1510 tracepoint(librbd
, get_parent_info_enter
, ictx
, ictx
->name
.c_str(),
1511 ictx
->snap_name
.c_str(), ictx
->read_only
);
1513 int r
= librbd::api::Image
<>::get_parent(ictx
, parent_image
, parent_snap
);
1515 tracepoint(librbd
, get_parent_info_exit
, r
,
1516 parent_image
->pool_name
.c_str(),
1517 parent_image
->image_name
.c_str(),
1518 parent_image
->image_id
.c_str(),
1519 parent_snap
->name
.c_str());
1523 int Image::get_flags(uint64_t *flags
)
1525 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1526 tracepoint(librbd
, get_flags_enter
, ictx
);
1527 int r
= librbd::get_flags(ictx
, flags
);
1528 tracepoint(librbd
, get_flags_exit
, ictx
, r
, *flags
);
1532 int Image::set_image_notification(int fd
, int type
)
1534 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1535 tracepoint(librbd
, set_image_notification_enter
, ictx
, fd
, type
);
1536 int r
= librbd::set_image_notification(ictx
, fd
, type
);
1537 tracepoint(librbd
, set_image_notification_exit
, ictx
, r
);
1541 int Image::is_exclusive_lock_owner(bool *is_owner
)
1543 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1544 tracepoint(librbd
, is_exclusive_lock_owner_enter
, ictx
);
1545 int r
= librbd::is_exclusive_lock_owner(ictx
, is_owner
);
1546 tracepoint(librbd
, is_exclusive_lock_owner_exit
, ictx
, r
, *is_owner
);
1550 int Image::lock_acquire(rbd_lock_mode_t lock_mode
)
1552 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1553 tracepoint(librbd
, lock_acquire_enter
, ictx
, lock_mode
);
1554 int r
= librbd::lock_acquire(ictx
, lock_mode
);
1555 tracepoint(librbd
, lock_acquire_exit
, ictx
, r
);
1559 int Image::lock_release()
1561 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1562 tracepoint(librbd
, lock_release_enter
, ictx
);
1563 int r
= librbd::lock_release(ictx
);
1564 tracepoint(librbd
, lock_release_exit
, ictx
, r
);
1568 int Image::lock_get_owners(rbd_lock_mode_t
*lock_mode
,
1569 std::list
<std::string
> *lock_owners
)
1571 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1572 tracepoint(librbd
, lock_get_owners_enter
, ictx
);
1573 int r
= librbd::lock_get_owners(ictx
, lock_mode
, lock_owners
);
1574 tracepoint(librbd
, lock_get_owners_exit
, ictx
, r
);
1578 int Image::lock_break(rbd_lock_mode_t lock_mode
,
1579 const std::string
&lock_owner
)
1581 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1582 tracepoint(librbd
, lock_break_enter
, ictx
, lock_mode
, lock_owner
.c_str());
1583 int r
= librbd::lock_break(ictx
, lock_mode
, lock_owner
);
1584 tracepoint(librbd
, lock_break_exit
, ictx
, r
);
1588 int Image::rebuild_object_map(ProgressContext
&prog_ctx
)
1590 ImageCtx
*ictx
= reinterpret_cast<ImageCtx
*>(ctx
);
1591 return ictx
->operations
->rebuild_object_map(prog_ctx
);
1594 int Image::check_object_map(ProgressContext
&prog_ctx
)
1596 ImageCtx
*ictx
= reinterpret_cast<ImageCtx
*>(ctx
);
1597 return ictx
->operations
->check_object_map(prog_ctx
);
1600 int Image::copy(IoCtx
& dest_io_ctx
, const char *destname
)
1602 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1603 tracepoint(librbd
, copy_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(), destname
);
1605 librbd::NoOpProgressContext prog_ctx
;
1606 int r
= librbd::copy(ictx
, dest_io_ctx
, destname
, opts
, prog_ctx
, 0);
1607 tracepoint(librbd
, copy_exit
, r
);
1611 int Image::copy2(Image
& dest
)
1613 ImageCtx
*srcctx
= (ImageCtx
*)ctx
;
1614 ImageCtx
*destctx
= (ImageCtx
*)dest
.ctx
;
1615 tracepoint(librbd
, copy2_enter
, srcctx
, srcctx
->name
.c_str(), srcctx
->snap_name
.c_str(), srcctx
->read_only
, destctx
, destctx
->name
.c_str(), destctx
->snap_name
.c_str(), destctx
->read_only
);
1616 librbd::NoOpProgressContext prog_ctx
;
1617 int r
= librbd::copy(srcctx
, destctx
, prog_ctx
, 0);
1618 tracepoint(librbd
, copy2_exit
, r
);
1622 int Image::copy3(IoCtx
& dest_io_ctx
, const char *destname
, ImageOptions
& opts
)
1624 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1625 tracepoint(librbd
, copy3_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(), destname
, opts
.opts
);
1626 librbd::NoOpProgressContext prog_ctx
;
1627 int r
= librbd::copy(ictx
, dest_io_ctx
, destname
, opts
, prog_ctx
, 0);
1628 tracepoint(librbd
, copy3_exit
, r
);
1632 int Image::copy4(IoCtx
& dest_io_ctx
, const char *destname
, ImageOptions
& opts
, size_t sparse_size
)
1634 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1635 tracepoint(librbd
, copy4_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(), destname
, opts
.opts
, sparse_size
);
1636 librbd::NoOpProgressContext prog_ctx
;
1637 int r
= librbd::copy(ictx
, dest_io_ctx
, destname
, opts
, prog_ctx
, sparse_size
);
1638 tracepoint(librbd
, copy4_exit
, r
);
1642 int Image::copy_with_progress(IoCtx
& dest_io_ctx
, const char *destname
,
1643 librbd::ProgressContext
&pctx
)
1645 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1646 tracepoint(librbd
, copy_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(), destname
);
1648 int r
= librbd::copy(ictx
, dest_io_ctx
, destname
, opts
, pctx
, 0);
1649 tracepoint(librbd
, copy_exit
, r
);
1653 int Image::copy_with_progress2(Image
& dest
, librbd::ProgressContext
&pctx
)
1655 ImageCtx
*srcctx
= (ImageCtx
*)ctx
;
1656 ImageCtx
*destctx
= (ImageCtx
*)dest
.ctx
;
1657 tracepoint(librbd
, copy2_enter
, srcctx
, srcctx
->name
.c_str(), srcctx
->snap_name
.c_str(), srcctx
->read_only
, destctx
, destctx
->name
.c_str(), destctx
->snap_name
.c_str(), destctx
->read_only
);
1658 int r
= librbd::copy(srcctx
, destctx
, pctx
, 0);
1659 tracepoint(librbd
, copy2_exit
, r
);
1663 int Image::copy_with_progress3(IoCtx
& dest_io_ctx
, const char *destname
,
1665 librbd::ProgressContext
&pctx
)
1667 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1668 tracepoint(librbd
, copy3_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(), destname
, opts
.opts
);
1669 int r
= librbd::copy(ictx
, dest_io_ctx
, destname
, opts
, pctx
, 0);
1670 tracepoint(librbd
, copy3_exit
, r
);
1674 int Image::copy_with_progress4(IoCtx
& dest_io_ctx
, const char *destname
,
1676 librbd::ProgressContext
&pctx
,
1679 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1680 tracepoint(librbd
, copy4_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(), destname
, opts
.opts
, sparse_size
);
1681 int r
= librbd::copy(ictx
, dest_io_ctx
, destname
, opts
, pctx
, sparse_size
);
1682 tracepoint(librbd
, copy4_exit
, r
);
1686 int Image::deep_copy(IoCtx
& dest_io_ctx
, const char *destname
,
1689 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1690 tracepoint(librbd
, deep_copy_enter
, ictx
, ictx
->name
.c_str(),
1691 ictx
->snap_name
.c_str(), ictx
->read_only
,
1692 dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(),
1693 destname
, opts
.opts
);
1694 librbd::NoOpProgressContext prog_ctx
;
1695 int r
= librbd::api::Image
<>::deep_copy(ictx
, dest_io_ctx
, destname
, opts
,
1697 tracepoint(librbd
, deep_copy_exit
, r
);
1701 int Image::deep_copy_with_progress(IoCtx
& dest_io_ctx
, const char *destname
,
1703 librbd::ProgressContext
&prog_ctx
)
1705 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1706 tracepoint(librbd
, deep_copy_enter
, ictx
, ictx
->name
.c_str(),
1707 ictx
->snap_name
.c_str(), ictx
->read_only
,
1708 dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(),
1709 destname
, opts
.opts
);
1710 int r
= librbd::api::Image
<>::deep_copy(ictx
, dest_io_ctx
, destname
, opts
,
1712 tracepoint(librbd
, deep_copy_exit
, r
);
1716 int Image::flatten()
1718 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1719 tracepoint(librbd
, flatten_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str());
1720 librbd::NoOpProgressContext prog_ctx
;
1721 int r
= ictx
->operations
->flatten(prog_ctx
);
1722 tracepoint(librbd
, flatten_exit
, r
);
1726 int Image::flatten_with_progress(librbd::ProgressContext
& prog_ctx
)
1728 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1729 tracepoint(librbd
, flatten_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str());
1730 int r
= ictx
->operations
->flatten(prog_ctx
);
1731 tracepoint(librbd
, flatten_exit
, r
);
1735 int Image::sparsify(size_t sparse_size
)
1737 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1738 tracepoint(librbd
, sparsify_enter
, ictx
, ictx
->name
.c_str(), sparse_size
,
1740 librbd::NoOpProgressContext prog_ctx
;
1741 int r
= ictx
->operations
->sparsify(sparse_size
, prog_ctx
);
1742 tracepoint(librbd
, sparsify_exit
, r
);
1746 int Image::sparsify_with_progress(size_t sparse_size
,
1747 librbd::ProgressContext
& prog_ctx
)
1749 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1750 tracepoint(librbd
, sparsify_enter
, ictx
, ictx
->name
.c_str(), sparse_size
,
1752 int r
= ictx
->operations
->sparsify(sparse_size
, prog_ctx
);
1753 tracepoint(librbd
, sparsify_exit
, r
);
1757 int Image::list_children(set
<pair
<string
, string
> > *children
)
1759 std::vector
<linked_image_spec_t
> images
;
1760 int r
= list_children3(&images
);
1765 for (auto& image
: images
) {
1767 children
->insert({image
.pool_name
, image
.image_name
});
1773 int Image::list_children2(vector
<librbd::child_info_t
> *children
)
1775 std::vector
<linked_image_spec_t
> images
;
1776 int r
= list_children3(&images
);
1781 for (auto& image
: images
) {
1782 children
->push_back({
1783 .pool_name
= image
.pool_name
,
1784 .image_name
= image
.image_name
,
1785 .image_id
= image
.image_id
,
1786 .trash
= image
.trash
});
1792 int Image::list_children3(std::vector
<linked_image_spec_t
> *images
)
1794 auto ictx
= reinterpret_cast<ImageCtx
*>(ctx
);
1795 tracepoint(librbd
, list_children_enter
, ictx
, ictx
->name
.c_str(),
1796 ictx
->snap_name
.c_str(), ictx
->read_only
);
1798 int r
= librbd::api::Image
<>::list_children(ictx
, images
);
1800 for (auto& it
: *images
) {
1801 tracepoint(librbd
, list_children_entry
, it
.pool_name
.c_str(),
1802 it
.image_name
.c_str());
1806 tracepoint(librbd
, list_children_exit
, r
);
1810 int Image::list_descendants(std::vector
<linked_image_spec_t
> *images
)
1812 auto ictx
= reinterpret_cast<ImageCtx
*>(ctx
);
1815 int r
= librbd::api::Image
<>::list_descendants(ictx
, {}, images
);
1819 int Image::list_lockers(std::list
<librbd::locker_t
> *lockers
,
1820 bool *exclusive
, string
*tag
)
1822 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1823 tracepoint(librbd
, list_lockers_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
1824 int r
= librbd::list_lockers(ictx
, lockers
, exclusive
, tag
);
1826 for (std::list
<librbd::locker_t
>::const_iterator it
= lockers
->begin();
1827 it
!= lockers
->end(); ++it
) {
1828 tracepoint(librbd
, list_lockers_entry
, it
->client
.c_str(), it
->cookie
.c_str(), it
->address
.c_str());
1831 tracepoint(librbd
, list_lockers_exit
, r
);
1835 int Image::lock_exclusive(const string
& cookie
)
1837 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1838 tracepoint(librbd
, lock_exclusive_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, cookie
.c_str());
1839 int r
= librbd::lock(ictx
, true, cookie
, "");
1840 tracepoint(librbd
, lock_exclusive_exit
, r
);
1844 int Image::lock_shared(const string
& cookie
, const std::string
& tag
)
1846 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1847 tracepoint(librbd
, lock_shared_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, cookie
.c_str(), tag
.c_str());
1848 int r
= librbd::lock(ictx
, false, cookie
, tag
);
1849 tracepoint(librbd
, lock_shared_exit
, r
);
1853 int Image::unlock(const string
& cookie
)
1855 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1856 tracepoint(librbd
, unlock_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, cookie
.c_str());
1857 int r
= librbd::unlock(ictx
, cookie
);
1858 tracepoint(librbd
, unlock_exit
, r
);
1862 int Image::break_lock(const string
& client
, const string
& cookie
)
1864 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1865 tracepoint(librbd
, break_lock_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, client
.c_str(), cookie
.c_str());
1866 int r
= librbd::break_lock(ictx
, client
, cookie
);
1867 tracepoint(librbd
, break_lock_exit
, r
);
1871 int Image::snap_create(const char *snap_name
)
1873 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1874 tracepoint(librbd
, snap_create_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
1875 int r
= ictx
->operations
->snap_create(cls::rbd::UserSnapshotNamespace(),
1877 tracepoint(librbd
, snap_create_exit
, r
);
1881 int Image::snap_remove(const char *snap_name
)
1883 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1884 tracepoint(librbd
, snap_remove_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
1885 librbd::NoOpProgressContext prog_ctx
;
1886 int r
= librbd::snap_remove(ictx
, snap_name
, 0, prog_ctx
);
1887 tracepoint(librbd
, snap_remove_exit
, r
);
1891 int Image::snap_remove2(const char *snap_name
, uint32_t flags
, ProgressContext
& pctx
)
1893 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1894 tracepoint(librbd
, snap_remove2_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
, flags
);
1895 int r
= librbd::snap_remove(ictx
, snap_name
, flags
, pctx
);
1896 tracepoint(librbd
, snap_remove_exit
, r
);
1900 int Image::snap_remove_by_id(uint64_t snap_id
)
1902 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1903 return librbd::api::Snapshot
<>::remove(ictx
, snap_id
);
1906 int Image::snap_rollback(const char *snap_name
)
1908 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1909 tracepoint(librbd
, snap_rollback_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
1910 librbd::NoOpProgressContext prog_ctx
;
1911 int r
= ictx
->operations
->snap_rollback(cls::rbd::UserSnapshotNamespace(), snap_name
, prog_ctx
);
1912 tracepoint(librbd
, snap_rollback_exit
, r
);
1916 int Image::snap_rename(const char *srcname
, const char *dstname
)
1918 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1919 tracepoint(librbd
, snap_rename_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, srcname
, dstname
);
1920 int r
= ictx
->operations
->snap_rename(srcname
, dstname
);
1921 tracepoint(librbd
, snap_rename_exit
, r
);
1925 int Image::snap_rollback_with_progress(const char *snap_name
,
1926 ProgressContext
& prog_ctx
)
1928 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1929 tracepoint(librbd
, snap_rollback_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
1930 int r
= ictx
->operations
->snap_rollback(cls::rbd::UserSnapshotNamespace(), snap_name
, prog_ctx
);
1931 tracepoint(librbd
, snap_rollback_exit
, r
);
1935 int Image::snap_protect(const char *snap_name
)
1937 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1938 tracepoint(librbd
, snap_protect_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
1939 int r
= ictx
->operations
->snap_protect(cls::rbd::UserSnapshotNamespace(), snap_name
);
1940 tracepoint(librbd
, snap_protect_exit
, r
);
1944 int Image::snap_unprotect(const char *snap_name
)
1946 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1947 tracepoint(librbd
, snap_unprotect_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
1948 int r
= ictx
->operations
->snap_unprotect(cls::rbd::UserSnapshotNamespace(), snap_name
);
1949 tracepoint(librbd
, snap_unprotect_exit
, r
);
1953 int Image::snap_is_protected(const char *snap_name
, bool *is_protected
)
1955 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1956 tracepoint(librbd
, snap_is_protected_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
1957 int r
= librbd::snap_is_protected(ictx
, snap_name
, is_protected
);
1958 tracepoint(librbd
, snap_is_protected_exit
, r
, *is_protected
? 1 : 0);
1962 int Image::snap_list(vector
<librbd::snap_info_t
>& snaps
)
1964 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1965 tracepoint(librbd
, snap_list_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, &snaps
);
1966 int r
= librbd::snap_list(ictx
, snaps
);
1968 for (int i
= 0, n
= snaps
.size(); i
< n
; i
++) {
1969 tracepoint(librbd
, snap_list_entry
, snaps
[i
].id
, snaps
[i
].size
, snaps
[i
].name
.c_str());
1972 tracepoint(librbd
, snap_list_exit
, r
, snaps
.size());
1974 // A little ugly, but the C++ API doesn't need a Image::snap_list_end,
1975 // and we want the tracepoints to mirror the C API
1976 tracepoint(librbd
, snap_list_end_enter
, &snaps
);
1977 tracepoint(librbd
, snap_list_end_exit
);
1982 bool Image::snap_exists(const char *snap_name
)
1984 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
1985 tracepoint(librbd
, snap_exists_enter
, ictx
, ictx
->name
.c_str(),
1986 ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
1988 int r
= librbd::snap_exists(ictx
, cls::rbd::UserSnapshotNamespace(), snap_name
, &exists
);
1989 tracepoint(librbd
, snap_exists_exit
, r
, exists
);
1991 // lie to caller since we don't know the real answer yet.
1997 // A safer verion of snap_exists.
1998 int Image::snap_exists2(const char *snap_name
, bool *exists
)
2000 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2001 tracepoint(librbd
, snap_exists_enter
, ictx
, ictx
->name
.c_str(),
2002 ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
2003 int r
= librbd::snap_exists(ictx
, cls::rbd::UserSnapshotNamespace(), snap_name
, exists
);
2004 tracepoint(librbd
, snap_exists_exit
, r
, *exists
);
2008 int Image::snap_get_timestamp(uint64_t snap_id
, struct timespec
*timestamp
)
2010 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2011 tracepoint(librbd
, snap_get_timestamp_enter
, ictx
, ictx
->name
.c_str());
2012 int r
= librbd::snap_get_timestamp(ictx
, snap_id
, timestamp
);
2013 tracepoint(librbd
, snap_get_timestamp_exit
, r
);
2017 int Image::snap_get_limit(uint64_t *limit
)
2019 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2020 tracepoint(librbd
, snap_get_limit_enter
, ictx
, ictx
->name
.c_str());
2021 int r
= librbd::snap_get_limit(ictx
, limit
);
2022 tracepoint(librbd
, snap_get_limit_exit
, r
, *limit
);
2026 int Image::snap_get_namespace_type(uint64_t snap_id
,
2027 snap_namespace_type_t
*namespace_type
) {
2028 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2029 tracepoint(librbd
, snap_get_namespace_type_enter
, ictx
, ictx
->name
.c_str());
2030 int r
= librbd::api::Snapshot
<>::get_namespace_type(ictx
, snap_id
, namespace_type
);
2031 tracepoint(librbd
, snap_get_namespace_type_exit
, r
);
2035 int Image::snap_get_group_namespace(uint64_t snap_id
,
2036 snap_group_namespace_t
*group_snap
,
2037 size_t group_snap_size
) {
2038 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2039 tracepoint(librbd
, snap_get_group_namespace_enter
, ictx
,
2040 ictx
->name
.c_str());
2042 if (group_snap_size
!= sizeof(snap_group_namespace_t
)) {
2043 tracepoint(librbd
, snap_get_group_namespace_exit
, -ERANGE
);
2047 int r
= librbd::api::Snapshot
<>::get_group_namespace(ictx
, snap_id
,
2049 tracepoint(librbd
, snap_get_group_namespace_exit
, r
);
2053 int Image::snap_get_trash_namespace(uint64_t snap_id
,
2054 std::string
* original_name
) {
2055 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2056 return librbd::api::Snapshot
<>::get_trash_namespace(ictx
, snap_id
,
2060 int Image::snap_set_limit(uint64_t limit
)
2062 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2064 tracepoint(librbd
, snap_set_limit_enter
, ictx
, ictx
->name
.c_str(), limit
);
2065 int r
= ictx
->operations
->snap_set_limit(limit
);
2066 tracepoint(librbd
, snap_set_limit_exit
, r
);
2070 int Image::snap_set(const char *snap_name
)
2072 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2073 tracepoint(librbd
, snap_set_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
2074 int r
= librbd::api::Image
<>::snap_set(
2075 ictx
, cls::rbd::UserSnapshotNamespace(), snap_name
);
2076 tracepoint(librbd
, snap_set_exit
, r
);
2080 int Image::snap_set_by_id(uint64_t snap_id
)
2082 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2083 return librbd::api::Image
<>::snap_set(ictx
, snap_id
);
2086 ssize_t
Image::read(uint64_t ofs
, size_t len
, bufferlist
& bl
)
2088 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2089 tracepoint(librbd
, read_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, ofs
, len
);
2091 bl
.push_back(std::move(ptr
));
2093 int r
= ictx
->io_work_queue
->read(ofs
, len
, io::ReadResult
{&bl
}, 0);
2094 tracepoint(librbd
, read_exit
, r
);
2098 ssize_t
Image::read2(uint64_t ofs
, size_t len
, bufferlist
& bl
, int op_flags
)
2100 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2101 tracepoint(librbd
, read2_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(),
2102 ictx
->read_only
, ofs
, len
, op_flags
);
2104 bl
.push_back(std::move(ptr
));
2106 int r
= ictx
->io_work_queue
->read(ofs
, len
, io::ReadResult
{&bl
}, op_flags
);
2107 tracepoint(librbd
, read_exit
, r
);
2111 int64_t Image::read_iterate(uint64_t ofs
, size_t len
,
2112 int (*cb
)(uint64_t, size_t, const char *, void *),
2115 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2116 tracepoint(librbd
, read_iterate_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, ofs
, len
);
2118 int64_t r
= librbd::read_iterate(ictx
, ofs
, len
, cb
, arg
);
2119 tracepoint(librbd
, read_iterate_exit
, r
);
2123 int Image::read_iterate2(uint64_t ofs
, uint64_t len
,
2124 int (*cb
)(uint64_t, size_t, const char *, void *),
2127 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2128 tracepoint(librbd
, read_iterate2_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, ofs
, len
);
2130 int64_t r
= librbd::read_iterate(ictx
, ofs
, len
, cb
, arg
);
2133 tracepoint(librbd
, read_iterate2_exit
, r
);
2137 int Image::diff_iterate(const char *fromsnapname
,
2138 uint64_t ofs
, uint64_t len
,
2139 int (*cb
)(uint64_t, size_t, int, void *),
2142 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2143 tracepoint(librbd
, diff_iterate_enter
, ictx
, ictx
->name
.c_str(),
2144 ictx
->snap_name
.c_str(), ictx
->read_only
, fromsnapname
, ofs
, len
,
2146 int r
= librbd::api::DiffIterate
<>::diff_iterate(ictx
,
2147 cls::rbd::UserSnapshotNamespace(),
2149 len
, true, false, cb
, arg
);
2150 tracepoint(librbd
, diff_iterate_exit
, r
);
2154 int Image::diff_iterate2(const char *fromsnapname
, uint64_t ofs
, uint64_t len
,
2155 bool include_parent
, bool whole_object
,
2156 int (*cb
)(uint64_t, size_t, int, void *), void *arg
)
2158 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2159 tracepoint(librbd
, diff_iterate_enter
, ictx
, ictx
->name
.c_str(),
2160 ictx
->snap_name
.c_str(), ictx
->read_only
, fromsnapname
, ofs
, len
,
2161 include_parent
, whole_object
);
2162 int r
= librbd::api::DiffIterate
<>::diff_iterate(ictx
,
2163 cls::rbd::UserSnapshotNamespace(),
2165 len
, include_parent
,
2166 whole_object
, cb
, arg
);
2167 tracepoint(librbd
, diff_iterate_exit
, r
);
2171 ssize_t
Image::write(uint64_t ofs
, size_t len
, bufferlist
& bl
)
2173 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2174 tracepoint(librbd
, write_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, ofs
, len
, bl
.length() < len
? NULL
: bl
.c_str());
2175 if (bl
.length() < len
) {
2176 tracepoint(librbd
, write_exit
, -EINVAL
);
2180 int r
= ictx
->io_work_queue
->write(ofs
, len
, bufferlist
{bl
}, 0);
2181 tracepoint(librbd
, write_exit
, r
);
2185 ssize_t
Image::write2(uint64_t ofs
, size_t len
, bufferlist
& bl
, int op_flags
)
2187 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2188 tracepoint(librbd
, write2_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
,
2189 ofs
, len
, bl
.length() < len
? NULL
: bl
.c_str(), op_flags
);
2190 if (bl
.length() < len
) {
2191 tracepoint(librbd
, write_exit
, -EINVAL
);
2195 int r
= ictx
->io_work_queue
->write(ofs
, len
, bufferlist
{bl
}, op_flags
);
2196 tracepoint(librbd
, write_exit
, r
);
2200 int Image::discard(uint64_t ofs
, uint64_t len
)
2202 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2203 tracepoint(librbd
, discard_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, ofs
, len
);
2204 if (len
> std::numeric_limits
<int32_t>::max()) {
2205 tracepoint(librbd
, discard_exit
, -EINVAL
);
2208 int r
= ictx
->io_work_queue
->discard(
2209 ofs
, len
, ictx
->discard_granularity_bytes
);
2210 tracepoint(librbd
, discard_exit
, r
);
2214 ssize_t
Image::writesame(uint64_t ofs
, size_t len
, bufferlist
& bl
, int op_flags
)
2216 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2217 tracepoint(librbd
, writesame_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(),
2218 ictx
->read_only
, ofs
, len
, bl
.length() <= 0 ? NULL
: bl
.c_str(), bl
.length(),
2220 if (bl
.length() <= 0 || len
% bl
.length() ||
2221 len
> std::numeric_limits
<int>::max()) {
2222 tracepoint(librbd
, writesame_exit
, -EINVAL
);
2226 bool discard_zero
= ictx
->config
.get_val
<bool>("rbd_discard_on_zeroed_write_same");
2227 if (discard_zero
&& mem_is_zero(bl
.c_str(), bl
.length())) {
2228 int r
= ictx
->io_work_queue
->discard(ofs
, len
, 0);
2229 tracepoint(librbd
, writesame_exit
, r
);
2233 int r
= ictx
->io_work_queue
->writesame(ofs
, len
, bufferlist
{bl
}, op_flags
);
2234 tracepoint(librbd
, writesame_exit
, r
);
2238 ssize_t
Image::compare_and_write(uint64_t ofs
, size_t len
,
2239 ceph::bufferlist
&cmp_bl
, ceph::bufferlist
& bl
,
2240 uint64_t *mismatch_off
, int op_flags
)
2242 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2243 tracepoint(librbd
, compare_and_write_enter
, ictx
, ictx
->name
.c_str(),
2244 ictx
->snap_name
.c_str(),
2245 ictx
->read_only
, ofs
, len
, cmp_bl
.length() < len
? NULL
: cmp_bl
.c_str(),
2246 bl
.length() < len
? NULL
: bl
.c_str(), op_flags
);
2248 if (bl
.length() < len
) {
2249 tracepoint(librbd
, write_exit
, -EINVAL
);
2253 int r
= ictx
->io_work_queue
->compare_and_write(ofs
, len
, bufferlist
{cmp_bl
},
2254 bufferlist
{bl
}, mismatch_off
,
2257 tracepoint(librbd
, compare_and_write_exit
, r
);
2262 int Image::aio_write(uint64_t off
, size_t len
, bufferlist
& bl
,
2263 RBD::AioCompletion
*c
)
2265 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2266 tracepoint(librbd
, aio_write_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, off
, len
, bl
.length() < len
? NULL
: bl
.c_str(), c
->pc
);
2267 if (bl
.length() < len
) {
2268 tracepoint(librbd
, aio_write_exit
, -EINVAL
);
2271 ictx
->io_work_queue
->aio_write(get_aio_completion(c
), off
, len
,
2274 tracepoint(librbd
, aio_write_exit
, 0);
2278 int Image::aio_write2(uint64_t off
, size_t len
, bufferlist
& bl
,
2279 RBD::AioCompletion
*c
, int op_flags
)
2281 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2282 tracepoint(librbd
, aio_write2_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(),
2283 ictx
->read_only
, off
, len
, bl
.length() < len
? NULL
: bl
.c_str(), c
->pc
, op_flags
);
2284 if (bl
.length() < len
) {
2285 tracepoint(librbd
, aio_write_exit
, -EINVAL
);
2288 ictx
->io_work_queue
->aio_write(get_aio_completion(c
), off
, len
,
2289 bufferlist
{bl
}, op_flags
);
2291 tracepoint(librbd
, aio_write_exit
, 0);
2295 int Image::aio_discard(uint64_t off
, uint64_t len
, RBD::AioCompletion
*c
)
2297 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2298 tracepoint(librbd
, aio_discard_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, off
, len
, c
->pc
);
2299 ictx
->io_work_queue
->aio_discard(
2300 get_aio_completion(c
), off
, len
, ictx
->discard_granularity_bytes
);
2301 tracepoint(librbd
, aio_discard_exit
, 0);
2305 int Image::aio_read(uint64_t off
, size_t len
, bufferlist
& bl
,
2306 RBD::AioCompletion
*c
)
2308 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2309 tracepoint(librbd
, aio_read_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, off
, len
, bl
.c_str(), c
->pc
);
2310 ldout(ictx
->cct
, 10) << "Image::aio_read() buf=" << (void *)bl
.c_str() << "~"
2311 << (void *)(bl
.c_str() + len
- 1) << dendl
;
2313 ictx
->io_work_queue
->aio_read(get_aio_completion(c
), off
, len
,
2314 io::ReadResult
{&bl
}, 0);
2315 tracepoint(librbd
, aio_read_exit
, 0);
2319 int Image::aio_read2(uint64_t off
, size_t len
, bufferlist
& bl
,
2320 RBD::AioCompletion
*c
, int op_flags
)
2322 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2323 tracepoint(librbd
, aio_read2_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(),
2324 ictx
->read_only
, off
, len
, bl
.c_str(), c
->pc
, op_flags
);
2325 ldout(ictx
->cct
, 10) << "Image::aio_read() buf=" << (void *)bl
.c_str() << "~"
2326 << (void *)(bl
.c_str() + len
- 1) << dendl
;
2328 ictx
->io_work_queue
->aio_read(get_aio_completion(c
), off
, len
,
2329 io::ReadResult
{&bl
}, op_flags
);
2330 tracepoint(librbd
, aio_read_exit
, 0);
2336 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2337 tracepoint(librbd
, flush_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
2338 int r
= ictx
->io_work_queue
->flush();
2339 tracepoint(librbd
, flush_exit
, r
);
2343 int Image::aio_flush(RBD::AioCompletion
*c
)
2345 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2346 tracepoint(librbd
, aio_flush_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, c
->pc
);
2347 ictx
->io_work_queue
->aio_flush(get_aio_completion(c
));
2348 tracepoint(librbd
, aio_flush_exit
, 0);
2352 int Image::aio_writesame(uint64_t off
, size_t len
, bufferlist
& bl
,
2353 RBD::AioCompletion
*c
, int op_flags
)
2355 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2356 tracepoint(librbd
, aio_writesame_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(),
2357 ictx
->read_only
, off
, len
, bl
.length() <= len
? NULL
: bl
.c_str(), bl
.length(),
2359 if (bl
.length() <= 0 || len
% bl
.length()) {
2360 tracepoint(librbd
, aio_writesame_exit
, -EINVAL
);
2364 bool discard_zero
= ictx
->config
.get_val
<bool>("rbd_discard_on_zeroed_write_same");
2365 if (discard_zero
&& mem_is_zero(bl
.c_str(), bl
.length())) {
2366 ictx
->io_work_queue
->aio_discard(get_aio_completion(c
), off
, len
, 0);
2367 tracepoint(librbd
, aio_writesame_exit
, 0);
2371 ictx
->io_work_queue
->aio_writesame(get_aio_completion(c
), off
, len
,
2372 bufferlist
{bl
}, op_flags
);
2373 tracepoint(librbd
, aio_writesame_exit
, 0);
2377 int Image::aio_compare_and_write(uint64_t off
, size_t len
,
2378 ceph::bufferlist
& cmp_bl
, ceph::bufferlist
& bl
,
2379 RBD::AioCompletion
*c
, uint64_t *mismatch_off
,
2382 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2383 tracepoint(librbd
, aio_compare_and_write_enter
, ictx
, ictx
->name
.c_str(),
2384 ictx
->snap_name
.c_str(),
2385 ictx
->read_only
, off
, len
, cmp_bl
.length() < len
? NULL
: cmp_bl
.c_str(),
2386 bl
.length() < len
? NULL
: bl
.c_str(), c
->pc
, op_flags
);
2388 if (bl
.length() < len
) {
2389 tracepoint(librbd
, compare_and_write_exit
, -EINVAL
);
2393 ictx
->io_work_queue
->aio_compare_and_write(get_aio_completion(c
), off
, len
,
2394 bufferlist
{cmp_bl
}, bufferlist
{bl
},
2395 mismatch_off
, op_flags
, false);
2397 tracepoint(librbd
, aio_compare_and_write_exit
, 0);
2402 int Image::invalidate_cache()
2404 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2405 tracepoint(librbd
, invalidate_cache_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
2406 int r
= librbd::invalidate_cache(ictx
);
2407 tracepoint(librbd
, invalidate_cache_exit
, r
);
2411 int Image::poll_io_events(RBD::AioCompletion
**comps
, int numcomp
)
2413 io::AioCompletion
*cs
[numcomp
];
2414 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2415 tracepoint(librbd
, poll_io_events_enter
, ictx
, numcomp
);
2416 int r
= librbd::poll_io_events(ictx
, cs
, numcomp
);
2417 tracepoint(librbd
, poll_io_events_exit
, r
);
2419 for (int i
= 0; i
< r
; ++i
)
2420 comps
[i
] = (RBD::AioCompletion
*)cs
[i
]->rbd_comp
;
2425 int Image::metadata_get(const std::string
&key
, std::string
*value
)
2427 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2428 tracepoint(librbd
, metadata_get_enter
, ictx
, key
.c_str());
2429 int r
= librbd::metadata_get(ictx
, key
, value
);
2431 tracepoint(librbd
, metadata_get_exit
, r
, key
.c_str(), NULL
);
2433 tracepoint(librbd
, metadata_get_exit
, r
, key
.c_str(), value
->c_str());
2438 int Image::metadata_set(const std::string
&key
, const std::string
&value
)
2440 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2441 tracepoint(librbd
, metadata_set_enter
, ictx
, key
.c_str(), value
.c_str());
2442 int r
= ictx
->operations
->metadata_set(key
, value
);
2443 tracepoint(librbd
, metadata_set_exit
, r
);
2447 int Image::metadata_remove(const std::string
&key
)
2449 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2450 tracepoint(librbd
, metadata_remove_enter
, ictx
, key
.c_str());
2451 int r
= ictx
->operations
->metadata_remove(key
);
2452 tracepoint(librbd
, metadata_remove_exit
, r
);
2456 int Image::metadata_list(const std::string
&start
, uint64_t max
, map
<string
, bufferlist
> *pairs
)
2458 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2459 tracepoint(librbd
, metadata_list_enter
, ictx
);
2460 int r
= librbd::metadata_list(ictx
, start
, max
, pairs
);
2462 for (map
<string
, bufferlist
>::iterator it
= pairs
->begin();
2463 it
!= pairs
->end(); ++it
) {
2464 tracepoint(librbd
, metadata_list_entry
, it
->first
.c_str(), it
->second
.c_str());
2467 tracepoint(librbd
, metadata_list_exit
, r
);
2471 int Image::mirror_image_enable() {
2472 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2473 return librbd::api::Mirror
<>::image_enable(ictx
, false);
2476 int Image::mirror_image_disable(bool force
) {
2477 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2478 return librbd::api::Mirror
<>::image_disable(ictx
, force
);
2481 int Image::mirror_image_promote(bool force
) {
2482 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2483 return librbd::api::Mirror
<>::image_promote(ictx
, force
);
2486 int Image::mirror_image_demote() {
2487 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2488 return librbd::api::Mirror
<>::image_demote(ictx
);
2491 int Image::mirror_image_resync()
2493 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2494 return librbd::api::Mirror
<>::image_resync(ictx
);
2497 int Image::mirror_image_get_info(mirror_image_info_t
*mirror_image_info
,
2499 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2501 if (sizeof(mirror_image_info_t
) != info_size
) {
2505 return librbd::api::Mirror
<>::image_get_info(ictx
, mirror_image_info
);
2508 int Image::mirror_image_get_status(mirror_image_status_t
*mirror_image_status
,
2509 size_t status_size
) {
2510 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2512 if (sizeof(mirror_image_status_t
) != status_size
) {
2516 return librbd::api::Mirror
<>::image_get_status(ictx
, mirror_image_status
);
2519 int Image::mirror_image_get_instance_id(std::string
*instance_id
) {
2520 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2522 return librbd::api::Mirror
<>::image_get_instance_id(ictx
, instance_id
);
2525 int Image::aio_mirror_image_promote(bool force
, RBD::AioCompletion
*c
) {
2526 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2527 librbd::api::Mirror
<>::image_promote(
2528 ictx
, force
, new C_AioCompletion(ictx
, librbd::io::AIO_TYPE_GENERIC
,
2529 get_aio_completion(c
)));
2533 int Image::aio_mirror_image_demote(RBD::AioCompletion
*c
) {
2534 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2535 librbd::api::Mirror
<>::image_demote(
2536 ictx
, new C_AioCompletion(ictx
, librbd::io::AIO_TYPE_GENERIC
,
2537 get_aio_completion(c
)));
2541 int Image::aio_mirror_image_get_info(mirror_image_info_t
*mirror_image_info
,
2543 RBD::AioCompletion
*c
) {
2544 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2546 if (sizeof(mirror_image_info_t
) != info_size
) {
2550 librbd::api::Mirror
<>::image_get_info(
2551 ictx
, mirror_image_info
,
2552 new C_AioCompletion(ictx
, librbd::io::AIO_TYPE_GENERIC
,
2553 get_aio_completion(c
)));
2557 int Image::aio_mirror_image_get_status(mirror_image_status_t
*status
,
2559 RBD::AioCompletion
*c
) {
2560 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2562 if (sizeof(mirror_image_status_t
) != status_size
) {
2566 librbd::api::Mirror
<>::image_get_status(
2567 ictx
, status
, new C_AioCompletion(ictx
, librbd::io::AIO_TYPE_GENERIC
,
2568 get_aio_completion(c
)));
2572 int Image::update_watch(UpdateWatchCtx
*wctx
, uint64_t *handle
) {
2573 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2574 tracepoint(librbd
, update_watch_enter
, ictx
, wctx
);
2575 int r
= ictx
->state
->register_update_watcher(wctx
, handle
);
2576 tracepoint(librbd
, update_watch_exit
, r
, *handle
);
2580 int Image::update_unwatch(uint64_t handle
) {
2581 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2582 tracepoint(librbd
, update_unwatch_enter
, ictx
, handle
);
2583 int r
= ictx
->state
->unregister_update_watcher(handle
);
2584 tracepoint(librbd
, update_unwatch_exit
, r
);
2588 int Image::list_watchers(std::list
<librbd::image_watcher_t
> &watchers
) {
2589 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2590 tracepoint(librbd
, list_watchers_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
2591 int r
= librbd::list_watchers(ictx
, watchers
);
2593 for (auto &watcher
: watchers
) {
2594 tracepoint(librbd
, list_watchers_entry
, watcher
.addr
.c_str(), watcher
.id
, watcher
.cookie
);
2597 tracepoint(librbd
, list_watchers_exit
, r
, watchers
.size());
2601 int Image::config_list(std::vector
<config_option_t
> *options
) {
2602 ImageCtx
*ictx
= (ImageCtx
*)ctx
;
2603 return librbd::api::Config
<>::list(ictx
, options
);
2606 } // namespace librbd
2608 extern "C" void rbd_version(int *major
, int *minor
, int *extra
)
2611 *major
= LIBRBD_VER_MAJOR
;
2613 *minor
= LIBRBD_VER_MINOR
;
2615 *extra
= LIBRBD_VER_EXTRA
;
2618 extern "C" void rbd_image_options_create(rbd_image_options_t
* opts
)
2620 librbd::image_options_create(opts
);
2623 extern "C" void rbd_image_options_destroy(rbd_image_options_t opts
)
2625 librbd::image_options_destroy(opts
);
2628 extern "C" int rbd_image_options_set_string(rbd_image_options_t opts
, int optname
,
2631 return librbd::image_options_set(opts
, optname
, optval
);
2634 extern "C" int rbd_image_options_set_uint64(rbd_image_options_t opts
, int optname
,
2637 return librbd::image_options_set(opts
, optname
, optval
);
2640 extern "C" int rbd_image_options_get_string(rbd_image_options_t opts
, int optname
,
2641 char* optval
, size_t maxlen
)
2643 std::string optval_
;
2645 int r
= librbd::image_options_get(opts
, optname
, &optval_
);
2651 if (optval_
.size() >= maxlen
) {
2655 strncpy(optval
, optval_
.c_str(), maxlen
);
2660 extern "C" int rbd_image_options_get_uint64(rbd_image_options_t opts
, int optname
,
2663 return librbd::image_options_get(opts
, optname
, optval
);
2666 extern "C" int rbd_image_options_is_set(rbd_image_options_t opts
, int optname
,
2669 return librbd::image_options_is_set(opts
, optname
, is_set
);
2672 extern "C" int rbd_image_options_unset(rbd_image_options_t opts
, int optname
)
2674 return librbd::image_options_unset(opts
, optname
);
2677 extern "C" void rbd_image_options_clear(rbd_image_options_t opts
)
2679 librbd::image_options_clear(opts
);
2682 extern "C" int rbd_image_options_is_empty(rbd_image_options_t opts
)
2684 return librbd::image_options_is_empty(opts
);
2687 /* pool mirroring */
2688 extern "C" int rbd_mirror_mode_get(rados_ioctx_t p
,
2689 rbd_mirror_mode_t
*mirror_mode
) {
2690 librados::IoCtx io_ctx
;
2691 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
2692 return librbd::api::Mirror
<>::mode_get(io_ctx
, mirror_mode
);
2695 extern "C" int rbd_mirror_mode_set(rados_ioctx_t p
,
2696 rbd_mirror_mode_t mirror_mode
) {
2697 librados::IoCtx io_ctx
;
2698 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
2699 return librbd::api::Mirror
<>::mode_set(io_ctx
, mirror_mode
);
2702 extern "C" int rbd_mirror_peer_add(rados_ioctx_t p
, char *uuid
,
2703 size_t uuid_max_length
,
2704 const char *cluster_name
,
2705 const char *client_name
) {
2706 static const std::size_t UUID_LENGTH
= 36;
2708 librados::IoCtx io_ctx
;
2709 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
2711 if (uuid_max_length
< UUID_LENGTH
+ 1) {
2715 std::string uuid_str
;
2716 int r
= librbd::api::Mirror
<>::peer_add(io_ctx
, &uuid_str
, cluster_name
,
2719 strncpy(uuid
, uuid_str
.c_str(), uuid_max_length
);
2720 uuid
[uuid_max_length
- 1] = '\0';
2725 extern "C" int rbd_mirror_peer_remove(rados_ioctx_t p
, const char *uuid
) {
2726 librados::IoCtx io_ctx
;
2727 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
2728 int r
= librbd::api::Mirror
<>::peer_remove(io_ctx
, uuid
);
2732 extern "C" int rbd_mirror_peer_list(rados_ioctx_t p
,
2733 rbd_mirror_peer_t
*peers
, int *max_peers
) {
2734 librados::IoCtx io_ctx
;
2735 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
2737 std::vector
<librbd::mirror_peer_t
> peer_vector
;
2738 int r
= librbd::api::Mirror
<>::peer_list(io_ctx
, &peer_vector
);
2743 if (*max_peers
< static_cast<int>(peer_vector
.size())) {
2744 *max_peers
= static_cast<int>(peer_vector
.size());
2748 for (int i
= 0; i
< static_cast<int>(peer_vector
.size()); ++i
) {
2749 peers
[i
].uuid
= strdup(peer_vector
[i
].uuid
.c_str());
2750 peers
[i
].cluster_name
= strdup(peer_vector
[i
].cluster_name
.c_str());
2751 peers
[i
].client_name
= strdup(peer_vector
[i
].client_name
.c_str());
2753 *max_peers
= static_cast<int>(peer_vector
.size());
2757 extern "C" void rbd_mirror_peer_list_cleanup(rbd_mirror_peer_t
*peers
,
2759 for (int i
= 0; i
< max_peers
; ++i
) {
2760 free(peers
[i
].uuid
);
2761 free(peers
[i
].cluster_name
);
2762 free(peers
[i
].client_name
);
2766 extern "C" int rbd_mirror_peer_set_client(rados_ioctx_t p
, const char *uuid
,
2767 const char *client_name
) {
2768 librados::IoCtx io_ctx
;
2769 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
2770 return librbd::api::Mirror
<>::peer_set_client(io_ctx
, uuid
, client_name
);
2773 extern "C" int rbd_mirror_peer_set_cluster(rados_ioctx_t p
, const char *uuid
,
2774 const char *cluster_name
) {
2775 librados::IoCtx io_ctx
;
2776 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
2777 return librbd::api::Mirror
<>::peer_set_cluster(io_ctx
, uuid
, cluster_name
);
2780 extern "C" int rbd_mirror_peer_get_attributes(
2781 rados_ioctx_t p
, const char *uuid
, char *keys
, size_t *max_key_len
,
2782 char *values
, size_t *max_val_len
, size_t *key_value_count
) {
2783 librados::IoCtx io_ctx
;
2784 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
2786 std::map
<std::string
, std::string
> attributes
;
2787 int r
= librbd::api::Mirror
<>::peer_get_attributes(io_ctx
, uuid
, &attributes
);
2792 size_t key_total_len
= 0, val_total_len
= 0;
2793 for (auto& it
: attributes
) {
2794 key_total_len
+= it
.first
.size() + 1;
2795 val_total_len
+= it
.second
.length() + 1;
2798 bool too_short
= ((*max_key_len
< key_total_len
) ||
2799 (*max_val_len
< val_total_len
));
2801 *max_key_len
= key_total_len
;
2802 *max_val_len
= val_total_len
;
2803 *key_value_count
= attributes
.size();
2808 char *keys_p
= keys
;
2809 char *values_p
= values
;
2810 for (auto& it
: attributes
) {
2811 strncpy(keys_p
, it
.first
.c_str(), it
.first
.size() + 1);
2812 keys_p
+= it
.first
.size() + 1;
2814 strncpy(values_p
, it
.second
.c_str(), it
.second
.length() + 1);
2815 values_p
+= it
.second
.length() + 1;
2821 extern "C" int rbd_mirror_peer_set_attributes(
2822 rados_ioctx_t p
, const char *uuid
, const char *keys
, const char *values
,
2824 librados::IoCtx io_ctx
;
2825 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
2827 std::map
<std::string
, std::string
> attributes
;
2829 for (size_t i
= 0; i
< count
; ++i
) {
2830 const char* key
= keys
;
2831 keys
+= strlen(key
) + 1;
2832 const char* value
= values
;
2833 values
+= strlen(value
) + 1;
2834 attributes
[key
] = value
;
2837 return librbd::api::Mirror
<>::peer_set_attributes(io_ctx
, uuid
, attributes
);
2840 extern "C" int rbd_mirror_image_status_list(rados_ioctx_t p
,
2841 const char *start_id
, size_t max
, char **image_ids
,
2842 rbd_mirror_image_status_t
*images
, size_t *len
) {
2843 librados::IoCtx io_ctx
;
2844 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
2845 std::map
<std::string
, librbd::mirror_image_status_t
> cpp_images
;
2847 int r
= librbd::api::Mirror
<>::image_status_list(io_ctx
, start_id
, max
,
2854 for (auto &it
: cpp_images
) {
2855 ceph_assert(i
< max
);
2856 const std::string
&image_id
= it
.first
;
2857 image_ids
[i
] = strdup(image_id
.c_str());
2858 mirror_image_status_cpp_to_c(it
.second
, &images
[i
]);
2865 extern "C" void rbd_mirror_image_status_list_cleanup(char **image_ids
,
2866 rbd_mirror_image_status_t
*images
, size_t len
) {
2867 for (size_t i
= 0; i
< len
; i
++) {
2869 free(images
[i
].name
);
2870 free(images
[i
].info
.global_id
);
2871 free(images
[i
].description
);
2875 extern "C" int rbd_mirror_image_status_summary(rados_ioctx_t p
,
2876 rbd_mirror_image_status_state_t
*states
, int *counts
, size_t *maxlen
) {
2878 librados::IoCtx io_ctx
;
2879 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
2881 std::map
<librbd::mirror_image_status_state_t
, int> states_
;
2882 int r
= librbd::api::Mirror
<>::image_status_summary(io_ctx
, &states_
);
2888 for (auto &it
: states_
) {
2892 states
[i
] = it
.first
;
2893 counts
[i
] = it
.second
;
2900 extern "C" int rbd_mirror_image_instance_id_list(
2901 rados_ioctx_t p
, const char *start_id
, size_t max
, char **image_ids
,
2902 char **instance_ids
, size_t *len
) {
2903 librados::IoCtx io_ctx
;
2904 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
2905 std::map
<std::string
, std::string
> cpp_instance_ids
;
2907 int r
= librbd::api::Mirror
<>::image_instance_id_list(io_ctx
, start_id
, max
,
2914 for (auto &it
: cpp_instance_ids
) {
2915 ceph_assert(i
< max
);
2916 image_ids
[i
] = strdup(it
.first
.c_str());
2917 instance_ids
[i
] = strdup(it
.second
.c_str());
2924 extern "C" void rbd_mirror_image_instance_id_list_cleanup(
2925 char **image_ids
, char **instance_ids
, size_t len
) {
2926 for (size_t i
= 0; i
< len
; i
++) {
2928 free(instance_ids
[i
]);
2934 extern "C" void rbd_image_spec_cleanup(rbd_image_spec_t
*image
)
2940 extern "C" void rbd_image_spec_list_cleanup(rbd_image_spec_t
*images
,
2943 for (size_t idx
= 0; idx
< num_images
; ++idx
) {
2944 rbd_image_spec_cleanup(&images
[idx
]);
2948 extern "C" void rbd_linked_image_spec_cleanup(rbd_linked_image_spec_t
*image
)
2950 free(image
->pool_name
);
2951 free(image
->pool_namespace
);
2952 free(image
->image_id
);
2953 free(image
->image_name
);
2956 extern "C" void rbd_linked_image_spec_list_cleanup(
2957 rbd_linked_image_spec_t
*images
, size_t num_images
)
2959 for (size_t idx
= 0; idx
< num_images
; ++idx
) {
2960 rbd_linked_image_spec_cleanup(&images
[idx
]);
2964 extern "C" void rbd_snap_spec_cleanup(rbd_snap_spec_t
*snap
)
2970 extern "C" int rbd_list(rados_ioctx_t p
, char *names
, size_t *size
)
2972 librados::IoCtx io_ctx
;
2973 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
2975 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
2976 tracepoint(librbd
, list_enter
, io_ctx
.get_pool_name().c_str(),
2978 std::vector
<librbd::image_spec_t
> cpp_image_specs
;
2979 int r
= librbd::api::Image
<>::list_images(io_ctx
, &cpp_image_specs
);
2981 tracepoint(librbd
, list_exit
, r
, *size
);
2985 size_t expected_size
= 0;
2987 for (auto& it
: cpp_image_specs
) {
2988 expected_size
+= it
.name
.size() + 1;
2990 if (*size
< expected_size
) {
2991 *size
= expected_size
;
2992 tracepoint(librbd
, list_exit
, -ERANGE
, *size
);
2996 if (names
== NULL
) {
2997 tracepoint(librbd
, list_exit
, -EINVAL
, *size
);
3001 for (auto& it
: cpp_image_specs
) {
3002 const char* name
= it
.name
.c_str();
3003 tracepoint(librbd
, list_entry
, name
);
3004 strcpy(names
, name
);
3005 names
+= strlen(names
) + 1;
3007 tracepoint(librbd
, list_exit
, (int)expected_size
, *size
);
3008 return (int)expected_size
;
3011 extern "C" int rbd_list2(rados_ioctx_t p
, rbd_image_spec_t
*images
,
3014 librados::IoCtx io_ctx
;
3015 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3017 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3018 tracepoint(librbd
, list_enter
, io_ctx
.get_pool_name().c_str(),
3020 memset(images
, 0, sizeof(*images
) * *size
);
3021 std::vector
<librbd::image_spec_t
> cpp_image_specs
;
3022 int r
= librbd::api::Image
<>::list_images(io_ctx
, &cpp_image_specs
);
3024 tracepoint(librbd
, list_exit
, r
, *size
);
3028 size_t expected_size
= cpp_image_specs
.size();
3029 if (*size
< expected_size
) {
3030 *size
= expected_size
;
3031 tracepoint(librbd
, list_exit
, -ERANGE
, *size
);
3035 *size
= expected_size
;
3036 for (size_t idx
= 0; idx
< expected_size
; ++idx
) {
3037 images
[idx
].id
= strdup(cpp_image_specs
[idx
].id
.c_str());
3038 images
[idx
].name
= strdup(cpp_image_specs
[idx
].name
.c_str());
3040 tracepoint(librbd
, list_exit
, 0, *size
);
3044 extern "C" int rbd_create(rados_ioctx_t p
, const char *name
, uint64_t size
, int *order
)
3046 librados::IoCtx io_ctx
;
3047 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3048 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3049 tracepoint(librbd
, create_enter
, io_ctx
.get_pool_name().c_str(), io_ctx
.get_id(), name
, size
, *order
);
3050 int r
= librbd::create(io_ctx
, name
, size
, order
);
3051 tracepoint(librbd
, create_exit
, r
, *order
);
3055 extern "C" int rbd_create2(rados_ioctx_t p
, const char *name
,
3056 uint64_t size
, uint64_t features
,
3059 librados::IoCtx io_ctx
;
3060 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3061 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3062 tracepoint(librbd
, create2_enter
, io_ctx
.get_pool_name().c_str(), io_ctx
.get_id(), name
, size
, features
, *order
);
3063 int r
= librbd::create(io_ctx
, name
, size
, false, features
, order
, 0, 0);
3064 tracepoint(librbd
, create2_exit
, r
, *order
);
3068 extern "C" int rbd_create3(rados_ioctx_t p
, const char *name
,
3069 uint64_t size
, uint64_t features
,
3071 uint64_t stripe_unit
, uint64_t stripe_count
)
3073 librados::IoCtx io_ctx
;
3074 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3075 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3076 tracepoint(librbd
, create3_enter
, io_ctx
.get_pool_name().c_str(), io_ctx
.get_id(), name
, size
, features
, *order
, stripe_unit
, stripe_count
);
3077 int r
= librbd::create(io_ctx
, name
, size
, false, features
, order
,
3078 stripe_unit
, stripe_count
);
3079 tracepoint(librbd
, create3_exit
, r
, *order
);
3083 extern "C" int rbd_create4(rados_ioctx_t p
, const char *name
,
3084 uint64_t size
, rbd_image_options_t opts
)
3086 librados::IoCtx io_ctx
;
3087 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3088 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3089 tracepoint(librbd
, create4_enter
, io_ctx
.get_pool_name().c_str(), io_ctx
.get_id(), name
, size
, opts
);
3090 librbd::ImageOptions
opts_(opts
);
3091 int r
= librbd::create(io_ctx
, name
, "", size
, opts_
, "", "", false);
3092 tracepoint(librbd
, create4_exit
, r
);
3096 extern "C" int rbd_clone(rados_ioctx_t p_ioctx
, const char *p_name
,
3097 const char *p_snap_name
, rados_ioctx_t c_ioctx
,
3098 const char *c_name
, uint64_t features
, int *c_order
)
3100 librados::IoCtx p_ioc
, c_ioc
;
3101 librados::IoCtx::from_rados_ioctx_t(p_ioctx
, p_ioc
);
3102 librados::IoCtx::from_rados_ioctx_t(c_ioctx
, c_ioc
);
3103 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(p_ioc
));
3104 tracepoint(librbd
, clone_enter
, p_ioc
.get_pool_name().c_str(), p_ioc
.get_id(), p_name
, p_snap_name
, c_ioc
.get_pool_name().c_str(), c_ioc
.get_id(), c_name
, features
);
3105 int r
= librbd::clone(p_ioc
, p_name
, p_snap_name
, c_ioc
, c_name
,
3106 features
, c_order
, 0, 0);
3107 tracepoint(librbd
, clone_exit
, r
, *c_order
);
3111 extern "C" int rbd_clone2(rados_ioctx_t p_ioctx
, const char *p_name
,
3112 const char *p_snap_name
, rados_ioctx_t c_ioctx
,
3113 const char *c_name
, uint64_t features
, int *c_order
,
3114 uint64_t stripe_unit
, int stripe_count
)
3116 librados::IoCtx p_ioc
, c_ioc
;
3117 librados::IoCtx::from_rados_ioctx_t(p_ioctx
, p_ioc
);
3118 librados::IoCtx::from_rados_ioctx_t(c_ioctx
, c_ioc
);
3119 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(p_ioc
));
3120 tracepoint(librbd
, clone2_enter
, p_ioc
.get_pool_name().c_str(), p_ioc
.get_id(), p_name
, p_snap_name
, c_ioc
.get_pool_name().c_str(), c_ioc
.get_id(), c_name
, features
, stripe_unit
, stripe_count
);
3121 int r
= librbd::clone(p_ioc
, p_name
, p_snap_name
, c_ioc
, c_name
,
3122 features
, c_order
, stripe_unit
, stripe_count
);
3123 tracepoint(librbd
, clone2_exit
, r
, *c_order
);
3127 extern "C" int rbd_clone3(rados_ioctx_t p_ioctx
, const char *p_name
,
3128 const char *p_snap_name
, rados_ioctx_t c_ioctx
,
3129 const char *c_name
, rbd_image_options_t c_opts
)
3131 librados::IoCtx p_ioc
, c_ioc
;
3132 librados::IoCtx::from_rados_ioctx_t(p_ioctx
, p_ioc
);
3133 librados::IoCtx::from_rados_ioctx_t(c_ioctx
, c_ioc
);
3134 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(p_ioc
));
3135 tracepoint(librbd
, clone3_enter
, p_ioc
.get_pool_name().c_str(), p_ioc
.get_id(), p_name
, p_snap_name
, c_ioc
.get_pool_name().c_str(), c_ioc
.get_id(), c_name
, c_opts
);
3136 librbd::ImageOptions
c_opts_(c_opts
);
3137 int r
= librbd::clone(p_ioc
, nullptr, p_name
, p_snap_name
, c_ioc
, nullptr,
3138 c_name
, c_opts_
, "", "");
3139 tracepoint(librbd
, clone3_exit
, r
);
3143 extern "C" int rbd_remove(rados_ioctx_t p
, const char *name
)
3145 librados::IoCtx io_ctx
;
3146 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3147 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3148 tracepoint(librbd
, remove_enter
, io_ctx
.get_pool_name().c_str(), io_ctx
.get_id(), name
);
3149 librbd::NoOpProgressContext prog_ctx
;
3150 int r
= librbd::api::Image
<>::remove(io_ctx
, name
, prog_ctx
);
3151 tracepoint(librbd
, remove_exit
, r
);
3155 extern "C" int rbd_remove_with_progress(rados_ioctx_t p
, const char *name
,
3156 librbd_progress_fn_t cb
, void *cbdata
)
3158 librados::IoCtx io_ctx
;
3159 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3160 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3161 tracepoint(librbd
, remove_enter
, io_ctx
.get_pool_name().c_str(), io_ctx
.get_id(), name
);
3162 librbd::CProgressContext
prog_ctx(cb
, cbdata
);
3163 int r
= librbd::api::Image
<>::remove(io_ctx
, name
, prog_ctx
);
3164 tracepoint(librbd
, remove_exit
, r
);
3168 extern "C" int rbd_trash_move(rados_ioctx_t p
, const char *name
,
3170 librados::IoCtx io_ctx
;
3171 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3172 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3173 tracepoint(librbd
, trash_move_enter
, io_ctx
.get_pool_name().c_str(),
3174 io_ctx
.get_id(), name
);
3175 int r
= librbd::api::Trash
<>::move(io_ctx
, RBD_TRASH_IMAGE_SOURCE_USER
, name
,
3177 tracepoint(librbd
, trash_move_exit
, r
);
3181 extern "C" int rbd_trash_get(rados_ioctx_t io
, const char *id
,
3182 rbd_trash_image_info_t
*info
) {
3183 librados::IoCtx io_ctx
;
3184 librados::IoCtx::from_rados_ioctx_t(io
, io_ctx
);
3186 librbd::trash_image_info_t cpp_info
;
3187 int r
= librbd::api::Trash
<>::get(io_ctx
, id
, &cpp_info
);
3192 trash_image_info_cpp_to_c(cpp_info
, info
);
3196 extern "C" void rbd_trash_get_cleanup(rbd_trash_image_info_t
*info
) {
3201 extern "C" int rbd_trash_list(rados_ioctx_t p
, rbd_trash_image_info_t
*entries
,
3202 size_t *num_entries
) {
3203 librados::IoCtx io_ctx
;
3204 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3205 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3206 tracepoint(librbd
, trash_list_enter
,
3207 io_ctx
.get_pool_name().c_str(), io_ctx
.get_id());
3208 memset(entries
, 0, sizeof(*entries
) * *num_entries
);
3210 vector
<librbd::trash_image_info_t
> cpp_entries
;
3211 int r
= librbd::api::Trash
<>::list(io_ctx
, cpp_entries
, true);
3213 tracepoint(librbd
, trash_list_exit
, r
, *num_entries
);
3217 if (*num_entries
< cpp_entries
.size()) {
3218 *num_entries
= cpp_entries
.size();
3219 tracepoint(librbd
, trash_list_exit
, -ERANGE
, *num_entries
);
3224 for (const auto &entry
: cpp_entries
) {
3225 trash_image_info_cpp_to_c(entry
, &entries
[i
++]);
3227 *num_entries
= cpp_entries
.size();
3229 return *num_entries
;
3232 extern "C" void rbd_trash_list_cleanup(rbd_trash_image_info_t
*entries
,
3233 size_t num_entries
) {
3234 for (size_t i
=0; i
< num_entries
; i
++) {
3235 rbd_trash_get_cleanup(&entries
[i
]);
3239 extern "C" int rbd_trash_purge(rados_ioctx_t io
, time_t expire_ts
,
3241 librados::IoCtx io_ctx
;
3242 librados::IoCtx::from_rados_ioctx_t(io
, io_ctx
);
3243 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3244 tracepoint(librbd
, trash_purge_enter
, io_ctx
.get_pool_name().c_str(),
3245 io_ctx
.get_id(), expire_ts
, threshold
);
3246 librbd::NoOpProgressContext nop_pctx
;
3247 int r
= librbd::api::Trash
<>::purge(io_ctx
, expire_ts
, threshold
, nop_pctx
);
3248 tracepoint(librbd
, trash_purge_exit
, r
);
3252 extern "C" int rbd_trash_purge_with_progress(rados_ioctx_t io
, time_t expire_ts
,
3253 float threshold
, librbd_progress_fn_t cb
, void* cbdata
) {
3254 librados::IoCtx io_ctx
;
3255 librados::IoCtx::from_rados_ioctx_t(io
, io_ctx
);
3256 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3257 tracepoint(librbd
, trash_purge_enter
, io_ctx
.get_pool_name().c_str(),
3258 io_ctx
.get_id(), expire_ts
, threshold
);
3259 librbd::CProgressContext
pctx(cb
, cbdata
);
3260 int r
= librbd::api::Trash
<>::purge(io_ctx
, expire_ts
, threshold
, pctx
);
3261 tracepoint(librbd
, trash_purge_exit
, r
);
3265 extern "C" int rbd_trash_remove(rados_ioctx_t p
, const char *image_id
,
3267 librados::IoCtx io_ctx
;
3268 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3269 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3270 tracepoint(librbd
, trash_remove_enter
, io_ctx
.get_pool_name().c_str(),
3271 io_ctx
.get_id(), image_id
, force
);
3272 librbd::NoOpProgressContext prog_ctx
;
3273 int r
= librbd::api::Trash
<>::remove(io_ctx
, image_id
, force
, prog_ctx
);
3274 tracepoint(librbd
, trash_remove_exit
, r
);
3278 extern "C" int rbd_trash_remove_with_progress(rados_ioctx_t p
,
3279 const char *image_id
,
3281 librbd_progress_fn_t cb
,
3283 librados::IoCtx io_ctx
;
3284 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3285 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3286 tracepoint(librbd
, trash_remove_enter
, io_ctx
.get_pool_name().c_str(),
3287 io_ctx
.get_id(), image_id
, force
);
3288 librbd::CProgressContext
prog_ctx(cb
, cbdata
);
3289 int r
= librbd::api::Trash
<>::remove(io_ctx
, image_id
, force
, prog_ctx
);
3290 tracepoint(librbd
, trash_remove_exit
, r
);
3294 extern "C" int rbd_trash_restore(rados_ioctx_t p
, const char *id
,
3296 librados::IoCtx io_ctx
;
3297 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3298 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3299 tracepoint(librbd
, trash_undelete_enter
, io_ctx
.get_pool_name().c_str(),
3300 io_ctx
.get_id(), id
, name
);
3301 int r
= librbd::api::Trash
<>::restore(io_ctx
, RBD_TRASH_IMAGE_SOURCE_USER
,
3303 tracepoint(librbd
, trash_undelete_exit
, r
);
3307 extern "C" int rbd_namespace_create(rados_ioctx_t io
,
3308 const char *namespace_name
) {
3309 librados::IoCtx io_ctx
;
3310 librados::IoCtx::from_rados_ioctx_t(io
, io_ctx
);
3312 return librbd::api::Namespace
<>::create(io_ctx
, namespace_name
);
3315 extern "C" int rbd_namespace_remove(rados_ioctx_t io
,
3316 const char *namespace_name
) {
3317 librados::IoCtx io_ctx
;
3318 librados::IoCtx::from_rados_ioctx_t(io
, io_ctx
);
3320 return librbd::api::Namespace
<>::remove(io_ctx
, namespace_name
);
3323 extern "C" int rbd_namespace_list(rados_ioctx_t io
, char *names
, size_t *size
) {
3324 librados::IoCtx io_ctx
;
3325 librados::IoCtx::from_rados_ioctx_t(io
, io_ctx
);
3327 if (names
== nullptr || size
== nullptr) {
3331 std::vector
<std::string
> cpp_names
;
3332 int r
= librbd::api::Namespace
<>::list(io_ctx
, &cpp_names
);
3337 size_t expected_size
= 0;
3338 for (size_t i
= 0; i
< cpp_names
.size(); i
++) {
3339 expected_size
+= cpp_names
[i
].size() + 1;
3341 if (*size
< expected_size
) {
3342 *size
= expected_size
;
3346 *size
= expected_size
;
3347 for (int i
= 0; i
< (int)cpp_names
.size(); i
++) {
3348 const char* name
= cpp_names
[i
].c_str();
3349 strcpy(names
, name
);
3350 names
+= strlen(names
) + 1;
3353 return (int)expected_size
;
3356 extern "C" int rbd_namespace_exists(rados_ioctx_t io
,
3357 const char *namespace_name
,
3359 librados::IoCtx io_ctx
;
3360 librados::IoCtx::from_rados_ioctx_t(io
, io_ctx
);
3362 return librbd::api::Namespace
<>::exists(io_ctx
, namespace_name
, exists
);
3365 extern "C" int rbd_pool_init(rados_ioctx_t io
, bool force
) {
3366 librados::IoCtx io_ctx
;
3367 librados::IoCtx::from_rados_ioctx_t(io
, io_ctx
);
3369 return librbd::api::Pool
<>::init(io_ctx
, force
);
3372 extern "C" void rbd_pool_stats_create(rbd_pool_stats_t
*stats
) {
3373 *stats
= reinterpret_cast<rbd_pool_stats_t
>(
3374 new librbd::api::Pool
<>::StatOptions
{});
3377 extern "C" void rbd_pool_stats_destroy(rbd_pool_stats_t stats
) {
3378 auto pool_stat_options
=
3379 reinterpret_cast<librbd::api::Pool
<>::StatOptions
*>(stats
);
3380 delete pool_stat_options
;
3383 extern "C" int rbd_pool_stats_option_add_uint64(rbd_pool_stats_t stats
,
3385 uint64_t* stat_val
) {
3386 auto pool_stat_options
=
3387 reinterpret_cast<librbd::api::Pool
<>::StatOptions
*>(stats
);
3388 return librbd::api::Pool
<>::add_stat_option(
3389 pool_stat_options
, static_cast<rbd_pool_stat_option_t
>(stat_option
),
3393 extern "C" int rbd_pool_stats_get(
3394 rados_ioctx_t io
, rbd_pool_stats_t pool_stats
) {
3395 librados::IoCtx io_ctx
;
3396 librados::IoCtx::from_rados_ioctx_t(io
, io_ctx
);
3398 auto pool_stat_options
=
3399 reinterpret_cast<librbd::api::Pool
<>::StatOptions
*>(pool_stats
);
3400 return librbd::api::Pool
<>::get_stats(io_ctx
, pool_stat_options
);
3403 extern "C" int rbd_copy(rbd_image_t image
, rados_ioctx_t dest_p
,
3404 const char *destname
)
3406 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
3407 librados::IoCtx dest_io_ctx
;
3408 librados::IoCtx::from_rados_ioctx_t(dest_p
, dest_io_ctx
);
3409 tracepoint(librbd
, copy_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(), destname
);
3410 librbd::ImageOptions opts
;
3411 librbd::NoOpProgressContext prog_ctx
;
3412 int r
= librbd::copy(ictx
, dest_io_ctx
, destname
, opts
, prog_ctx
, 0);
3413 tracepoint(librbd
, copy_exit
, r
);
3417 extern "C" int rbd_copy2(rbd_image_t srcp
, rbd_image_t destp
)
3419 librbd::ImageCtx
*src
= (librbd::ImageCtx
*)srcp
;
3420 librbd::ImageCtx
*dest
= (librbd::ImageCtx
*)destp
;
3421 tracepoint(librbd
, copy2_enter
, src
, src
->name
.c_str(), src
->snap_name
.c_str(), src
->read_only
, dest
, dest
->name
.c_str(), dest
->snap_name
.c_str(), dest
->read_only
);
3422 librbd::NoOpProgressContext prog_ctx
;
3423 int r
= librbd::copy(src
, dest
, prog_ctx
, 0);
3424 tracepoint(librbd
, copy2_exit
, r
);
3428 extern "C" int rbd_copy3(rbd_image_t image
, rados_ioctx_t dest_p
,
3429 const char *destname
, rbd_image_options_t c_opts
)
3431 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
3432 librados::IoCtx dest_io_ctx
;
3433 librados::IoCtx::from_rados_ioctx_t(dest_p
, dest_io_ctx
);
3434 tracepoint(librbd
, copy3_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(), destname
, c_opts
);
3435 librbd::ImageOptions
c_opts_(c_opts
);
3436 librbd::NoOpProgressContext prog_ctx
;
3437 int r
= librbd::copy(ictx
, dest_io_ctx
, destname
, c_opts_
, prog_ctx
, 0);
3438 tracepoint(librbd
, copy3_exit
, r
);
3442 extern "C" int rbd_copy4(rbd_image_t image
, rados_ioctx_t dest_p
,
3443 const char *destname
, rbd_image_options_t c_opts
, size_t sparse_size
)
3445 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
3446 librados::IoCtx dest_io_ctx
;
3447 librados::IoCtx::from_rados_ioctx_t(dest_p
, dest_io_ctx
);
3448 tracepoint(librbd
, copy4_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(), destname
, c_opts
, sparse_size
);
3449 librbd::ImageOptions
c_opts_(c_opts
);
3450 librbd::NoOpProgressContext prog_ctx
;
3451 int r
= librbd::copy(ictx
, dest_io_ctx
, destname
, c_opts_
, prog_ctx
, sparse_size
);
3452 tracepoint(librbd
, copy4_exit
, r
);
3456 extern "C" int rbd_copy_with_progress(rbd_image_t image
, rados_ioctx_t dest_p
,
3457 const char *destname
,
3458 librbd_progress_fn_t fn
, void *data
)
3460 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
3461 librados::IoCtx dest_io_ctx
;
3462 librados::IoCtx::from_rados_ioctx_t(dest_p
, dest_io_ctx
);
3463 tracepoint(librbd
, copy_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(), destname
);
3464 librbd::ImageOptions opts
;
3465 librbd::CProgressContext
prog_ctx(fn
, data
);
3466 int ret
= librbd::copy(ictx
, dest_io_ctx
, destname
, opts
, prog_ctx
, 0);
3467 tracepoint(librbd
, copy_exit
, ret
);
3471 extern "C" int rbd_copy_with_progress2(rbd_image_t srcp
, rbd_image_t destp
,
3472 librbd_progress_fn_t fn
, void *data
)
3474 librbd::ImageCtx
*src
= (librbd::ImageCtx
*)srcp
;
3475 librbd::ImageCtx
*dest
= (librbd::ImageCtx
*)destp
;
3476 tracepoint(librbd
, copy2_enter
, src
, src
->name
.c_str(), src
->snap_name
.c_str(), src
->read_only
, dest
, dest
->name
.c_str(), dest
->snap_name
.c_str(), dest
->read_only
);
3477 librbd::CProgressContext
prog_ctx(fn
, data
);
3478 int ret
= librbd::copy(src
, dest
, prog_ctx
, 0);
3479 tracepoint(librbd
, copy2_exit
, ret
);
3483 extern "C" int rbd_copy_with_progress3(rbd_image_t image
, rados_ioctx_t dest_p
,
3484 const char *destname
,
3485 rbd_image_options_t dest_opts
,
3486 librbd_progress_fn_t fn
, void *data
)
3488 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
3489 librados::IoCtx dest_io_ctx
;
3490 librados::IoCtx::from_rados_ioctx_t(dest_p
, dest_io_ctx
);
3491 tracepoint(librbd
, copy3_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(), destname
, dest_opts
);
3492 librbd::ImageOptions
dest_opts_(dest_opts
);
3493 librbd::CProgressContext
prog_ctx(fn
, data
);
3494 int ret
= librbd::copy(ictx
, dest_io_ctx
, destname
, dest_opts_
, prog_ctx
, 0);
3495 tracepoint(librbd
, copy3_exit
, ret
);
3499 extern "C" int rbd_copy_with_progress4(rbd_image_t image
, rados_ioctx_t dest_p
,
3500 const char *destname
,
3501 rbd_image_options_t dest_opts
,
3502 librbd_progress_fn_t fn
, void *data
, size_t sparse_size
)
3504 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
3505 librados::IoCtx dest_io_ctx
;
3506 librados::IoCtx::from_rados_ioctx_t(dest_p
, dest_io_ctx
);
3507 tracepoint(librbd
, copy4_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(), destname
, dest_opts
, sparse_size
);
3508 librbd::ImageOptions
dest_opts_(dest_opts
);
3509 librbd::CProgressContext
prog_ctx(fn
, data
);
3510 int ret
= librbd::copy(ictx
, dest_io_ctx
, destname
, dest_opts_
, prog_ctx
, sparse_size
);
3511 tracepoint(librbd
, copy4_exit
, ret
);
3515 extern "C" int rbd_deep_copy(rbd_image_t image
, rados_ioctx_t dest_p
,
3516 const char *destname
, rbd_image_options_t c_opts
)
3518 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
3519 librados::IoCtx dest_io_ctx
;
3520 librados::IoCtx::from_rados_ioctx_t(dest_p
, dest_io_ctx
);
3521 tracepoint(librbd
, deep_copy_enter
, ictx
, ictx
->name
.c_str(),
3522 ictx
->snap_name
.c_str(), ictx
->read_only
,
3523 dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(),
3525 librbd::ImageOptions
opts(c_opts
);
3526 librbd::NoOpProgressContext prog_ctx
;
3527 int r
= librbd::api::Image
<>::deep_copy(ictx
, dest_io_ctx
, destname
, opts
,
3529 tracepoint(librbd
, deep_copy_exit
, r
);
3533 extern "C" int rbd_deep_copy_with_progress(rbd_image_t image
,
3534 rados_ioctx_t dest_p
,
3535 const char *destname
,
3536 rbd_image_options_t dest_opts
,
3537 librbd_progress_fn_t fn
, void *data
)
3539 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
3540 librados::IoCtx dest_io_ctx
;
3541 librados::IoCtx::from_rados_ioctx_t(dest_p
, dest_io_ctx
);
3542 tracepoint(librbd
, deep_copy_enter
, ictx
, ictx
->name
.c_str(),
3543 ictx
->snap_name
.c_str(), ictx
->read_only
,
3544 dest_io_ctx
.get_pool_name().c_str(), dest_io_ctx
.get_id(),
3545 destname
, dest_opts
);
3546 librbd::ImageOptions
opts(dest_opts
);
3547 librbd::CProgressContext
prog_ctx(fn
, data
);
3548 int ret
= librbd::api::Image
<>::deep_copy(ictx
, dest_io_ctx
, destname
, opts
,
3550 tracepoint(librbd
, deep_copy_exit
, ret
);
3554 extern "C" int rbd_flatten(rbd_image_t image
)
3556 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
3557 tracepoint(librbd
, flatten_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str());
3558 librbd::NoOpProgressContext prog_ctx
;
3559 int r
= ictx
->operations
->flatten(prog_ctx
);
3560 tracepoint(librbd
, flatten_exit
, r
);
3564 extern "C" int rbd_flatten_with_progress(rbd_image_t image
,
3565 librbd_progress_fn_t cb
, void *cbdata
)
3567 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
3568 tracepoint(librbd
, flatten_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str());
3569 librbd::CProgressContext
prog_ctx(cb
, cbdata
);
3570 int r
= ictx
->operations
->flatten(prog_ctx
);
3571 tracepoint(librbd
, flatten_exit
, r
);
3575 extern "C" int rbd_sparsify(rbd_image_t image
, size_t sparse_size
)
3577 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
3578 tracepoint(librbd
, sparsify_enter
, ictx
, ictx
->name
.c_str(), sparse_size
,
3580 librbd::NoOpProgressContext prog_ctx
;
3581 int r
= ictx
->operations
->sparsify(sparse_size
, prog_ctx
);
3582 tracepoint(librbd
, sparsify_exit
, r
);
3586 extern "C" int rbd_sparsify_with_progress(rbd_image_t image
, size_t sparse_size
,
3587 librbd_progress_fn_t cb
, void *cbdata
)
3589 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
3590 tracepoint(librbd
, sparsify_enter
, ictx
, ictx
->name
.c_str(), sparse_size
,
3592 librbd::CProgressContext
prog_ctx(cb
, cbdata
);
3593 int r
= ictx
->operations
->sparsify(sparse_size
, prog_ctx
);
3594 tracepoint(librbd
, sparsify_exit
, r
);
3598 extern "C" int rbd_rename(rados_ioctx_t src_p
, const char *srcname
,
3599 const char *destname
)
3601 librados::IoCtx src_io_ctx
;
3602 librados::IoCtx::from_rados_ioctx_t(src_p
, src_io_ctx
);
3603 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(src_io_ctx
));
3604 tracepoint(librbd
, rename_enter
, src_io_ctx
.get_pool_name().c_str(), src_io_ctx
.get_id(), srcname
, destname
);
3605 int r
= librbd::rename(src_io_ctx
, srcname
, destname
);
3606 tracepoint(librbd
, rename_exit
, r
);
3610 extern "C" int rbd_migration_prepare(rados_ioctx_t p
, const char *image_name
,
3611 rados_ioctx_t dest_p
,
3612 const char *dest_image_name
,
3613 rbd_image_options_t opts_
)
3615 librados::IoCtx io_ctx
;
3616 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3617 librados::IoCtx dest_io_ctx
;
3618 librados::IoCtx::from_rados_ioctx_t(dest_p
, dest_io_ctx
);
3619 tracepoint(librbd
, migration_prepare_enter
, io_ctx
.get_pool_name().c_str(),
3620 io_ctx
.get_id(), image_name
, dest_io_ctx
.get_pool_name().c_str(),
3621 dest_io_ctx
.get_id(), dest_image_name
, opts_
);
3622 librbd::ImageOptions
opts(opts_
);
3623 int r
= librbd::api::Migration
<>::prepare(io_ctx
, image_name
, dest_io_ctx
,
3624 dest_image_name
, opts
);
3625 tracepoint(librbd
, migration_prepare_exit
, r
);
3629 extern "C" int rbd_migration_execute(rados_ioctx_t p
, const char *image_name
)
3631 librados::IoCtx io_ctx
;
3632 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3633 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3634 tracepoint(librbd
, migration_execute_enter
, io_ctx
.get_pool_name().c_str(),
3635 io_ctx
.get_id(), image_name
);
3636 librbd::NoOpProgressContext prog_ctx
;
3637 int r
= librbd::api::Migration
<>::execute(io_ctx
, image_name
, prog_ctx
);
3638 tracepoint(librbd
, migration_execute_exit
, r
);
3642 extern "C" int rbd_migration_execute_with_progress(rados_ioctx_t p
,
3644 librbd_progress_fn_t fn
,
3647 librados::IoCtx io_ctx
;
3648 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3649 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3650 tracepoint(librbd
, migration_execute_enter
, io_ctx
.get_pool_name().c_str(),
3651 io_ctx
.get_id(), name
);
3652 librbd::CProgressContext
prog_ctx(fn
, data
);
3653 int r
= librbd::api::Migration
<>::execute(io_ctx
, name
, prog_ctx
);
3654 tracepoint(librbd
, migration_execute_exit
, r
);
3658 extern "C" int rbd_migration_abort(rados_ioctx_t p
, const char *image_name
)
3660 librados::IoCtx io_ctx
;
3661 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3662 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3663 tracepoint(librbd
, migration_abort_enter
, io_ctx
.get_pool_name().c_str(),
3664 io_ctx
.get_id(), image_name
);
3665 librbd::NoOpProgressContext prog_ctx
;
3666 int r
= librbd::api::Migration
<>::abort(io_ctx
, image_name
, prog_ctx
);
3667 tracepoint(librbd
, migration_abort_exit
, r
);
3671 extern "C" int rbd_migration_abort_with_progress(rados_ioctx_t p
,
3673 librbd_progress_fn_t fn
,
3676 librados::IoCtx io_ctx
;
3677 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3678 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3679 tracepoint(librbd
, migration_abort_enter
, io_ctx
.get_pool_name().c_str(),
3680 io_ctx
.get_id(), name
);
3681 librbd::CProgressContext
prog_ctx(fn
, data
);
3682 int r
= librbd::api::Migration
<>::abort(io_ctx
, name
, prog_ctx
);
3683 tracepoint(librbd
, migration_abort_exit
, r
);
3687 extern "C" int rbd_migration_commit(rados_ioctx_t p
, const char *image_name
)
3689 librados::IoCtx io_ctx
;
3690 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3691 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3692 tracepoint(librbd
, migration_commit_enter
, io_ctx
.get_pool_name().c_str(),
3693 io_ctx
.get_id(), image_name
);
3694 librbd::NoOpProgressContext prog_ctx
;
3695 int r
= librbd::api::Migration
<>::commit(io_ctx
, image_name
, prog_ctx
);
3696 tracepoint(librbd
, migration_commit_exit
, r
);
3700 extern "C" int rbd_migration_commit_with_progress(rados_ioctx_t p
,
3702 librbd_progress_fn_t fn
,
3705 librados::IoCtx io_ctx
;
3706 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3707 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3708 tracepoint(librbd
, migration_commit_enter
, io_ctx
.get_pool_name().c_str(),
3709 io_ctx
.get_id(), name
);
3710 librbd::CProgressContext
prog_ctx(fn
, data
);
3711 int r
= librbd::api::Migration
<>::commit(io_ctx
, name
, prog_ctx
);
3712 tracepoint(librbd
, migration_commit_exit
, r
);
3716 extern "C" int rbd_migration_status(rados_ioctx_t p
, const char *image_name
,
3717 rbd_image_migration_status_t
*status
,
3720 librados::IoCtx io_ctx
;
3721 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3722 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3723 tracepoint(librbd
, migration_status_enter
, io_ctx
.get_pool_name().c_str(),
3724 io_ctx
.get_id(), image_name
);
3726 if (status_size
!= sizeof(rbd_image_migration_status_t
)) {
3727 tracepoint(librbd
, migration_status_exit
, -ERANGE
);
3731 librbd::image_migration_status_t cpp_status
;
3732 int r
= librbd::api::Migration
<>::status(io_ctx
, image_name
, &cpp_status
);
3734 status
->source_pool_id
= cpp_status
.source_pool_id
;
3735 status
->source_pool_namespace
=
3736 strdup(cpp_status
.source_pool_namespace
.c_str());
3737 status
->source_image_name
= strdup(cpp_status
.source_image_name
.c_str());
3738 status
->source_image_id
= strdup(cpp_status
.source_image_id
.c_str());
3739 status
->dest_pool_id
= cpp_status
.dest_pool_id
;
3740 status
->dest_pool_namespace
=
3741 strdup(cpp_status
.dest_pool_namespace
.c_str());
3742 status
->dest_image_name
= strdup(cpp_status
.dest_image_name
.c_str());
3743 status
->dest_image_id
= strdup(cpp_status
.dest_image_id
.c_str());
3744 status
->state
= cpp_status
.state
;
3745 status
->state_description
= strdup(cpp_status
.state_description
.c_str());
3748 tracepoint(librbd
, migration_status_exit
, r
);
3752 extern "C" void rbd_migration_status_cleanup(rbd_image_migration_status_t
*s
)
3754 free(s
->source_pool_namespace
);
3755 free(s
->source_image_name
);
3756 free(s
->source_image_id
);
3757 free(s
->dest_pool_namespace
);
3758 free(s
->dest_image_name
);
3759 free(s
->dest_image_id
);
3760 free(s
->state_description
);
3763 extern "C" int rbd_pool_metadata_get(rados_ioctx_t p
, const char *key
,
3764 char *value
, size_t *vallen
)
3766 librados::IoCtx io_ctx
;
3767 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3769 int r
= librbd::api::PoolMetadata
<>::get(io_ctx
, key
, &val_s
);
3770 if (*vallen
< val_s
.size() + 1) {
3772 *vallen
= val_s
.size() + 1;
3774 strncpy(value
, val_s
.c_str(), val_s
.size() + 1);
3780 extern "C" int rbd_pool_metadata_set(rados_ioctx_t p
, const char *key
,
3783 librados::IoCtx io_ctx
;
3784 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3785 int r
= librbd::api::PoolMetadata
<>::set(io_ctx
, key
, value
);
3789 extern "C" int rbd_pool_metadata_remove(rados_ioctx_t p
, const char *key
)
3791 librados::IoCtx io_ctx
;
3792 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3793 int r
= librbd::api::PoolMetadata
<>::remove(io_ctx
, key
);
3797 extern "C" int rbd_pool_metadata_list(rados_ioctx_t p
, const char *start
,
3798 uint64_t max
, char *key
, size_t *key_len
,
3799 char *value
, size_t *val_len
)
3801 librados::IoCtx io_ctx
;
3802 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3803 map
<string
, bufferlist
> pairs
;
3804 int r
= librbd::api::PoolMetadata
<>::list(io_ctx
, start
, max
, &pairs
);
3808 size_t key_total_len
= 0, val_total_len
= 0;
3809 for (auto &it
: pairs
) {
3810 key_total_len
+= it
.first
.size() + 1;
3811 val_total_len
+= it
.second
.length() + 1;
3813 if (*key_len
< key_total_len
|| *val_len
< val_total_len
) {
3814 *key_len
= key_total_len
;
3815 *val_len
= val_total_len
;
3818 *key_len
= key_total_len
;
3819 *val_len
= val_total_len
;
3821 char *key_p
= key
, *value_p
= value
;
3822 for (auto &it
: pairs
) {
3823 strncpy(key_p
, it
.first
.c_str(), it
.first
.size() + 1);
3824 key_p
+= it
.first
.size() + 1;
3825 strncpy(value_p
, it
.second
.c_str(), it
.second
.length());
3826 value_p
+= it
.second
.length();
3833 extern "C" int rbd_config_pool_list(rados_ioctx_t p
,
3834 rbd_config_option_t
*options
,
3836 librados::IoCtx io_ctx
;
3837 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3839 std::vector
<librbd::config_option_t
> option_vector
;
3840 int r
= librbd::api::Config
<>::list(io_ctx
, &option_vector
);
3845 if (*max_options
< static_cast<int>(option_vector
.size())) {
3846 *max_options
= static_cast<int>(option_vector
.size());
3850 for (int i
= 0; i
< static_cast<int>(option_vector
.size()); ++i
) {
3851 config_option_cpp_to_c(option_vector
[i
], &options
[i
]);
3853 *max_options
= static_cast<int>(option_vector
.size());
3857 extern "C" void rbd_config_pool_list_cleanup(rbd_config_option_t
*options
,
3859 for (int i
= 0; i
< max_options
; ++i
) {
3860 config_option_cleanup(options
[i
]);
3864 extern "C" int rbd_open(rados_ioctx_t p
, const char *name
, rbd_image_t
*image
,
3865 const char *snap_name
)
3867 librados::IoCtx io_ctx
;
3868 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3869 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3870 librbd::ImageCtx
*ictx
= new librbd::ImageCtx(name
, "", snap_name
, io_ctx
,
3872 tracepoint(librbd
, open_image_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
3874 int r
= ictx
->state
->open(0);
3876 *image
= (rbd_image_t
)ictx
;
3878 tracepoint(librbd
, open_image_exit
, r
);
3882 extern "C" int rbd_open_by_id(rados_ioctx_t p
, const char *id
,
3883 rbd_image_t
*image
, const char *snap_name
)
3885 librados::IoCtx io_ctx
;
3886 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3887 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3888 librbd::ImageCtx
*ictx
= new librbd::ImageCtx("", id
, snap_name
, io_ctx
,
3890 tracepoint(librbd
, open_image_enter
, ictx
, ictx
->name
.c_str(),
3891 ictx
->id
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
3893 int r
= ictx
->state
->open(0);
3897 *image
= (rbd_image_t
)ictx
;
3899 tracepoint(librbd
, open_image_exit
, r
);
3903 extern "C" int rbd_aio_open(rados_ioctx_t p
, const char *name
,
3904 rbd_image_t
*image
, const char *snap_name
,
3907 librados::IoCtx io_ctx
;
3908 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3909 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3910 librbd::ImageCtx
*ictx
= new librbd::ImageCtx(name
, "", snap_name
, io_ctx
,
3912 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
3913 tracepoint(librbd
, aio_open_image_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, comp
->pc
);
3914 ictx
->state
->open(0, new C_OpenComplete(ictx
, get_aio_completion(comp
),
3916 tracepoint(librbd
, aio_open_image_exit
, 0);
3920 extern "C" int rbd_aio_open_by_id(rados_ioctx_t p
, const char *id
,
3921 rbd_image_t
*image
, const char *snap_name
,
3924 librados::IoCtx io_ctx
;
3925 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3926 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3927 librbd::ImageCtx
*ictx
= new librbd::ImageCtx("", id
, snap_name
, io_ctx
,
3929 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
3930 tracepoint(librbd
, aio_open_image_enter
, ictx
, ictx
->name
.c_str(),
3931 ictx
->id
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
,
3933 ictx
->state
->open(0, new C_OpenComplete(ictx
, get_aio_completion(comp
),
3935 tracepoint(librbd
, aio_open_image_exit
, 0);
3939 extern "C" int rbd_open_read_only(rados_ioctx_t p
, const char *name
,
3940 rbd_image_t
*image
, const char *snap_name
)
3942 librados::IoCtx io_ctx
;
3943 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3944 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3945 librbd::ImageCtx
*ictx
= new librbd::ImageCtx(name
, "", snap_name
, io_ctx
,
3947 tracepoint(librbd
, open_image_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
3949 int r
= ictx
->state
->open(0);
3951 *image
= (rbd_image_t
)ictx
;
3953 tracepoint(librbd
, open_image_exit
, r
);
3957 extern "C" int rbd_open_by_id_read_only(rados_ioctx_t p
, const char *id
,
3958 rbd_image_t
*image
, const char *snap_name
)
3960 librados::IoCtx io_ctx
;
3961 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3962 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3963 librbd::ImageCtx
*ictx
= new librbd::ImageCtx("", id
, snap_name
, io_ctx
,
3965 tracepoint(librbd
, open_image_enter
, ictx
, ictx
->name
.c_str(),
3966 ictx
->id
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
3968 int r
= ictx
->state
->open(0);
3972 *image
= (rbd_image_t
)ictx
;
3974 tracepoint(librbd
, open_image_exit
, r
);
3978 extern "C" int rbd_aio_open_read_only(rados_ioctx_t p
, const char *name
,
3979 rbd_image_t
*image
, const char *snap_name
,
3982 librados::IoCtx io_ctx
;
3983 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
3984 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
3985 librbd::ImageCtx
*ictx
= new librbd::ImageCtx(name
, "", snap_name
, io_ctx
,
3987 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
3988 tracepoint(librbd
, aio_open_image_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, comp
->pc
);
3989 ictx
->state
->open(0, new C_OpenComplete(ictx
, get_aio_completion(comp
),
3991 tracepoint(librbd
, aio_open_image_exit
, 0);
3995 extern "C" int rbd_aio_open_by_id_read_only(rados_ioctx_t p
, const char *id
,
3997 const char *snap_name
,
4000 librados::IoCtx io_ctx
;
4001 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
4002 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
4003 librbd::ImageCtx
*ictx
= new librbd::ImageCtx("", id
, snap_name
, io_ctx
,
4005 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
4006 tracepoint(librbd
, aio_open_image_enter
, ictx
, ictx
->name
.c_str(),
4007 ictx
->id
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, comp
->pc
);
4008 ictx
->state
->open(0, new C_OpenComplete(ictx
, get_aio_completion(comp
),
4010 tracepoint(librbd
, aio_open_image_exit
, 0);
4014 extern "C" int rbd_close(rbd_image_t image
)
4016 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4017 tracepoint(librbd
, close_image_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str());
4019 int r
= ictx
->state
->close();
4021 tracepoint(librbd
, close_image_exit
, r
);
4025 extern "C" int rbd_aio_close(rbd_image_t image
, rbd_completion_t c
)
4027 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4028 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
4029 tracepoint(librbd
, aio_close_image_enter
, ictx
, ictx
->name
.c_str(), ictx
->id
.c_str(), comp
->pc
);
4030 ictx
->state
->close(new C_AioCompletion(ictx
, librbd::io::AIO_TYPE_CLOSE
,
4031 get_aio_completion(comp
)));
4032 tracepoint(librbd
, aio_close_image_exit
, 0);
4036 extern "C" int rbd_resize(rbd_image_t image
, uint64_t size
)
4038 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4039 tracepoint(librbd
, resize_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, size
);
4040 librbd::NoOpProgressContext prog_ctx
;
4041 int r
= ictx
->operations
->resize(size
, true, prog_ctx
);
4042 tracepoint(librbd
, resize_exit
, r
);
4046 extern "C" int rbd_resize2(rbd_image_t image
, uint64_t size
, bool allow_shrink
,
4047 librbd_progress_fn_t cb
, void *cbdata
)
4049 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4050 tracepoint(librbd
, resize_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, size
);
4051 librbd::CProgressContext
prog_ctx(cb
, cbdata
);
4052 int r
= ictx
->operations
->resize(size
, allow_shrink
, prog_ctx
);
4053 tracepoint(librbd
, resize_exit
, r
);
4057 extern "C" int rbd_resize_with_progress(rbd_image_t image
, uint64_t size
,
4058 librbd_progress_fn_t cb
, void *cbdata
)
4060 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4061 tracepoint(librbd
, resize_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, size
);
4062 librbd::CProgressContext
prog_ctx(cb
, cbdata
);
4063 int r
= ictx
->operations
->resize(size
, true, prog_ctx
);
4064 tracepoint(librbd
, resize_exit
, r
);
4068 extern "C" int rbd_stat(rbd_image_t image
, rbd_image_info_t
*info
,
4071 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4072 tracepoint(librbd
, stat_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
4073 int r
= librbd::info(ictx
, *info
, infosize
);
4074 tracepoint(librbd
, stat_exit
, r
, info
);
4078 extern "C" int rbd_get_old_format(rbd_image_t image
, uint8_t *old
)
4080 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4081 tracepoint(librbd
, get_old_format_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
4082 int r
= librbd::get_old_format(ictx
, old
);
4083 tracepoint(librbd
, get_old_format_exit
, r
, *old
);
4087 extern "C" int rbd_get_size(rbd_image_t image
, uint64_t *size
)
4089 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4090 tracepoint(librbd
, get_size_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
4091 int r
= librbd::get_size(ictx
, size
);
4092 tracepoint(librbd
, get_size_exit
, r
, *size
);
4096 extern "C" int rbd_get_features(rbd_image_t image
, uint64_t *features
)
4098 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4099 tracepoint(librbd
, get_features_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
4100 int r
= librbd::get_features(ictx
, features
);
4101 tracepoint(librbd
, get_features_exit
, r
, *features
);
4105 extern "C" int rbd_update_features(rbd_image_t image
, uint64_t features
,
4108 librbd::ImageCtx
*ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4109 bool features_enabled
= enabled
!= 0;
4110 tracepoint(librbd
, update_features_enter
, ictx
, features
, features_enabled
);
4111 int r
= ictx
->operations
->update_features(features
, features_enabled
);
4112 tracepoint(librbd
, update_features_exit
, r
);
4116 extern "C" int rbd_get_op_features(rbd_image_t image
, uint64_t *op_features
)
4118 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4119 return librbd::api::Image
<>::get_op_features(ictx
, op_features
);
4122 extern "C" int rbd_get_stripe_unit(rbd_image_t image
, uint64_t *stripe_unit
)
4124 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4125 tracepoint(librbd
, get_stripe_unit_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
4126 *stripe_unit
= ictx
->get_stripe_unit();
4127 tracepoint(librbd
, get_stripe_unit_exit
, 0, *stripe_unit
);
4131 extern "C" int rbd_get_stripe_count(rbd_image_t image
, uint64_t *stripe_count
)
4133 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4134 tracepoint(librbd
, get_stripe_count_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
4135 *stripe_count
= ictx
->get_stripe_count();
4136 tracepoint(librbd
, get_stripe_count_exit
, 0, *stripe_count
);
4140 extern "C" int rbd_get_create_timestamp(rbd_image_t image
,
4141 struct timespec
*timestamp
)
4143 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4144 tracepoint(librbd
, get_create_timestamp_enter
, ictx
, ictx
->name
.c_str(),
4146 utime_t time
= ictx
->get_create_timestamp();
4147 time
.to_timespec(timestamp
);
4148 tracepoint(librbd
, get_create_timestamp_exit
, 0, timestamp
);
4152 extern "C" int rbd_get_access_timestamp(rbd_image_t image
,
4153 struct timespec
*timestamp
)
4155 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4156 tracepoint(librbd
, get_access_timestamp_enter
, ictx
, ictx
->name
.c_str(),
4158 utime_t time
= ictx
->get_access_timestamp();
4159 time
.to_timespec(timestamp
);
4160 tracepoint(librbd
, get_access_timestamp_exit
, 0, timestamp
);
4164 extern "C" int rbd_get_modify_timestamp(rbd_image_t image
,
4165 struct timespec
*timestamp
)
4167 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4168 tracepoint(librbd
, get_modify_timestamp_enter
, ictx
, ictx
->name
.c_str(),
4170 utime_t time
= ictx
->get_modify_timestamp();
4171 time
.to_timespec(timestamp
);
4172 tracepoint(librbd
, get_modify_timestamp_exit
, 0, timestamp
);
4177 extern "C" int rbd_get_overlap(rbd_image_t image
, uint64_t *overlap
)
4179 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4180 tracepoint(librbd
, get_overlap_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
4181 int r
= librbd::get_overlap(ictx
, overlap
);
4182 tracepoint(librbd
, get_overlap_exit
, r
, *overlap
);
4186 extern "C" int rbd_get_name(rbd_image_t image
, char *name
, size_t *name_len
)
4188 librbd::ImageCtx
*ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4189 if (*name_len
<= ictx
->name
.size()) {
4190 *name_len
= ictx
->name
.size() + 1;
4194 strncpy(name
, ictx
->name
.c_str(), ictx
->name
.size());
4195 name
[ictx
->name
.size()] = '\0';
4196 *name_len
= ictx
->name
.size() + 1;
4200 extern "C" int rbd_get_id(rbd_image_t image
, char *id
, size_t id_len
)
4202 librbd::ImageCtx
*ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4203 if (ictx
->old_format
) {
4206 if (ictx
->id
.size() >= id_len
) {
4210 strncpy(id
, ictx
->id
.c_str(), id_len
- 1);
4211 id
[id_len
- 1] = '\0';
4215 extern "C" int rbd_get_block_name_prefix(rbd_image_t image
, char *prefix
,
4218 librbd::ImageCtx
*ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4219 if (ictx
->object_prefix
.size() >= prefix_len
) {
4223 strncpy(prefix
, ictx
->object_prefix
.c_str(), prefix_len
- 1);
4224 prefix
[prefix_len
- 1] = '\0';
4228 extern "C" int64_t rbd_get_data_pool_id(rbd_image_t image
)
4230 librbd::ImageCtx
*ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4231 return ictx
->data_ctx
.get_id();
4234 extern "C" int rbd_get_parent_info(rbd_image_t image
,
4235 char *parent_pool_name
, size_t ppool_namelen
,
4236 char *parent_name
, size_t pnamelen
,
4237 char *parent_snap_name
, size_t psnap_namelen
)
4239 auto ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4240 tracepoint(librbd
, get_parent_info_enter
, ictx
, ictx
->name
.c_str(),
4241 ictx
->snap_name
.c_str(), ictx
->read_only
);
4243 librbd::linked_image_spec_t parent_image
;
4244 librbd::snap_spec_t parent_snap
;
4245 int r
= librbd::api::Image
<>::get_parent(ictx
, &parent_image
, &parent_snap
);
4247 if (parent_pool_name
) {
4248 if (parent_image
.pool_name
.length() + 1 > ppool_namelen
) {
4251 strcpy(parent_pool_name
, parent_image
.pool_name
.c_str());
4255 if (parent_image
.image_name
.length() + 1 > pnamelen
) {
4258 strcpy(parent_name
, parent_image
.image_name
.c_str());
4261 if (parent_snap_name
) {
4262 if (parent_snap
.name
.length() + 1 > psnap_namelen
) {
4265 strcpy(parent_snap_name
, parent_snap
.name
.c_str());
4271 tracepoint(librbd
, get_parent_info_exit
, r
, NULL
, NULL
, NULL
, NULL
);
4275 tracepoint(librbd
, get_parent_info_exit
, r
,
4276 parent_image
.pool_name
.c_str(),
4277 parent_image
.image_name
.c_str(),
4278 parent_image
.image_id
.c_str(),
4279 parent_snap
.name
.c_str());
4283 extern "C" int rbd_get_parent_info2(rbd_image_t image
,
4284 char *parent_pool_name
,
4285 size_t ppool_namelen
,
4286 char *parent_name
, size_t pnamelen
,
4287 char *parent_id
, size_t pidlen
,
4288 char *parent_snap_name
,
4289 size_t psnap_namelen
)
4291 auto ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4292 tracepoint(librbd
, get_parent_info_enter
, ictx
, ictx
->name
.c_str(),
4293 ictx
->snap_name
.c_str(), ictx
->read_only
);
4295 librbd::linked_image_spec_t parent_image
;
4296 librbd::snap_spec_t parent_snap
;
4297 int r
= librbd::api::Image
<>::get_parent(ictx
, &parent_image
, &parent_snap
);
4299 if (parent_pool_name
) {
4300 if (parent_image
.pool_name
.length() + 1 > ppool_namelen
) {
4303 strcpy(parent_pool_name
, parent_image
.pool_name
.c_str());
4307 if (parent_image
.image_name
.length() + 1 > pnamelen
) {
4310 strcpy(parent_name
, parent_image
.image_name
.c_str());
4314 if (parent_image
.image_id
.length() + 1 > pidlen
) {
4317 strcpy(parent_id
, parent_image
.image_id
.c_str());
4320 if (parent_snap_name
) {
4321 if (parent_snap
.name
.length() + 1 > psnap_namelen
) {
4324 strcpy(parent_snap_name
, parent_snap
.name
.c_str());
4330 tracepoint(librbd
, get_parent_info_exit
, r
, NULL
, NULL
, NULL
, NULL
);
4334 tracepoint(librbd
, get_parent_info_exit
, r
,
4335 parent_image
.pool_name
.c_str(),
4336 parent_image
.image_name
.c_str(),
4337 parent_image
.image_id
.c_str(),
4338 parent_snap
.name
.c_str());
4342 extern "C" int rbd_get_parent(rbd_image_t image
,
4343 rbd_linked_image_spec_t
*parent_image
,
4344 rbd_snap_spec_t
*parent_snap
)
4346 auto ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4347 tracepoint(librbd
, get_parent_info_enter
, ictx
, ictx
->name
.c_str(),
4348 ictx
->snap_name
.c_str(), ictx
->read_only
);
4350 librbd::linked_image_spec_t cpp_parent_image
;
4351 librbd::snap_spec_t cpp_parent_snap
;
4352 int r
= librbd::api::Image
<>::get_parent(ictx
, &cpp_parent_image
,
4355 memset(parent_image
, 0, sizeof(rbd_linked_image_spec_t
));
4356 memset(parent_snap
, 0, sizeof(rbd_snap_spec_t
));
4359 .pool_id
= cpp_parent_image
.pool_id
,
4360 .pool_name
= strdup(cpp_parent_image
.pool_name
.c_str()),
4361 .pool_namespace
= strdup(cpp_parent_image
.pool_namespace
.c_str()),
4362 .image_id
= strdup(cpp_parent_image
.image_id
.c_str()),
4363 .image_name
= strdup(cpp_parent_image
.image_name
.c_str()),
4364 .trash
= cpp_parent_image
.trash
};
4366 .id
= cpp_parent_snap
.id
,
4367 .namespace_type
= cpp_parent_snap
.namespace_type
,
4368 .name
= strdup(cpp_parent_snap
.name
.c_str())};
4371 tracepoint(librbd
, get_parent_info_exit
, r
,
4372 parent_image
->pool_name
,
4373 parent_image
->image_name
,
4374 parent_image
->image_id
,
4379 extern "C" int rbd_get_flags(rbd_image_t image
, uint64_t *flags
)
4381 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4382 tracepoint(librbd
, get_flags_enter
, ictx
);
4383 int r
= librbd::get_flags(ictx
, flags
);
4384 tracepoint(librbd
, get_flags_exit
, ictx
, r
, *flags
);
4388 extern "C" int rbd_get_group(rbd_image_t image
, rbd_group_info_t
*group_info
,
4389 size_t group_info_size
)
4391 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4392 tracepoint(librbd
, image_get_group_enter
, ictx
->name
.c_str());
4394 if (group_info_size
!= sizeof(rbd_group_info_t
)) {
4395 tracepoint(librbd
, image_get_group_exit
, -ERANGE
);
4399 librbd::group_info_t cpp_group_info
;
4400 int r
= librbd::api::Group
<>::image_get_group(ictx
, &cpp_group_info
);
4402 group_info_cpp_to_c(cpp_group_info
, group_info
);
4404 group_info
->name
= NULL
;
4407 tracepoint(librbd
, image_get_group_exit
, r
);
4411 extern "C" int rbd_set_image_notification(rbd_image_t image
, int fd
, int type
)
4413 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4414 tracepoint(librbd
, set_image_notification_enter
, ictx
, fd
, type
);
4415 int r
= librbd::set_image_notification(ictx
, fd
, type
);
4416 tracepoint(librbd
, set_image_notification_exit
, ictx
, r
);
4420 extern "C" int rbd_is_exclusive_lock_owner(rbd_image_t image
, int *is_owner
)
4422 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4423 tracepoint(librbd
, is_exclusive_lock_owner_enter
, ictx
);
4425 int r
= librbd::is_exclusive_lock_owner(ictx
, &owner
);
4426 *is_owner
= owner
? 1 : 0;
4427 tracepoint(librbd
, is_exclusive_lock_owner_exit
, ictx
, r
, *is_owner
);
4431 extern "C" int rbd_lock_acquire(rbd_image_t image
, rbd_lock_mode_t lock_mode
)
4433 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4434 tracepoint(librbd
, lock_acquire_enter
, ictx
, lock_mode
);
4435 int r
= librbd::lock_acquire(ictx
, lock_mode
);
4436 tracepoint(librbd
, lock_acquire_exit
, ictx
, r
);
4440 extern "C" int rbd_lock_release(rbd_image_t image
)
4442 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4443 tracepoint(librbd
, lock_release_enter
, ictx
);
4444 int r
= librbd::lock_release(ictx
);
4445 tracepoint(librbd
, lock_release_exit
, ictx
, r
);
4449 extern "C" int rbd_lock_get_owners(rbd_image_t image
,
4450 rbd_lock_mode_t
*lock_mode
,
4452 size_t *max_lock_owners
)
4454 librbd::ImageCtx
*ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4455 tracepoint(librbd
, lock_get_owners_enter
, ictx
);
4456 memset(lock_owners
, 0, sizeof(*lock_owners
) * *max_lock_owners
);
4457 std::list
<std::string
> lock_owner_list
;
4458 int r
= librbd::lock_get_owners(ictx
, lock_mode
, &lock_owner_list
);
4460 if (*max_lock_owners
>= lock_owner_list
.size()) {
4461 *max_lock_owners
= 0;
4462 for (auto &lock_owner
: lock_owner_list
) {
4463 lock_owners
[(*max_lock_owners
)++] = strdup(lock_owner
.c_str());
4466 *max_lock_owners
= lock_owner_list
.size();
4470 tracepoint(librbd
, lock_get_owners_exit
, ictx
, r
);
4474 extern "C" void rbd_lock_get_owners_cleanup(char **lock_owners
,
4475 size_t lock_owner_count
)
4477 for (size_t i
= 0; i
< lock_owner_count
; ++i
) {
4478 free(lock_owners
[i
]);
4482 extern "C" int rbd_lock_break(rbd_image_t image
, rbd_lock_mode_t lock_mode
,
4483 const char *lock_owner
)
4485 librbd::ImageCtx
*ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4486 tracepoint(librbd
, lock_break_enter
, ictx
, lock_mode
, lock_owner
);
4487 int r
= librbd::lock_break(ictx
, lock_mode
, lock_owner
);
4488 tracepoint(librbd
, lock_break_exit
, ictx
, r
);
4492 extern "C" int rbd_rebuild_object_map(rbd_image_t image
,
4493 librbd_progress_fn_t cb
, void *cbdata
)
4495 librbd::ImageCtx
*ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4496 librbd::CProgressContext
prog_ctx(cb
, cbdata
);
4497 return ictx
->operations
->rebuild_object_map(prog_ctx
);
4501 extern "C" int rbd_snap_create(rbd_image_t image
, const char *snap_name
)
4503 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4504 tracepoint(librbd
, snap_create_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
4505 int r
= ictx
->operations
->snap_create(cls::rbd::UserSnapshotNamespace(),
4507 tracepoint(librbd
, snap_create_exit
, r
);
4511 extern "C" int rbd_snap_rename(rbd_image_t image
, const char *srcname
, const char *dstname
)
4513 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4514 tracepoint(librbd
, snap_rename_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, srcname
, dstname
);
4515 int r
= ictx
->operations
->snap_rename(srcname
, dstname
);
4516 tracepoint(librbd
, snap_rename_exit
, r
);
4520 extern "C" int rbd_snap_remove(rbd_image_t image
, const char *snap_name
)
4522 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4523 tracepoint(librbd
, snap_remove_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
4524 librbd::NoOpProgressContext prog_ctx
;
4525 int r
= librbd::snap_remove(ictx
, snap_name
, 0, prog_ctx
);
4526 tracepoint(librbd
, snap_remove_exit
, r
);
4530 extern "C" int rbd_snap_remove2(rbd_image_t image
, const char *snap_name
, uint32_t flags
,
4531 librbd_progress_fn_t cb
, void *cbdata
)
4533 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4534 tracepoint(librbd
, snap_remove2_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
, flags
);
4535 librbd::CProgressContext
prog_ctx(cb
, cbdata
);
4536 int r
= librbd::snap_remove(ictx
, snap_name
, flags
, prog_ctx
);
4537 tracepoint(librbd
, snap_remove_exit
, r
);
4541 extern "C" int rbd_snap_remove_by_id(rbd_image_t image
, uint64_t snap_id
)
4543 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4544 return librbd::api::Snapshot
<>::remove(ictx
, snap_id
);
4547 extern "C" int rbd_snap_rollback(rbd_image_t image
, const char *snap_name
)
4549 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4550 tracepoint(librbd
, snap_rollback_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
4551 librbd::NoOpProgressContext prog_ctx
;
4552 int r
= ictx
->operations
->snap_rollback(cls::rbd::UserSnapshotNamespace(), snap_name
, prog_ctx
);
4553 tracepoint(librbd
, snap_rollback_exit
, r
);
4557 extern "C" int rbd_snap_rollback_with_progress(rbd_image_t image
,
4558 const char *snap_name
,
4559 librbd_progress_fn_t cb
,
4562 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4563 tracepoint(librbd
, snap_rollback_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
4564 librbd::CProgressContext
prog_ctx(cb
, cbdata
);
4565 int r
= ictx
->operations
->snap_rollback(cls::rbd::UserSnapshotNamespace(), snap_name
, prog_ctx
);
4566 tracepoint(librbd
, snap_rollback_exit
, r
);
4570 extern "C" int rbd_snap_list(rbd_image_t image
, rbd_snap_info_t
*snaps
,
4573 vector
<librbd::snap_info_t
> cpp_snaps
;
4574 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4575 tracepoint(librbd
, snap_list_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snaps
);
4578 tracepoint(librbd
, snap_list_exit
, -EINVAL
, 0);
4581 memset(snaps
, 0, sizeof(*snaps
) * *max_snaps
);
4583 int r
= librbd::snap_list(ictx
, cpp_snaps
);
4585 tracepoint(librbd
, snap_list_exit
, 0, *max_snaps
);
4589 tracepoint(librbd
, snap_list_exit
, r
, *max_snaps
);
4592 if (*max_snaps
< (int)cpp_snaps
.size() + 1) {
4593 *max_snaps
= (int)cpp_snaps
.size() + 1;
4594 tracepoint(librbd
, snap_list_exit
, -ERANGE
, *max_snaps
);
4600 for (i
= 0; i
< (int)cpp_snaps
.size(); i
++) {
4601 snaps
[i
].id
= cpp_snaps
[i
].id
;
4602 snaps
[i
].size
= cpp_snaps
[i
].size
;
4603 snaps
[i
].name
= strdup(cpp_snaps
[i
].name
.c_str());
4604 if (!snaps
[i
].name
) {
4605 for (int j
= 0; j
< i
; j
++)
4606 free((void *)snaps
[j
].name
);
4607 tracepoint(librbd
, snap_list_exit
, -ENOMEM
, *max_snaps
);
4610 tracepoint(librbd
, snap_list_entry
, snaps
[i
].id
, snaps
[i
].size
, snaps
[i
].name
);
4614 snaps
[i
].name
= NULL
;
4616 r
= (int)cpp_snaps
.size();
4617 tracepoint(librbd
, snap_list_exit
, r
, *max_snaps
);
4621 extern "C" void rbd_snap_list_end(rbd_snap_info_t
*snaps
)
4623 tracepoint(librbd
, snap_list_end_enter
, snaps
);
4624 while (snaps
->name
) {
4625 free((void *)snaps
->name
);
4628 tracepoint(librbd
, snap_list_end_exit
);
4631 extern "C" int rbd_snap_protect(rbd_image_t image
, const char *snap_name
)
4633 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4634 tracepoint(librbd
, snap_protect_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
4635 int r
= ictx
->operations
->snap_protect(cls::rbd::UserSnapshotNamespace(), snap_name
);
4636 tracepoint(librbd
, snap_protect_exit
, r
);
4640 extern "C" int rbd_snap_unprotect(rbd_image_t image
, const char *snap_name
)
4642 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4643 tracepoint(librbd
, snap_unprotect_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
4644 int r
= ictx
->operations
->snap_unprotect(cls::rbd::UserSnapshotNamespace(), snap_name
);
4645 tracepoint(librbd
, snap_unprotect_exit
, r
);
4649 extern "C" int rbd_snap_is_protected(rbd_image_t image
, const char *snap_name
,
4652 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4653 tracepoint(librbd
, snap_is_protected_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
4654 bool protected_snap
;
4655 int r
= librbd::snap_is_protected(ictx
, snap_name
, &protected_snap
);
4657 tracepoint(librbd
, snap_is_protected_exit
, r
, *is_protected
? 1 : 0);
4660 *is_protected
= protected_snap
? 1 : 0;
4661 tracepoint(librbd
, snap_is_protected_exit
, 0, *is_protected
? 1 : 0);
4665 extern "C" int rbd_snap_get_limit(rbd_image_t image
, uint64_t *limit
)
4667 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4668 tracepoint(librbd
, snap_get_limit_enter
, ictx
, ictx
->name
.c_str());
4669 int r
= librbd::snap_get_limit(ictx
, limit
);
4670 tracepoint(librbd
, snap_get_limit_exit
, r
, *limit
);
4674 extern "C" int rbd_snap_get_timestamp(rbd_image_t image
, uint64_t snap_id
, struct timespec
*timestamp
)
4676 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4677 tracepoint(librbd
, snap_get_timestamp_enter
, ictx
, ictx
->name
.c_str());
4678 int r
= librbd::snap_get_timestamp(ictx
, snap_id
, timestamp
);
4679 tracepoint(librbd
, snap_get_timestamp_exit
, r
);
4683 extern "C" int rbd_snap_set_limit(rbd_image_t image
, uint64_t limit
)
4685 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4686 tracepoint(librbd
, snap_set_limit_enter
, ictx
, ictx
->name
.c_str(), limit
);
4687 int r
= librbd::snap_set_limit(ictx
, limit
);
4688 tracepoint(librbd
, snap_set_limit_exit
, r
);
4692 extern "C" int rbd_snap_set(rbd_image_t image
, const char *snap_name
)
4694 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4695 tracepoint(librbd
, snap_set_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, snap_name
);
4696 int r
= librbd::api::Image
<>::snap_set(
4697 ictx
, cls::rbd::UserSnapshotNamespace(), snap_name
);
4698 tracepoint(librbd
, snap_set_exit
, r
);
4702 extern "C" int rbd_snap_set_by_id(rbd_image_t image
, uint64_t snap_id
)
4704 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4705 return librbd::api::Image
<>::snap_set(ictx
, snap_id
);
4708 extern "C" ssize_t
rbd_list_children(rbd_image_t image
, char *pools
,
4709 size_t *pools_len
, char *images
,
4712 auto ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4713 tracepoint(librbd
, list_children_enter
, ictx
, ictx
->name
.c_str(),
4714 ictx
->snap_name
.c_str(), ictx
->read_only
);
4716 std::vector
<librbd::linked_image_spec_t
> cpp_images
;
4717 int r
= librbd::api::Image
<>::list_children(ictx
, &cpp_images
);
4719 tracepoint(librbd
, list_children_exit
, r
);
4723 std::set
<std::pair
<std::string
, std::string
>> image_set
;
4724 for (auto& image
: cpp_images
) {
4726 image_set
.insert({image
.pool_name
, image
.image_name
});
4730 size_t pools_total
= 0;
4731 size_t images_total
= 0;
4732 for (auto it
: image_set
) {
4733 pools_total
+= it
.first
.length() + 1;
4734 images_total
+= it
.second
.length() + 1;
4737 bool too_short
= false;
4738 if (pools_total
> *pools_len
)
4740 if (images_total
> *images_len
)
4742 *pools_len
= pools_total
;
4743 *images_len
= images_total
;
4745 tracepoint(librbd
, list_children_exit
, -ERANGE
);
4749 char *pools_p
= pools
;
4750 char *images_p
= images
;
4751 for (auto it
: image_set
) {
4752 const char* pool
= it
.first
.c_str();
4753 strcpy(pools_p
, pool
);
4754 pools_p
+= it
.first
.length() + 1;
4755 const char* image
= it
.second
.c_str();
4756 strcpy(images_p
, image
);
4757 images_p
+= it
.second
.length() + 1;
4758 tracepoint(librbd
, list_children_entry
, pool
, image
);
4761 ssize_t ret
= image_set
.size();
4762 tracepoint(librbd
, list_children_exit
, ret
);
4766 extern "C" int rbd_list_children2(rbd_image_t image
,
4767 rbd_child_info_t
*children
,
4770 auto ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4771 tracepoint(librbd
, list_children_enter
, ictx
, ictx
->name
.c_str(),
4772 ictx
->snap_name
.c_str(), ictx
->read_only
);
4773 memset(children
, 0, sizeof(*children
) * *max_children
);
4775 if (!max_children
) {
4776 tracepoint(librbd
, list_children_exit
, -EINVAL
);
4780 std::vector
<librbd::linked_image_spec_t
> cpp_children
;
4781 int r
= librbd::api::Image
<>::list_children(ictx
, &cpp_children
);
4783 tracepoint(librbd
, list_children_exit
, r
);
4787 if (*max_children
< (int)cpp_children
.size() + 1) {
4788 *max_children
= (int)cpp_children
.size() + 1;
4789 tracepoint(librbd
, list_children_exit
, *max_children
);
4794 for (i
= 0; i
< (int)cpp_children
.size(); i
++) {
4795 children
[i
].pool_name
= strdup(cpp_children
[i
].pool_name
.c_str());
4796 children
[i
].image_name
= strdup(cpp_children
[i
].image_name
.c_str());
4797 children
[i
].image_id
= strdup(cpp_children
[i
].image_id
.c_str());
4798 children
[i
].trash
= cpp_children
[i
].trash
;
4799 tracepoint(librbd
, list_children_entry
, children
[i
].pool_name
,
4800 children
[i
].image_name
);
4802 children
[i
].pool_name
= NULL
;
4803 children
[i
].image_name
= NULL
;
4804 children
[i
].image_id
= NULL
;
4806 r
= (int)cpp_children
.size();
4807 tracepoint(librbd
, list_children_exit
, *max_children
);
4811 extern "C" void rbd_list_child_cleanup(rbd_child_info_t
*child
)
4813 free((void *)child
->pool_name
);
4814 free((void *)child
->image_name
);
4815 free((void *)child
->image_id
);
4818 extern "C" void rbd_list_children_cleanup(rbd_child_info_t
*children
,
4819 size_t num_children
)
4821 for (size_t i
=0; i
< num_children
; i
++) {
4822 free((void *)children
[i
].pool_name
);
4823 free((void *)children
[i
].image_name
);
4824 free((void *)children
[i
].image_id
);
4828 extern "C" int rbd_list_children3(rbd_image_t image
,
4829 rbd_linked_image_spec_t
*images
,
4832 auto ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4833 tracepoint(librbd
, list_children_enter
, ictx
, ictx
->name
.c_str(),
4834 ictx
->snap_name
.c_str(), ictx
->read_only
);
4835 memset(images
, 0, sizeof(*images
) * *max_images
);
4837 std::vector
<librbd::linked_image_spec_t
> cpp_children
;
4838 int r
= librbd::api::Image
<>::list_children(ictx
, &cpp_children
);
4840 tracepoint(librbd
, list_children_exit
, r
);
4844 if (*max_images
< cpp_children
.size()) {
4845 *max_images
= cpp_children
.size();
4849 *max_images
= cpp_children
.size();
4850 for (size_t idx
= 0; idx
< cpp_children
.size(); ++idx
) {
4852 .pool_id
= cpp_children
[idx
].pool_id
,
4853 .pool_name
= strdup(cpp_children
[idx
].pool_name
.c_str()),
4854 .pool_namespace
= strdup(cpp_children
[idx
].pool_namespace
.c_str()),
4855 .image_id
= strdup(cpp_children
[idx
].image_id
.c_str()),
4856 .image_name
= strdup(cpp_children
[idx
].image_name
.c_str()),
4857 .trash
= cpp_children
[idx
].trash
};
4858 tracepoint(librbd
, list_children_entry
, images
[idx
].pool_name
,
4859 images
[idx
].image_name
);
4864 extern "C" int rbd_list_descendants(rbd_image_t image
,
4865 rbd_linked_image_spec_t
*images
,
4868 auto ictx
= reinterpret_cast<librbd::ImageCtx
*>(image
);
4869 memset(images
, 0, sizeof(*images
) * *max_images
);
4871 std::vector
<librbd::linked_image_spec_t
> cpp_children
;
4872 int r
= librbd::api::Image
<>::list_descendants(ictx
, {}, &cpp_children
);
4877 if (*max_images
< cpp_children
.size()) {
4878 *max_images
= cpp_children
.size();
4882 *max_images
= cpp_children
.size();
4883 for (size_t idx
= 0; idx
< cpp_children
.size(); ++idx
) {
4885 .pool_id
= cpp_children
[idx
].pool_id
,
4886 .pool_name
= strdup(cpp_children
[idx
].pool_name
.c_str()),
4887 .pool_namespace
= strdup(cpp_children
[idx
].pool_namespace
.c_str()),
4888 .image_id
= strdup(cpp_children
[idx
].image_id
.c_str()),
4889 .image_name
= strdup(cpp_children
[idx
].image_name
.c_str()),
4890 .trash
= cpp_children
[idx
].trash
};
4895 extern "C" ssize_t
rbd_list_lockers(rbd_image_t image
, int *exclusive
,
4896 char *tag
, size_t *tag_len
,
4897 char *clients
, size_t *clients_len
,
4898 char *cookies
, size_t *cookies_len
,
4899 char *addrs
, size_t *addrs_len
)
4901 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4902 tracepoint(librbd
, list_lockers_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
4903 std::list
<librbd::locker_t
> lockers
;
4904 bool exclusive_bool
;
4907 int r
= list_lockers(ictx
, &lockers
, &exclusive_bool
, &tag_str
);
4909 tracepoint(librbd
, list_lockers_exit
, r
);
4913 ldout(ictx
->cct
, 20) << "list_lockers r = " << r
<< " lockers.size() = " << lockers
.size() << dendl
;
4915 *exclusive
= (int)exclusive_bool
;
4916 size_t clients_total
= 0;
4917 size_t cookies_total
= 0;
4918 size_t addrs_total
= 0;
4919 for (list
<librbd::locker_t
>::const_iterator it
= lockers
.begin();
4920 it
!= lockers
.end(); ++it
) {
4921 clients_total
+= it
->client
.length() + 1;
4922 cookies_total
+= it
->cookie
.length() + 1;
4923 addrs_total
+= it
->address
.length() + 1;
4926 bool too_short
= ((clients_total
> *clients_len
) ||
4927 (cookies_total
> *cookies_len
) ||
4928 (addrs_total
> *addrs_len
) ||
4929 (tag_str
.length() + 1 > *tag_len
));
4930 *clients_len
= clients_total
;
4931 *cookies_len
= cookies_total
;
4932 *addrs_len
= addrs_total
;
4933 *tag_len
= tag_str
.length() + 1;
4935 tracepoint(librbd
, list_lockers_exit
, -ERANGE
);
4939 strcpy(tag
, tag_str
.c_str());
4940 char *clients_p
= clients
;
4941 char *cookies_p
= cookies
;
4942 char *addrs_p
= addrs
;
4943 for (list
<librbd::locker_t
>::const_iterator it
= lockers
.begin();
4944 it
!= lockers
.end(); ++it
) {
4945 const char* client
= it
->client
.c_str();
4946 strcpy(clients_p
, client
);
4947 clients_p
+= it
->client
.length() + 1;
4948 const char* cookie
= it
->cookie
.c_str();
4949 strcpy(cookies_p
, cookie
);
4950 cookies_p
+= it
->cookie
.length() + 1;
4951 const char* address
= it
->address
.c_str();
4952 strcpy(addrs_p
, address
);
4953 addrs_p
+= it
->address
.length() + 1;
4954 tracepoint(librbd
, list_lockers_entry
, client
, cookie
, address
);
4957 ssize_t ret
= lockers
.size();
4958 tracepoint(librbd
, list_lockers_exit
, ret
);
4962 extern "C" int rbd_lock_exclusive(rbd_image_t image
, const char *cookie
)
4964 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4965 tracepoint(librbd
, lock_exclusive_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, cookie
);
4966 int r
= librbd::lock(ictx
, true, cookie
? cookie
: "", "");
4967 tracepoint(librbd
, lock_exclusive_exit
, r
);
4971 extern "C" int rbd_lock_shared(rbd_image_t image
, const char *cookie
,
4974 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4975 tracepoint(librbd
, lock_shared_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, cookie
, tag
);
4976 int r
= librbd::lock(ictx
, false, cookie
? cookie
: "", tag
? tag
: "");
4977 tracepoint(librbd
, lock_shared_exit
, r
);
4981 extern "C" int rbd_unlock(rbd_image_t image
, const char *cookie
)
4983 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4984 tracepoint(librbd
, unlock_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, cookie
);
4985 int r
= librbd::unlock(ictx
, cookie
? cookie
: "");
4986 tracepoint(librbd
, unlock_exit
, r
);
4990 extern "C" int rbd_break_lock(rbd_image_t image
, const char *client
,
4993 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
4994 tracepoint(librbd
, break_lock_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, client
, cookie
);
4995 int r
= librbd::break_lock(ictx
, client
, cookie
? cookie
: "");
4996 tracepoint(librbd
, break_lock_exit
, r
);
5001 extern "C" ssize_t
rbd_read(rbd_image_t image
, uint64_t ofs
, size_t len
,
5004 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5005 tracepoint(librbd
, read_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, ofs
, len
);
5006 int r
= ictx
->io_work_queue
->read(ofs
, len
, librbd::io::ReadResult
{buf
, len
},
5008 tracepoint(librbd
, read_exit
, r
);
5012 extern "C" ssize_t
rbd_read2(rbd_image_t image
, uint64_t ofs
, size_t len
,
5013 char *buf
, int op_flags
)
5015 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5016 tracepoint(librbd
, read2_enter
, ictx
, ictx
->name
.c_str(),
5017 ictx
->snap_name
.c_str(), ictx
->read_only
, ofs
, len
, op_flags
);
5018 int r
= ictx
->io_work_queue
->read(ofs
, len
, librbd::io::ReadResult
{buf
, len
},
5020 tracepoint(librbd
, read_exit
, r
);
5025 extern "C" int64_t rbd_read_iterate(rbd_image_t image
, uint64_t ofs
, size_t len
,
5026 int (*cb
)(uint64_t, size_t, const char *, void *),
5029 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5030 tracepoint(librbd
, read_iterate_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, ofs
, len
);
5031 int64_t r
= librbd::read_iterate(ictx
, ofs
, len
, cb
, arg
);
5032 tracepoint(librbd
, read_iterate_exit
, r
);
5036 extern "C" int rbd_read_iterate2(rbd_image_t image
, uint64_t ofs
, uint64_t len
,
5037 int (*cb
)(uint64_t, size_t, const char *, void *),
5040 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5041 tracepoint(librbd
, read_iterate2_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, ofs
, len
);
5042 int64_t r
= librbd::read_iterate(ictx
, ofs
, len
, cb
, arg
);
5045 tracepoint(librbd
, read_iterate2_exit
, r
);
5049 extern "C" int rbd_diff_iterate(rbd_image_t image
,
5050 const char *fromsnapname
,
5051 uint64_t ofs
, uint64_t len
,
5052 int (*cb
)(uint64_t, size_t, int, void *),
5055 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5056 tracepoint(librbd
, diff_iterate_enter
, ictx
, ictx
->name
.c_str(),
5057 ictx
->snap_name
.c_str(), ictx
->read_only
, fromsnapname
, ofs
, len
,
5059 int r
= librbd::api::DiffIterate
<>::diff_iterate(ictx
,
5060 cls::rbd::UserSnapshotNamespace(),
5061 fromsnapname
, ofs
, len
,
5062 true, false, cb
, arg
);
5063 tracepoint(librbd
, diff_iterate_exit
, r
);
5067 extern "C" int rbd_diff_iterate2(rbd_image_t image
, const char *fromsnapname
,
5068 uint64_t ofs
, uint64_t len
,
5069 uint8_t include_parent
, uint8_t whole_object
,
5070 int (*cb
)(uint64_t, size_t, int, void *),
5073 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5074 tracepoint(librbd
, diff_iterate_enter
, ictx
, ictx
->name
.c_str(),
5075 ictx
->snap_name
.c_str(), ictx
->read_only
, fromsnapname
, ofs
, len
,
5076 include_parent
!= 0, whole_object
!= 0);
5077 int r
= librbd::api::DiffIterate
<>::diff_iterate(ictx
,
5078 cls::rbd::UserSnapshotNamespace(),
5079 fromsnapname
, ofs
, len
,
5080 include_parent
, whole_object
,
5082 tracepoint(librbd
, diff_iterate_exit
, r
);
5086 extern "C" ssize_t
rbd_write(rbd_image_t image
, uint64_t ofs
, size_t len
,
5089 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5090 tracepoint(librbd
, write_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, ofs
, len
, buf
);
5093 bl
.push_back(create_write_raw(ictx
, buf
, len
));
5094 int r
= ictx
->io_work_queue
->write(ofs
, len
, std::move(bl
), 0);
5095 tracepoint(librbd
, write_exit
, r
);
5099 extern "C" ssize_t
rbd_write2(rbd_image_t image
, uint64_t ofs
, size_t len
,
5100 const char *buf
, int op_flags
)
5102 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5103 tracepoint(librbd
, write2_enter
, ictx
, ictx
->name
.c_str(),
5104 ictx
->snap_name
.c_str(), ictx
->read_only
, ofs
, len
, buf
, op_flags
);
5107 bl
.push_back(create_write_raw(ictx
, buf
, len
));
5108 int r
= ictx
->io_work_queue
->write(ofs
, len
, std::move(bl
), op_flags
);
5109 tracepoint(librbd
, write_exit
, r
);
5114 extern "C" int rbd_discard(rbd_image_t image
, uint64_t ofs
, uint64_t len
)
5116 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5117 tracepoint(librbd
, discard_enter
, ictx
, ictx
->name
.c_str(),
5118 ictx
->snap_name
.c_str(), ictx
->read_only
, ofs
, len
);
5119 if (len
> std::numeric_limits
<int>::max()) {
5120 tracepoint(librbd
, discard_exit
, -EINVAL
);
5124 int r
= ictx
->io_work_queue
->discard(
5125 ofs
, len
, ictx
->discard_granularity_bytes
);
5126 tracepoint(librbd
, discard_exit
, r
);
5130 extern "C" ssize_t
rbd_writesame(rbd_image_t image
, uint64_t ofs
, size_t len
,
5131 const char *buf
, size_t data_len
, int op_flags
)
5133 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5134 tracepoint(librbd
, writesame_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(),
5135 ictx
->read_only
, ofs
, len
, data_len
== 0 ? NULL
: buf
, data_len
, op_flags
);
5137 if (data_len
== 0 || len
% data_len
||
5138 len
> std::numeric_limits
<int>::max()) {
5139 tracepoint(librbd
, writesame_exit
, -EINVAL
);
5143 bool discard_zero
= ictx
->config
.get_val
<bool>("rbd_discard_on_zeroed_write_same");
5144 if (discard_zero
&& mem_is_zero(buf
, data_len
)) {
5145 int r
= ictx
->io_work_queue
->discard(ofs
, len
, 0);
5146 tracepoint(librbd
, writesame_exit
, r
);
5151 bl
.push_back(create_write_raw(ictx
, buf
, data_len
));
5152 int r
= ictx
->io_work_queue
->writesame(ofs
, len
, std::move(bl
), op_flags
);
5153 tracepoint(librbd
, writesame_exit
, r
);
5157 extern "C" ssize_t
rbd_compare_and_write(rbd_image_t image
,
5158 uint64_t ofs
, size_t len
,
5159 const char *cmp_buf
,
5161 uint64_t *mismatch_off
,
5164 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5165 tracepoint(librbd
, compare_and_write_enter
, ictx
, ictx
->name
.c_str(),
5166 ictx
->snap_name
.c_str(), ictx
->read_only
, ofs
,
5167 len
, cmp_buf
, buf
, op_flags
);
5170 cmp_bl
.push_back(create_write_raw(ictx
, cmp_buf
, len
));
5172 bl
.push_back(create_write_raw(ictx
, buf
, len
));
5174 int r
= ictx
->io_work_queue
->compare_and_write(ofs
, len
, std::move(cmp_bl
),
5175 std::move(bl
), mismatch_off
,
5177 tracepoint(librbd
, compare_and_write_exit
, r
);
5181 extern "C" int rbd_aio_create_completion(void *cb_arg
,
5182 rbd_callback_t complete_cb
,
5183 rbd_completion_t
*c
)
5185 librbd::RBD::AioCompletion
*rbd_comp
=
5186 new librbd::RBD::AioCompletion(cb_arg
, complete_cb
);
5187 *c
= (rbd_completion_t
) rbd_comp
;
5191 extern "C" int rbd_aio_write(rbd_image_t image
, uint64_t off
, size_t len
,
5192 const char *buf
, rbd_completion_t c
)
5194 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5195 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5196 tracepoint(librbd
, aio_write_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, off
, len
, buf
, comp
->pc
);
5199 bl
.push_back(create_write_raw(ictx
, buf
, len
));
5200 ictx
->io_work_queue
->aio_write(get_aio_completion(comp
), off
, len
,
5202 tracepoint(librbd
, aio_write_exit
, 0);
5206 extern "C" int rbd_aio_write2(rbd_image_t image
, uint64_t off
, size_t len
,
5207 const char *buf
, rbd_completion_t c
, int op_flags
)
5209 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5210 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5211 tracepoint(librbd
, aio_write2_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(),
5212 ictx
->read_only
, off
, len
, buf
, comp
->pc
, op_flags
);
5215 bl
.push_back(create_write_raw(ictx
, buf
, len
));
5216 ictx
->io_work_queue
->aio_write(get_aio_completion(comp
), off
, len
,
5217 std::move(bl
), op_flags
);
5218 tracepoint(librbd
, aio_write_exit
, 0);
5222 extern "C" int rbd_aio_writev(rbd_image_t image
, const struct iovec
*iov
,
5223 int iovcnt
, uint64_t off
, rbd_completion_t c
)
5225 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5226 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5228 // convert the scatter list into a bufferlist
5231 for (int i
= 0; i
< iovcnt
; ++i
) {
5232 const struct iovec
&io
= iov
[i
];
5238 bl
.push_back(create_write_raw(ictx
, static_cast<char*>(io
.iov_base
),
5243 if (iovcnt
<= 0 || len
< 0) {
5247 tracepoint(librbd
, aio_write_enter
, ictx
, ictx
->name
.c_str(),
5248 ictx
->snap_name
.c_str(), ictx
->read_only
, off
, len
, NULL
,
5251 ictx
->io_work_queue
->aio_write(get_aio_completion(comp
), off
, len
,
5254 tracepoint(librbd
, aio_write_exit
, r
);
5258 extern "C" int rbd_aio_discard(rbd_image_t image
, uint64_t off
, uint64_t len
,
5261 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5262 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5263 tracepoint(librbd
, aio_discard_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, off
, len
, comp
->pc
);
5264 ictx
->io_work_queue
->aio_discard(
5265 get_aio_completion(comp
), off
, len
, ictx
->discard_granularity_bytes
);
5266 tracepoint(librbd
, aio_discard_exit
, 0);
5270 extern "C" int rbd_aio_read(rbd_image_t image
, uint64_t off
, size_t len
,
5271 char *buf
, rbd_completion_t c
)
5273 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5274 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5275 tracepoint(librbd
, aio_read_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, off
, len
, buf
, comp
->pc
);
5276 ictx
->io_work_queue
->aio_read(get_aio_completion(comp
), off
, len
,
5277 librbd::io::ReadResult
{buf
, len
}, 0);
5278 tracepoint(librbd
, aio_read_exit
, 0);
5282 extern "C" int rbd_aio_read2(rbd_image_t image
, uint64_t off
, size_t len
,
5283 char *buf
, rbd_completion_t c
, int op_flags
)
5285 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5286 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5287 tracepoint(librbd
, aio_read2_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(),
5288 ictx
->read_only
, off
, len
, buf
, comp
->pc
, op_flags
);
5289 ictx
->io_work_queue
->aio_read(get_aio_completion(comp
), off
, len
,
5290 librbd::io::ReadResult
{buf
, len
},op_flags
);
5291 tracepoint(librbd
, aio_read_exit
, 0);
5295 extern "C" int rbd_aio_readv(rbd_image_t image
, const struct iovec
*iov
,
5296 int iovcnt
, uint64_t off
, rbd_completion_t c
)
5298 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5299 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5302 for (int i
= 0; i
< iovcnt
; ++i
) {
5303 len
+= iov
[i
].iov_len
;
5310 if (iovcnt
== 0 || len
< 0) {
5314 tracepoint(librbd
, aio_read_enter
, ictx
, ictx
->name
.c_str(),
5315 ictx
->snap_name
.c_str(), ictx
->read_only
, off
, len
, NULL
,
5318 librbd::io::ReadResult read_result
;
5320 read_result
= librbd::io::ReadResult(
5321 static_cast<char *>(iov
[0].iov_base
), iov
[0].iov_len
);
5323 read_result
= librbd::io::ReadResult(iov
, iovcnt
);
5325 ictx
->io_work_queue
->aio_read(get_aio_completion(comp
), off
, len
,
5326 std::move(read_result
), 0);
5328 tracepoint(librbd
, aio_read_exit
, r
);
5332 extern "C" int rbd_flush(rbd_image_t image
)
5334 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5335 tracepoint(librbd
, flush_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
5336 int r
= ictx
->io_work_queue
->flush();
5337 tracepoint(librbd
, flush_exit
, r
);
5341 extern "C" int rbd_aio_flush(rbd_image_t image
, rbd_completion_t c
)
5343 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5344 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5345 tracepoint(librbd
, aio_flush_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
, comp
->pc
);
5346 ictx
->io_work_queue
->aio_flush(get_aio_completion(comp
));
5347 tracepoint(librbd
, aio_flush_exit
, 0);
5351 extern "C" int rbd_aio_writesame(rbd_image_t image
, uint64_t off
, size_t len
,
5352 const char *buf
, size_t data_len
, rbd_completion_t c
,
5355 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5356 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5357 tracepoint(librbd
, aio_writesame_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(),
5358 ictx
->read_only
, off
, len
, data_len
== 0 ? NULL
: buf
, data_len
, comp
->pc
,
5361 if (data_len
== 0 || len
% data_len
) {
5362 tracepoint(librbd
, aio_writesame_exit
, -EINVAL
);
5366 bool discard_zero
= ictx
->config
.get_val
<bool>("rbd_discard_on_zeroed_write_same");
5367 if (discard_zero
&& mem_is_zero(buf
, data_len
)) {
5368 ictx
->io_work_queue
->aio_discard(get_aio_completion(comp
), off
, len
, 0);
5369 tracepoint(librbd
, aio_writesame_exit
, 0);
5374 bl
.push_back(create_write_raw(ictx
, buf
, data_len
));
5375 ictx
->io_work_queue
->aio_writesame(get_aio_completion(comp
), off
, len
,
5376 std::move(bl
), op_flags
);
5377 tracepoint(librbd
, aio_writesame_exit
, 0);
5381 extern "C" ssize_t
rbd_aio_compare_and_write(rbd_image_t image
, uint64_t off
,
5382 size_t len
, const char *cmp_buf
,
5383 const char *buf
, rbd_completion_t c
,
5384 uint64_t *mismatch_off
,
5387 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5388 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5389 tracepoint(librbd
, aio_compare_and_write_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(),
5390 ictx
->read_only
, off
, len
, cmp_buf
, buf
, comp
->pc
, op_flags
);
5393 cmp_bl
.push_back(create_write_raw(ictx
, cmp_buf
, len
));
5395 bl
.push_back(create_write_raw(ictx
, buf
, len
));
5396 ictx
->io_work_queue
->aio_compare_and_write(get_aio_completion(comp
), off
, len
,
5397 std::move(cmp_bl
), std::move(bl
),
5398 mismatch_off
, op_flags
, false);
5400 tracepoint(librbd
, aio_compare_and_write_exit
, 0);
5404 extern "C" int rbd_invalidate_cache(rbd_image_t image
)
5406 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5407 tracepoint(librbd
, invalidate_cache_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
5408 int r
= librbd::invalidate_cache(ictx
);
5409 tracepoint(librbd
, invalidate_cache_exit
, r
);
5413 extern "C" int rbd_poll_io_events(rbd_image_t image
, rbd_completion_t
*comps
, int numcomp
)
5415 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5416 librbd::io::AioCompletion
*cs
[numcomp
];
5417 tracepoint(librbd
, poll_io_events_enter
, ictx
, numcomp
);
5418 int r
= librbd::poll_io_events(ictx
, cs
, numcomp
);
5419 tracepoint(librbd
, poll_io_events_exit
, r
);
5421 for (int i
= 0; i
< r
; ++i
)
5422 comps
[i
] = cs
[i
]->rbd_comp
;
5427 extern "C" int rbd_metadata_get(rbd_image_t image
, const char *key
, char *value
, size_t *vallen
)
5429 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5431 tracepoint(librbd
, metadata_get_enter
, ictx
, key
);
5432 int r
= librbd::metadata_get(ictx
, key
, &val_s
);
5434 tracepoint(librbd
, metadata_get_exit
, r
, key
, NULL
);
5437 if (*vallen
< val_s
.size() + 1) {
5439 *vallen
= val_s
.size() + 1;
5440 tracepoint(librbd
, metadata_get_exit
, r
, key
, NULL
);
5442 strncpy(value
, val_s
.c_str(), val_s
.size() + 1);
5443 tracepoint(librbd
, metadata_get_exit
, r
, key
, value
);
5448 extern "C" int rbd_metadata_set(rbd_image_t image
, const char *key
, const char *value
)
5450 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5451 tracepoint(librbd
, metadata_set_enter
, ictx
, key
, value
);
5452 int r
= ictx
->operations
->metadata_set(key
, value
);
5453 tracepoint(librbd
, metadata_set_exit
, r
);
5457 extern "C" int rbd_metadata_remove(rbd_image_t image
, const char *key
)
5459 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5460 tracepoint(librbd
, metadata_remove_enter
, ictx
, key
);
5461 int r
= ictx
->operations
->metadata_remove(key
);
5462 tracepoint(librbd
, metadata_remove_exit
, r
);
5466 extern "C" int rbd_metadata_list(rbd_image_t image
, const char *start
, uint64_t max
,
5467 char *key
, size_t *key_len
, char *value
, size_t *val_len
)
5469 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5470 tracepoint(librbd
, metadata_list_enter
, ictx
);
5471 map
<string
, bufferlist
> pairs
;
5472 int r
= librbd::metadata_list(ictx
, start
, max
, &pairs
);
5473 size_t key_total_len
= 0, val_total_len
= 0;
5474 bool too_short
= false;
5475 for (map
<string
, bufferlist
>::iterator it
= pairs
.begin();
5476 it
!= pairs
.end(); ++it
) {
5477 key_total_len
+= it
->first
.size() + 1;
5478 val_total_len
+= it
->second
.length() + 1;
5480 if (*key_len
< key_total_len
|| *val_len
< val_total_len
)
5482 *key_len
= key_total_len
;
5483 *val_len
= val_total_len
;
5485 tracepoint(librbd
, metadata_list_exit
, -ERANGE
);
5489 char *key_p
= key
, *value_p
= value
;
5491 for (map
<string
, bufferlist
>::iterator it
= pairs
.begin();
5492 it
!= pairs
.end(); ++it
) {
5493 strncpy(key_p
, it
->first
.c_str(), it
->first
.size() + 1);
5494 key_p
+= it
->first
.size() + 1;
5495 strncpy(value_p
, it
->second
.c_str(), it
->second
.length());
5496 value_p
+= it
->second
.length();
5499 tracepoint(librbd
, metadata_list_entry
, it
->first
.c_str(), it
->second
.c_str());
5501 tracepoint(librbd
, metadata_list_exit
, r
);
5505 extern "C" int rbd_mirror_image_enable(rbd_image_t image
)
5507 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5508 return librbd::api::Mirror
<>::image_enable(ictx
, false);
5511 extern "C" int rbd_mirror_image_disable(rbd_image_t image
, bool force
)
5513 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5514 return librbd::api::Mirror
<>::image_disable(ictx
, force
);
5517 extern "C" int rbd_mirror_image_promote(rbd_image_t image
, bool force
)
5519 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5520 return librbd::api::Mirror
<>::image_promote(ictx
, force
);
5523 extern "C" int rbd_mirror_image_demote(rbd_image_t image
)
5525 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5526 return librbd::api::Mirror
<>::image_demote(ictx
);
5529 extern "C" int rbd_mirror_image_resync(rbd_image_t image
)
5531 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5532 return librbd::api::Mirror
<>::image_resync(ictx
);
5535 extern "C" int rbd_mirror_image_get_info(rbd_image_t image
,
5536 rbd_mirror_image_info_t
*mirror_image_info
,
5539 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5541 if (sizeof(rbd_mirror_image_info_t
) != info_size
) {
5545 librbd::mirror_image_info_t cpp_mirror_image
;
5546 int r
= librbd::api::Mirror
<>::image_get_info(ictx
, &cpp_mirror_image
);
5551 mirror_image_info_cpp_to_c(cpp_mirror_image
, mirror_image_info
);
5555 extern "C" int rbd_mirror_image_get_status(rbd_image_t image
,
5556 rbd_mirror_image_status_t
*status
,
5559 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5561 if (sizeof(rbd_mirror_image_status_t
) != status_size
) {
5565 librbd::mirror_image_status_t cpp_status
;
5566 int r
= librbd::api::Mirror
<>::image_get_status(ictx
, &cpp_status
);
5571 mirror_image_status_cpp_to_c(cpp_status
, status
);
5575 extern "C" int rbd_mirror_image_get_instance_id(rbd_image_t image
,
5577 size_t *instance_id_max_length
)
5579 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5581 std::string cpp_instance_id
;
5582 int r
= librbd::api::Mirror
<>::image_get_instance_id(ictx
, &cpp_instance_id
);
5587 if (cpp_instance_id
.size() >= *instance_id_max_length
) {
5588 *instance_id_max_length
= cpp_instance_id
.size() + 1;
5592 strcpy(instance_id
, cpp_instance_id
.c_str());
5593 *instance_id_max_length
= cpp_instance_id
.size() + 1;
5597 extern "C" int rbd_aio_mirror_image_promote(rbd_image_t image
, bool force
,
5598 rbd_completion_t c
) {
5599 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5600 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5601 librbd::api::Mirror
<>::image_promote(
5602 ictx
, force
, new C_AioCompletion(ictx
, librbd::io::AIO_TYPE_GENERIC
,
5603 get_aio_completion(comp
)));
5607 extern "C" int rbd_aio_mirror_image_demote(rbd_image_t image
,
5608 rbd_completion_t c
) {
5609 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5610 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5611 librbd::api::Mirror
<>::image_demote(
5612 ictx
, new C_AioCompletion(ictx
, librbd::io::AIO_TYPE_GENERIC
,
5613 get_aio_completion(comp
)));
5617 extern "C" int rbd_aio_mirror_image_get_info(rbd_image_t image
,
5618 rbd_mirror_image_info_t
*info
,
5620 rbd_completion_t c
) {
5621 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5622 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5624 if (sizeof(rbd_mirror_image_info_t
) != info_size
) {
5628 auto ctx
= new C_MirrorImageGetInfo(
5629 info
, new C_AioCompletion(ictx
, librbd::io::AIO_TYPE_GENERIC
,
5630 get_aio_completion(comp
)));
5631 librbd::api::Mirror
<>::image_get_info(
5632 ictx
, &ctx
->cpp_mirror_image_info
, ctx
);
5636 extern "C" int rbd_aio_mirror_image_get_status(rbd_image_t image
,
5637 rbd_mirror_image_status_t
*status
,
5639 rbd_completion_t c
) {
5640 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5641 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5643 if (sizeof(rbd_mirror_image_status_t
) != status_size
) {
5647 auto ctx
= new C_MirrorImageGetStatus(
5648 status
, new C_AioCompletion(ictx
, librbd::io::AIO_TYPE_GENERIC
,
5649 get_aio_completion(comp
)));
5650 librbd::api::Mirror
<>::image_get_status(ictx
, &ctx
->cpp_mirror_image_status
,
5655 extern "C" int rbd_update_watch(rbd_image_t image
, uint64_t *handle
,
5656 rbd_update_callback_t watch_cb
, void *arg
)
5658 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5659 C_UpdateWatchCB
*wctx
= new C_UpdateWatchCB(watch_cb
, arg
);
5660 tracepoint(librbd
, update_watch_enter
, ictx
, wctx
);
5661 int r
= ictx
->state
->register_update_watcher(wctx
, &wctx
->handle
);
5662 tracepoint(librbd
, update_watch_exit
, r
, wctx
->handle
);
5663 *handle
= reinterpret_cast<uint64_t>(wctx
);
5667 extern "C" int rbd_update_unwatch(rbd_image_t image
, uint64_t handle
)
5669 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
5670 C_UpdateWatchCB
*wctx
= reinterpret_cast<C_UpdateWatchCB
*>(handle
);
5671 tracepoint(librbd
, update_unwatch_enter
, ictx
, wctx
->handle
);
5672 int r
= ictx
->state
->unregister_update_watcher(wctx
->handle
);
5674 tracepoint(librbd
, update_unwatch_exit
, r
);
5678 extern "C" int rbd_aio_is_complete(rbd_completion_t c
)
5680 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5681 return comp
->is_complete();
5684 extern "C" int rbd_aio_wait_for_complete(rbd_completion_t c
)
5686 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5687 return comp
->wait_for_complete();
5690 extern "C" ssize_t
rbd_aio_get_return_value(rbd_completion_t c
)
5692 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5693 return comp
->get_return_value();
5696 extern "C" void *rbd_aio_get_arg(rbd_completion_t c
)
5698 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5699 return comp
->get_arg();
5702 extern "C" void rbd_aio_release(rbd_completion_t c
)
5704 librbd::RBD::AioCompletion
*comp
= (librbd::RBD::AioCompletion
*)c
;
5708 extern "C" int rbd_group_create(rados_ioctx_t p
, const char *name
)
5710 librados::IoCtx io_ctx
;
5711 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
5712 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
5713 tracepoint(librbd
, group_create_enter
, io_ctx
.get_pool_name().c_str(),
5714 io_ctx
.get_id(), name
);
5715 int r
= librbd::api::Group
<>::create(io_ctx
, name
);
5716 tracepoint(librbd
, group_create_exit
, r
);
5720 extern "C" int rbd_group_remove(rados_ioctx_t p
, const char *name
)
5722 librados::IoCtx io_ctx
;
5723 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
5724 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
5725 tracepoint(librbd
, group_remove_enter
, io_ctx
.get_pool_name().c_str(),
5726 io_ctx
.get_id(), name
);
5727 int r
= librbd::api::Group
<>::remove(io_ctx
, name
);
5728 tracepoint(librbd
, group_remove_exit
, r
);
5732 extern "C" int rbd_group_list(rados_ioctx_t p
, char *names
, size_t *size
)
5734 librados::IoCtx io_ctx
;
5735 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
5736 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
5737 tracepoint(librbd
, group_list_enter
, io_ctx
.get_pool_name().c_str(),
5740 vector
<string
> cpp_names
;
5741 int r
= librbd::api::Group
<>::list(io_ctx
, &cpp_names
);
5744 tracepoint(librbd
, group_list_exit
, r
);
5748 size_t expected_size
= 0;
5750 for (size_t i
= 0; i
< cpp_names
.size(); i
++) {
5751 expected_size
+= cpp_names
[i
].size() + 1;
5753 if (*size
< expected_size
) {
5754 *size
= expected_size
;
5755 tracepoint(librbd
, group_list_exit
, -ERANGE
);
5759 if (names
== NULL
) {
5760 tracepoint(librbd
, group_list_exit
, -EINVAL
);
5764 for (int i
= 0; i
< (int)cpp_names
.size(); i
++) {
5765 const char* name
= cpp_names
[i
].c_str();
5766 tracepoint(librbd
, group_list_entry
, name
);
5767 strcpy(names
, name
);
5768 names
+= strlen(names
) + 1;
5770 tracepoint(librbd
, group_list_exit
, (int)expected_size
);
5771 return (int)expected_size
;
5774 extern "C" int rbd_group_rename(rados_ioctx_t p
, const char *src_name
,
5775 const char *dest_name
)
5777 librados::IoCtx io_ctx
;
5778 librados::IoCtx::from_rados_ioctx_t(p
, io_ctx
);
5779 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(io_ctx
));
5780 tracepoint(librbd
, group_rename_enter
, io_ctx
.get_pool_name().c_str(),
5781 io_ctx
.get_id(), src_name
, dest_name
);
5782 int r
= librbd::api::Group
<>::rename(io_ctx
, src_name
, dest_name
);
5783 tracepoint(librbd
, group_rename_exit
, r
);
5787 extern "C" int rbd_group_image_add(rados_ioctx_t group_p
,
5788 const char *group_name
,
5789 rados_ioctx_t image_p
,
5790 const char *image_name
)
5792 librados::IoCtx group_ioctx
;
5793 librados::IoCtx image_ioctx
;
5795 librados::IoCtx::from_rados_ioctx_t(group_p
, group_ioctx
);
5796 librados::IoCtx::from_rados_ioctx_t(image_p
, image_ioctx
);
5798 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
5799 tracepoint(librbd
, group_image_add_enter
, group_ioctx
.get_pool_name().c_str(),
5800 group_ioctx
.get_id(), group_name
, image_ioctx
.get_pool_name().c_str(),
5801 image_ioctx
.get_id(), image_name
);
5803 int r
= librbd::api::Group
<>::image_add(group_ioctx
, group_name
, image_ioctx
,
5806 tracepoint(librbd
, group_image_add_exit
, r
);
5810 extern "C" int rbd_group_image_remove(rados_ioctx_t group_p
,
5811 const char *group_name
,
5812 rados_ioctx_t image_p
,
5813 const char *image_name
)
5815 librados::IoCtx group_ioctx
;
5816 librados::IoCtx image_ioctx
;
5818 librados::IoCtx::from_rados_ioctx_t(group_p
, group_ioctx
);
5819 librados::IoCtx::from_rados_ioctx_t(image_p
, image_ioctx
);
5821 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
5822 tracepoint(librbd
, group_image_remove_enter
, group_ioctx
.get_pool_name().c_str(),
5823 group_ioctx
.get_id(), group_name
, image_ioctx
.get_pool_name().c_str(),
5824 image_ioctx
.get_id(), image_name
);
5826 int r
= librbd::api::Group
<>::image_remove(group_ioctx
, group_name
,
5827 image_ioctx
, image_name
);
5829 tracepoint(librbd
, group_image_remove_exit
, r
);
5833 extern "C" int rbd_group_image_remove_by_id(rados_ioctx_t group_p
,
5834 const char *group_name
,
5835 rados_ioctx_t image_p
,
5836 const char *image_id
)
5838 librados::IoCtx group_ioctx
;
5839 librados::IoCtx image_ioctx
;
5841 librados::IoCtx::from_rados_ioctx_t(group_p
, group_ioctx
);
5842 librados::IoCtx::from_rados_ioctx_t(image_p
, image_ioctx
);
5844 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
5845 tracepoint(librbd
, group_image_remove_by_id_enter
,
5846 group_ioctx
.get_pool_name().c_str(),
5847 group_ioctx
.get_id(), group_name
,
5848 image_ioctx
.get_pool_name().c_str(),
5849 image_ioctx
.get_id(), image_id
);
5851 int r
= librbd::api::Group
<>::image_remove_by_id(group_ioctx
, group_name
,
5852 image_ioctx
, image_id
);
5854 tracepoint(librbd
, group_image_remove_by_id_exit
, r
);
5858 extern "C" int rbd_group_image_list(rados_ioctx_t group_p
,
5859 const char *group_name
,
5860 rbd_group_image_info_t
*images
,
5861 size_t group_image_info_size
,
5864 librados::IoCtx group_ioctx
;
5865 librados::IoCtx::from_rados_ioctx_t(group_p
, group_ioctx
);
5867 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
5868 tracepoint(librbd
, group_image_list_enter
,
5869 group_ioctx
.get_pool_name().c_str(),
5870 group_ioctx
.get_id(), group_name
);
5871 memset(images
, 0, sizeof(*images
) * *image_size
);
5873 if (group_image_info_size
!= sizeof(rbd_group_image_info_t
)) {
5875 tracepoint(librbd
, group_image_list_exit
, -ERANGE
);
5879 std::vector
<librbd::group_image_info_t
> cpp_images
;
5880 int r
= librbd::api::Group
<>::image_list(group_ioctx
, group_name
,
5884 tracepoint(librbd
, group_image_list_exit
, 0);
5890 tracepoint(librbd
, group_image_list_exit
, r
);
5894 if (*image_size
< cpp_images
.size()) {
5895 *image_size
= cpp_images
.size();
5896 tracepoint(librbd
, group_image_list_exit
, -ERANGE
);
5900 for (size_t i
= 0; i
< cpp_images
.size(); ++i
) {
5901 group_image_status_cpp_to_c(cpp_images
[i
], &images
[i
]);
5904 r
= *image_size
= cpp_images
.size();
5905 tracepoint(librbd
, group_image_list_exit
, r
);
5909 extern "C" int rbd_group_info_cleanup(rbd_group_info_t
*group_info
,
5910 size_t group_info_size
) {
5911 if (group_info_size
!= sizeof(rbd_group_info_t
)) {
5915 free(group_info
->name
);
5919 extern "C" int rbd_group_image_list_cleanup(rbd_group_image_info_t
*images
,
5920 size_t group_image_info_size
,
5922 if (group_image_info_size
!= sizeof(rbd_group_image_info_t
)) {
5926 for (size_t i
= 0; i
< len
; ++i
) {
5927 free(images
[i
].name
);
5932 extern "C" int rbd_group_snap_create(rados_ioctx_t group_p
,
5933 const char *group_name
,
5934 const char *snap_name
)
5936 librados::IoCtx group_ioctx
;
5937 librados::IoCtx::from_rados_ioctx_t(group_p
, group_ioctx
);
5939 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
5940 tracepoint(librbd
, group_snap_create_enter
,
5941 group_ioctx
.get_pool_name().c_str(),
5942 group_ioctx
.get_id(), group_name
, snap_name
);
5944 int r
= librbd::api::Group
<>::snap_create(group_ioctx
, group_name
, snap_name
);
5946 tracepoint(librbd
, group_snap_create_exit
, r
);
5951 extern "C" int rbd_group_snap_remove(rados_ioctx_t group_p
,
5952 const char *group_name
,
5953 const char *snap_name
)
5955 librados::IoCtx group_ioctx
;
5956 librados::IoCtx::from_rados_ioctx_t(group_p
, group_ioctx
);
5958 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
5959 tracepoint(librbd
, group_snap_remove_enter
,
5960 group_ioctx
.get_pool_name().c_str(),
5961 group_ioctx
.get_id(), group_name
, snap_name
);
5963 int r
= librbd::api::Group
<>::snap_remove(group_ioctx
, group_name
, snap_name
);
5965 tracepoint(librbd
, group_snap_remove_exit
, r
);
5970 extern "C" int rbd_group_snap_rename(rados_ioctx_t group_p
,
5971 const char *group_name
,
5972 const char *old_snap_name
,
5973 const char *new_snap_name
)
5975 librados::IoCtx group_ioctx
;
5976 librados::IoCtx::from_rados_ioctx_t(group_p
, group_ioctx
);
5978 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
5979 tracepoint(librbd
, group_snap_rename_enter
,
5980 group_ioctx
.get_pool_name().c_str(), group_ioctx
.get_id(),
5981 group_name
, old_snap_name
, new_snap_name
);
5983 int r
= librbd::api::Group
<>::snap_rename(group_ioctx
, group_name
,
5984 old_snap_name
, new_snap_name
);
5986 tracepoint(librbd
, group_snap_list_exit
, r
);
5990 extern "C" int rbd_group_snap_list(rados_ioctx_t group_p
,
5991 const char *group_name
,
5992 rbd_group_snap_info_t
*snaps
,
5993 size_t group_snap_info_size
,
5996 librados::IoCtx group_ioctx
;
5997 librados::IoCtx::from_rados_ioctx_t(group_p
, group_ioctx
);
5999 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
6000 tracepoint(librbd
, group_snap_list_enter
, group_ioctx
.get_pool_name().c_str(),
6001 group_ioctx
.get_id(), group_name
);
6002 memset(snaps
, 0, sizeof(*snaps
) * *snaps_size
);
6004 if (group_snap_info_size
!= sizeof(rbd_group_snap_info_t
)) {
6006 tracepoint(librbd
, group_snap_list_exit
, -ERANGE
);
6010 std::vector
<librbd::group_snap_info_t
> cpp_snaps
;
6011 int r
= librbd::api::Group
<>::snap_list(group_ioctx
, group_name
, &cpp_snaps
);
6015 tracepoint(librbd
, group_snap_list_exit
, 0);
6020 tracepoint(librbd
, group_snap_list_exit
, r
);
6024 if (*snaps_size
< cpp_snaps
.size()) {
6025 *snaps_size
= cpp_snaps
.size();
6026 tracepoint(librbd
, group_snap_list_exit
, -ERANGE
);
6030 for (size_t i
= 0; i
< cpp_snaps
.size(); ++i
) {
6031 group_snap_info_cpp_to_c(cpp_snaps
[i
], &snaps
[i
]);
6034 r
= *snaps_size
= cpp_snaps
.size();
6035 tracepoint(librbd
, group_snap_list_exit
, r
);
6039 extern "C" int rbd_group_snap_list_cleanup(rbd_group_snap_info_t
*snaps
,
6040 size_t group_snap_info_size
,
6042 if (group_snap_info_size
!= sizeof(rbd_group_snap_info_t
)) {
6046 for (size_t i
= 0; i
< len
; ++i
) {
6047 free(snaps
[i
].name
);
6052 extern "C" int rbd_group_snap_rollback(rados_ioctx_t group_p
,
6053 const char *group_name
,
6054 const char *snap_name
)
6056 librados::IoCtx group_ioctx
;
6057 librados::IoCtx::from_rados_ioctx_t(group_p
, group_ioctx
);
6059 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
6060 tracepoint(librbd
, group_snap_rollback_enter
,
6061 group_ioctx
.get_pool_name().c_str(),
6062 group_ioctx
.get_id(), group_name
, snap_name
);
6064 librbd::NoOpProgressContext prog_ctx
;
6065 int r
= librbd::api::Group
<>::snap_rollback(group_ioctx
, group_name
,
6066 snap_name
, prog_ctx
);
6068 tracepoint(librbd
, group_snap_rollback_exit
, r
);
6073 extern "C" int rbd_group_snap_rollback_with_progress(rados_ioctx_t group_p
,
6074 const char *group_name
,
6075 const char *snap_name
,
6076 librbd_progress_fn_t cb
,
6079 librados::IoCtx group_ioctx
;
6080 librados::IoCtx::from_rados_ioctx_t(group_p
, group_ioctx
);
6082 TracepointProvider::initialize
<tracepoint_traits
>(get_cct(group_ioctx
));
6083 tracepoint(librbd
, group_snap_rollback_enter
,
6084 group_ioctx
.get_pool_name().c_str(),
6085 group_ioctx
.get_id(), group_name
, snap_name
);
6087 librbd::CProgressContext
prog_ctx(cb
, cbdata
);
6088 int r
= librbd::api::Group
<>::snap_rollback(group_ioctx
, group_name
,
6089 snap_name
, prog_ctx
);
6091 tracepoint(librbd
, group_snap_rollback_exit
, r
);
6096 extern "C" int rbd_snap_get_namespace_type(rbd_image_t image
,
6098 rbd_snap_namespace_type_t
*namespace_type
) {
6099 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
6100 tracepoint(librbd
, snap_get_namespace_type_enter
, ictx
, ictx
->name
.c_str());
6101 int r
= librbd::api::Snapshot
<>::get_namespace_type(ictx
, snap_id
,
6103 tracepoint(librbd
, snap_get_namespace_type_exit
, r
);
6107 extern "C" int rbd_snap_get_group_namespace(rbd_image_t image
, uint64_t snap_id
,
6108 rbd_snap_group_namespace_t
*group_snap
,
6109 size_t snap_group_namespace_size
) {
6110 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
6111 tracepoint(librbd
, snap_get_group_namespace_enter
, ictx
,
6112 ictx
->name
.c_str());
6114 if (snap_group_namespace_size
!= sizeof(rbd_snap_group_namespace_t
)) {
6115 tracepoint(librbd
, snap_get_group_namespace_exit
, -ERANGE
);
6119 librbd::snap_group_namespace_t group_namespace
;
6120 int r
= librbd::api::Snapshot
<>::get_group_namespace(ictx
, snap_id
,
6123 group_snap
->group_pool
= group_namespace
.group_pool
;
6124 group_snap
->group_name
= strdup(group_namespace
.group_name
.c_str());
6125 group_snap
->group_snap_name
=
6126 strdup(group_namespace
.group_snap_name
.c_str());
6129 tracepoint(librbd
, snap_get_group_namespace_exit
, r
);
6133 extern "C" int rbd_snap_group_namespace_cleanup(rbd_snap_group_namespace_t
*group_snap
,
6134 size_t snap_group_namespace_size
) {
6135 if (snap_group_namespace_size
!= sizeof(rbd_snap_group_namespace_t
)) {
6136 tracepoint(librbd
, snap_get_group_namespace_exit
, -ERANGE
);
6140 free(group_snap
->group_name
);
6141 free(group_snap
->group_snap_name
);
6145 extern "C" int rbd_snap_get_trash_namespace(rbd_image_t image
, uint64_t snap_id
,
6146 char *original_name
,
6147 size_t max_length
) {
6148 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
6150 std::string cpp_original_name
;
6151 int r
= librbd::api::Snapshot
<>::get_trash_namespace(ictx
, snap_id
,
6152 &cpp_original_name
);
6157 if (cpp_original_name
.length() >= max_length
) {
6161 strcpy(original_name
, cpp_original_name
.c_str());
6164 extern "C" int rbd_watchers_list(rbd_image_t image
,
6165 rbd_image_watcher_t
*watchers
,
6166 size_t *max_watchers
) {
6167 std::list
<librbd::image_watcher_t
> watcher_list
;
6168 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
6170 tracepoint(librbd
, list_watchers_enter
, ictx
, ictx
->name
.c_str(), ictx
->snap_name
.c_str(), ictx
->read_only
);
6171 memset(watchers
, 0, sizeof(*watchers
) * *max_watchers
);
6172 int r
= librbd::list_watchers(ictx
, watcher_list
);
6174 tracepoint(librbd
, list_watchers_exit
, r
, 0);
6178 if (watcher_list
.size() > *max_watchers
) {
6179 *max_watchers
= watcher_list
.size();
6180 tracepoint(librbd
, list_watchers_exit
, -ERANGE
, watcher_list
.size());
6185 for (auto &watcher
: watcher_list
) {
6186 tracepoint(librbd
, list_watchers_entry
, watcher
.addr
.c_str(), watcher
.id
, watcher
.cookie
);
6187 watchers
[*max_watchers
].addr
= strdup(watcher
.addr
.c_str());
6188 watchers
[*max_watchers
].id
= watcher
.id
;
6189 watchers
[*max_watchers
].cookie
= watcher
.cookie
;
6193 tracepoint(librbd
, list_watchers_exit
, r
, watcher_list
.size());
6197 extern "C" void rbd_watchers_list_cleanup(rbd_image_watcher_t
*watchers
,
6198 size_t num_watchers
) {
6199 for (size_t i
= 0; i
< num_watchers
; ++i
) {
6200 free(watchers
[i
].addr
);
6204 extern "C" int rbd_config_image_list(rbd_image_t image
,
6205 rbd_config_option_t
*options
,
6207 librbd::ImageCtx
*ictx
= (librbd::ImageCtx
*)image
;
6209 std::vector
<librbd::config_option_t
> option_vector
;
6210 int r
= librbd::api::Config
<>::list(ictx
, &option_vector
);
6215 if (*max_options
< static_cast<int>(option_vector
.size())) {
6216 *max_options
= static_cast<int>(option_vector
.size());
6220 for (int i
= 0; i
< static_cast<int>(option_vector
.size()); ++i
) {
6221 config_option_cpp_to_c(option_vector
[i
], &options
[i
]);
6223 *max_options
= static_cast<int>(option_vector
.size());
6227 extern "C" void rbd_config_image_list_cleanup(rbd_config_option_t
*options
,
6229 for (int i
= 0; i
< max_options
; ++i
) {
6230 config_option_cleanup(options
[i
]);