]>
Commit | Line | Data |
---|---|---|
7c673cae FG |
1 | // -*- mode:C++; tab-width:8; c-basic-offset:2; indent-tabs-mode:t -*- |
2 | // vim: ts=8 sw=2 smarttab | |
3 | /* | |
4 | * Ceph - scalable distributed file system | |
5 | * | |
6 | * Copyright (C) 2011 New Dream Network | |
7 | * | |
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. | |
12 | * | |
13 | */ | |
14 | ||
15 | #ifndef __LIBRBD_HPP | |
16 | #define __LIBRBD_HPP | |
17 | ||
18 | #include <stdbool.h> | |
19 | #include <string> | |
20 | #include <list> | |
21 | #include <map> | |
22 | #include <vector> | |
23 | #include "../rados/buffer.h" | |
24 | #include "../rados/librados.hpp" | |
25 | #include "librbd.h" | |
26 | ||
27 | namespace librbd { | |
28 | ||
29 | using librados::IoCtx; | |
30 | ||
31 | class Image; | |
32 | class ImageOptions; | |
33 | typedef void *image_ctx_t; | |
34 | typedef void *completion_t; | |
35 | typedef void (*callback_t)(completion_t cb, void *arg); | |
36 | ||
37 | typedef struct { | |
38 | uint64_t id; | |
39 | uint64_t size; | |
40 | std::string name; | |
41 | } snap_info_t; | |
42 | ||
43 | typedef struct { | |
44 | std::string client; | |
45 | std::string cookie; | |
46 | std::string address; | |
47 | } locker_t; | |
48 | ||
49 | typedef struct { | |
50 | std::string uuid; | |
51 | std::string cluster_name; | |
52 | std::string client_name; | |
53 | } mirror_peer_t; | |
54 | ||
55 | typedef rbd_mirror_image_state_t mirror_image_state_t; | |
56 | ||
57 | typedef struct { | |
58 | std::string global_id; | |
59 | mirror_image_state_t state; | |
60 | bool primary; | |
61 | } mirror_image_info_t; | |
62 | ||
63 | typedef rbd_mirror_image_status_state_t mirror_image_status_state_t; | |
64 | ||
65 | typedef struct { | |
66 | std::string name; | |
67 | mirror_image_info_t info; | |
68 | mirror_image_status_state_t state; | |
69 | std::string description; | |
70 | time_t last_update; | |
71 | bool up; | |
72 | } mirror_image_status_t; | |
73 | ||
7c673cae FG |
74 | typedef rbd_image_info_t image_info_t; |
75 | ||
76 | class CEPH_RBD_API ProgressContext | |
77 | { | |
78 | public: | |
79 | virtual ~ProgressContext(); | |
80 | virtual int update_progress(uint64_t offset, uint64_t total) = 0; | |
81 | }; | |
82 | ||
83 | typedef struct { | |
84 | std::string id; | |
85 | std::string name; | |
86 | rbd_trash_image_source_t source; | |
87 | time_t deletion_time; | |
88 | time_t deferment_end_time; | |
89 | } trash_image_info_t; | |
90 | ||
91 | class CEPH_RBD_API RBD | |
92 | { | |
93 | public: | |
94 | RBD(); | |
95 | ~RBD(); | |
96 | ||
97 | // This must be dynamically allocated with new, and | |
98 | // must be released with release(). | |
99 | // Do not use delete. | |
100 | struct AioCompletion { | |
101 | void *pc; | |
102 | AioCompletion(void *cb_arg, callback_t complete_cb); | |
103 | bool is_complete(); | |
104 | int wait_for_complete(); | |
105 | ssize_t get_return_value(); | |
106 | void *get_arg(); | |
107 | void release(); | |
108 | }; | |
109 | ||
110 | void version(int *major, int *minor, int *extra); | |
111 | ||
112 | int open(IoCtx& io_ctx, Image& image, const char *name); | |
113 | int open(IoCtx& io_ctx, Image& image, const char *name, const char *snapname); | |
114 | int open_by_id(IoCtx& io_ctx, Image& image, const char *id); | |
115 | int open_by_id(IoCtx& io_ctx, Image& image, const char *id, const char *snapname); | |
116 | int aio_open(IoCtx& io_ctx, Image& image, const char *name, | |
117 | const char *snapname, RBD::AioCompletion *c); | |
118 | int aio_open_by_id(IoCtx& io_ctx, Image& image, const char *id, | |
119 | const char *snapname, RBD::AioCompletion *c); | |
120 | // see librbd.h | |
121 | int open_read_only(IoCtx& io_ctx, Image& image, const char *name, | |
122 | const char *snapname); | |
123 | int open_by_id_read_only(IoCtx& io_ctx, Image& image, const char *id, | |
124 | const char *snapname); | |
125 | int aio_open_read_only(IoCtx& io_ctx, Image& image, const char *name, | |
126 | const char *snapname, RBD::AioCompletion *c); | |
127 | int aio_open_by_id_read_only(IoCtx& io_ctx, Image& image, const char *id, | |
128 | const char *snapname, RBD::AioCompletion *c); | |
129 | int list(IoCtx& io_ctx, std::vector<std::string>& names); | |
130 | int create(IoCtx& io_ctx, const char *name, uint64_t size, int *order); | |
131 | int create2(IoCtx& io_ctx, const char *name, uint64_t size, | |
132 | uint64_t features, int *order); | |
133 | int create3(IoCtx& io_ctx, const char *name, uint64_t size, | |
134 | uint64_t features, int *order, | |
135 | uint64_t stripe_unit, uint64_t stripe_count); | |
136 | int create4(IoCtx& io_ctx, const char *name, uint64_t size, | |
137 | ImageOptions& opts); | |
138 | int clone(IoCtx& p_ioctx, const char *p_name, const char *p_snapname, | |
139 | IoCtx& c_ioctx, const char *c_name, uint64_t features, | |
140 | int *c_order); | |
141 | int clone2(IoCtx& p_ioctx, const char *p_name, const char *p_snapname, | |
142 | IoCtx& c_ioctx, const char *c_name, uint64_t features, | |
143 | int *c_order, uint64_t stripe_unit, int stripe_count); | |
144 | int clone3(IoCtx& p_ioctx, const char *p_name, const char *p_snapname, | |
145 | IoCtx& c_ioctx, const char *c_name, ImageOptions& opts); | |
146 | int remove(IoCtx& io_ctx, const char *name); | |
147 | int remove_with_progress(IoCtx& io_ctx, const char *name, ProgressContext& pctx); | |
148 | int rename(IoCtx& src_io_ctx, const char *srcname, const char *destname); | |
149 | ||
150 | int trash_move(IoCtx &io_ctx, const char *name, uint64_t delay); | |
151 | int trash_get(IoCtx &io_ctx, const char *id, trash_image_info_t *info); | |
152 | int trash_list(IoCtx &io_ctx, std::vector<trash_image_info_t> &entries); | |
153 | int trash_remove(IoCtx &io_ctx, const char *image_id, bool force); | |
154 | int trash_remove_with_progress(IoCtx &io_ctx, const char *image_id, | |
155 | bool force, ProgressContext &pctx); | |
156 | int trash_restore(IoCtx &io_ctx, const char *id, const char *name); | |
157 | ||
158 | // RBD pool mirroring support functions | |
159 | int mirror_mode_get(IoCtx& io_ctx, rbd_mirror_mode_t *mirror_mode); | |
160 | int mirror_mode_set(IoCtx& io_ctx, rbd_mirror_mode_t mirror_mode); | |
161 | int mirror_peer_add(IoCtx& io_ctx, std::string *uuid, | |
162 | const std::string &cluster_name, | |
163 | const std::string &client_name); | |
164 | int mirror_peer_remove(IoCtx& io_ctx, const std::string &uuid); | |
165 | int mirror_peer_list(IoCtx& io_ctx, std::vector<mirror_peer_t> *peers); | |
166 | int mirror_peer_set_client(IoCtx& io_ctx, const std::string &uuid, | |
167 | const std::string &client_name); | |
168 | int mirror_peer_set_cluster(IoCtx& io_ctx, const std::string &uuid, | |
169 | const std::string &cluster_name); | |
170 | int mirror_image_status_list(IoCtx& io_ctx, const std::string &start_id, | |
171 | size_t max, std::map<std::string, mirror_image_status_t> *images); | |
172 | int mirror_image_status_summary(IoCtx& io_ctx, | |
173 | std::map<mirror_image_status_state_t, int> *states); | |
174 | ||
7c673cae FG |
175 | private: |
176 | /* We don't allow assignment or copying */ | |
177 | RBD(const RBD& rhs); | |
178 | const RBD& operator=(const RBD& rhs); | |
179 | }; | |
180 | ||
181 | class CEPH_RBD_API ImageOptions { | |
182 | public: | |
183 | ImageOptions(); | |
184 | ImageOptions(rbd_image_options_t opts); | |
185 | ImageOptions(const ImageOptions &imgopts); | |
186 | ~ImageOptions(); | |
187 | ||
188 | int set(int optname, const std::string& optval); | |
189 | int set(int optname, uint64_t optval); | |
190 | int get(int optname, std::string* optval) const; | |
191 | int get(int optname, uint64_t* optval) const; | |
192 | int is_set(int optname, bool* is_set); | |
193 | int unset(int optname); | |
194 | void clear(); | |
195 | bool empty() const; | |
196 | ||
197 | private: | |
198 | friend class RBD; | |
199 | friend class Image; | |
200 | ||
201 | rbd_image_options_t opts; | |
202 | }; | |
203 | ||
204 | class CEPH_RBD_API UpdateWatchCtx { | |
205 | public: | |
206 | virtual ~UpdateWatchCtx() {} | |
207 | /** | |
208 | * Callback activated when we receive a notify event. | |
209 | */ | |
210 | virtual void handle_notify() = 0; | |
211 | }; | |
212 | ||
213 | class CEPH_RBD_API Image | |
214 | { | |
215 | public: | |
216 | Image(); | |
217 | ~Image(); | |
218 | ||
219 | int close(); | |
220 | int aio_close(RBD::AioCompletion *c); | |
221 | ||
222 | int resize(uint64_t size); | |
223 | int resize2(uint64_t size, bool allow_shrink, ProgressContext& pctx); | |
224 | int resize_with_progress(uint64_t size, ProgressContext& pctx); | |
225 | int stat(image_info_t &info, size_t infosize); | |
226 | int get_id(std::string *id); | |
227 | std::string get_block_name_prefix(); | |
228 | int64_t get_data_pool_id(); | |
229 | int parent_info(std::string *parent_poolname, std::string *parent_name, | |
230 | std::string *parent_snapname); | |
231 | int parent_info2(std::string *parent_poolname, std::string *parent_name, | |
232 | std::string *parent_id, std::string *parent_snapname); | |
233 | int old_format(uint8_t *old); | |
234 | int size(uint64_t *size); | |
7c673cae FG |
235 | int features(uint64_t *features); |
236 | int update_features(uint64_t features, bool enabled); | |
237 | int overlap(uint64_t *overlap); | |
238 | int get_flags(uint64_t *flags); | |
239 | int set_image_notification(int fd, int type); | |
240 | ||
241 | /* exclusive lock feature */ | |
242 | int is_exclusive_lock_owner(bool *is_owner); | |
243 | int lock_acquire(rbd_lock_mode_t lock_mode); | |
244 | int lock_release(); | |
245 | int lock_get_owners(rbd_lock_mode_t *lock_mode, | |
246 | std::list<std::string> *lock_owners); | |
247 | int lock_break(rbd_lock_mode_t lock_mode, const std::string &lock_owner); | |
248 | ||
249 | /* object map feature */ | |
250 | int rebuild_object_map(ProgressContext &prog_ctx); | |
251 | ||
252 | int check_object_map(ProgressContext &prog_ctx); | |
253 | ||
254 | int copy(IoCtx& dest_io_ctx, const char *destname); | |
255 | int copy2(Image& dest); | |
256 | int copy3(IoCtx& dest_io_ctx, const char *destname, ImageOptions& opts); | |
257 | int copy4(IoCtx& dest_io_ctx, const char *destname, ImageOptions& opts, | |
258 | size_t sparse_size); | |
259 | int copy_with_progress(IoCtx& dest_io_ctx, const char *destname, | |
260 | ProgressContext &prog_ctx); | |
261 | int copy_with_progress2(Image& dest, ProgressContext &prog_ctx); | |
262 | int copy_with_progress3(IoCtx& dest_io_ctx, const char *destname, | |
263 | ImageOptions& opts, ProgressContext &prog_ctx); | |
264 | int copy_with_progress4(IoCtx& dest_io_ctx, const char *destname, | |
265 | ImageOptions& opts, ProgressContext &prog_ctx, | |
266 | size_t sparse_size); | |
267 | ||
268 | /* striping */ | |
269 | uint64_t get_stripe_unit() const; | |
270 | uint64_t get_stripe_count() const; | |
271 | ||
31f18b77 FG |
272 | int get_create_timestamp(struct timespec *timestamp); |
273 | ||
7c673cae FG |
274 | int flatten(); |
275 | int flatten_with_progress(ProgressContext &prog_ctx); | |
276 | /** | |
277 | * Returns a pair of poolname, imagename for each clone | |
278 | * of this image at the currently set snapshot. | |
279 | */ | |
280 | int list_children(std::set<std::pair<std::string, std::string> > *children); | |
281 | ||
282 | /* advisory locking (see librbd.h for details) */ | |
283 | int list_lockers(std::list<locker_t> *lockers, | |
284 | bool *exclusive, std::string *tag); | |
285 | int lock_exclusive(const std::string& cookie); | |
286 | int lock_shared(const std::string& cookie, const std::string& tag); | |
287 | int unlock(const std::string& cookie); | |
288 | int break_lock(const std::string& client, const std::string& cookie); | |
289 | ||
290 | /* snapshots */ | |
291 | int snap_list(std::vector<snap_info_t>& snaps); | |
292 | /* DEPRECATED; use snap_exists2 */ | |
293 | bool snap_exists(const char *snapname) __attribute__ ((deprecated)); | |
294 | int snap_exists2(const char *snapname, bool *exists); | |
295 | int snap_create(const char *snapname); | |
296 | int snap_remove(const char *snapname); | |
297 | int snap_remove2(const char *snapname, uint32_t flags, ProgressContext& pctx); | |
298 | int snap_rollback(const char *snap_name); | |
299 | int snap_rollback_with_progress(const char *snap_name, ProgressContext& pctx); | |
300 | int snap_protect(const char *snap_name); | |
301 | int snap_unprotect(const char *snap_name); | |
302 | int snap_is_protected(const char *snap_name, bool *is_protected); | |
303 | int snap_set(const char *snap_name); | |
304 | int snap_rename(const char *srcname, const char *dstname); | |
305 | int snap_get_limit(uint64_t *limit); | |
306 | int snap_set_limit(uint64_t limit); | |
307 | int snap_get_timestamp(uint64_t snap_id, struct timespec *timestamp); | |
308 | ||
309 | /* I/O */ | |
310 | ssize_t read(uint64_t ofs, size_t len, ceph::bufferlist& bl); | |
311 | /* @param op_flags see librados.h constants beginning with LIBRADOS_OP_FLAG */ | |
312 | ssize_t read2(uint64_t ofs, size_t len, ceph::bufferlist& bl, int op_flags); | |
313 | int64_t read_iterate(uint64_t ofs, size_t len, | |
314 | int (*cb)(uint64_t, size_t, const char *, void *), void *arg); | |
315 | int read_iterate2(uint64_t ofs, uint64_t len, | |
316 | int (*cb)(uint64_t, size_t, const char *, void *), void *arg); | |
317 | /** | |
318 | * get difference between two versions of an image | |
319 | * | |
320 | * This will return the differences between two versions of an image | |
321 | * via a callback, which gets the offset and length and a flag | |
322 | * indicating whether the extent exists (1), or is known/defined to | |
323 | * be zeros (a hole, 0). If the source snapshot name is NULL, we | |
324 | * interpret that as the beginning of time and return all allocated | |
325 | * regions of the image. The end version is whatever is currently | |
326 | * selected for the image handle (either a snapshot or the writeable | |
327 | * head). | |
328 | * | |
329 | * @param fromsnapname start snapshot name, or NULL | |
330 | * @param ofs start offset | |
331 | * @param len len in bytes of region to report on | |
332 | * @param include_parent true if full history diff should include parent | |
333 | * @param whole_object 1 if diff extents should cover whole object | |
334 | * @param cb callback to call for each allocated region | |
335 | * @param arg argument to pass to the callback | |
336 | * @returns 0 on success, or negative error code on error | |
337 | */ | |
338 | int diff_iterate(const char *fromsnapname, | |
339 | uint64_t ofs, uint64_t len, | |
340 | int (*cb)(uint64_t, size_t, int, void *), void *arg); | |
341 | int diff_iterate2(const char *fromsnapname, | |
342 | uint64_t ofs, uint64_t len, | |
343 | bool include_parent, bool whole_object, | |
344 | int (*cb)(uint64_t, size_t, int, void *), void *arg); | |
345 | ||
346 | ssize_t write(uint64_t ofs, size_t len, ceph::bufferlist& bl); | |
347 | /* @param op_flags see librados.h constants beginning with LIBRADOS_OP_FLAG */ | |
348 | ssize_t write2(uint64_t ofs, size_t len, ceph::bufferlist& bl, int op_flags); | |
349 | int discard(uint64_t ofs, uint64_t len); | |
350 | ssize_t writesame(uint64_t ofs, size_t len, ceph::bufferlist &bl, int op_flags); | |
c07f9fc5 FG |
351 | ssize_t compare_and_write(uint64_t ofs, size_t len, ceph::bufferlist &cmp_bl, |
352 | ceph::bufferlist& bl, uint64_t *mismatch_off, int op_flags); | |
7c673cae FG |
353 | |
354 | int aio_write(uint64_t off, size_t len, ceph::bufferlist& bl, RBD::AioCompletion *c); | |
355 | /* @param op_flags see librados.h constants beginning with LIBRADOS_OP_FLAG */ | |
356 | int aio_write2(uint64_t off, size_t len, ceph::bufferlist& bl, | |
357 | RBD::AioCompletion *c, int op_flags); | |
358 | int aio_writesame(uint64_t off, size_t len, ceph::bufferlist& bl, | |
359 | RBD::AioCompletion *c, int op_flags); | |
c07f9fc5 FG |
360 | int aio_compare_and_write(uint64_t off, size_t len, ceph::bufferlist& cmp_bl, |
361 | ceph::bufferlist& bl, RBD::AioCompletion *c, | |
362 | uint64_t *mismatch_off, int op_flags); | |
7c673cae FG |
363 | /** |
364 | * read async from image | |
365 | * | |
366 | * The target bufferlist is populated with references to buffers | |
367 | * that contain the data for the given extent of the image. | |
368 | * | |
369 | * NOTE: If caching is enabled, the bufferlist will directly | |
370 | * reference buffers in the cache to avoid an unnecessary data copy. | |
371 | * As a result, if the user intends to modify the buffer contents | |
372 | * directly, they should make a copy first (unconditionally, or when | |
373 | * the reference count on ther underlying buffer is more than 1). | |
374 | * | |
375 | * @param off offset in image | |
376 | * @param len length of read | |
377 | * @param bl bufferlist to read into | |
378 | * @param c aio completion to notify when read is complete | |
379 | */ | |
380 | int aio_read(uint64_t off, size_t len, ceph::bufferlist& bl, RBD::AioCompletion *c); | |
381 | /* @param op_flags see librados.h constants beginning with LIBRADOS_OP_FLAG */ | |
382 | int aio_read2(uint64_t off, size_t len, ceph::bufferlist& bl, | |
383 | RBD::AioCompletion *c, int op_flags); | |
384 | int aio_discard(uint64_t off, uint64_t len, RBD::AioCompletion *c); | |
385 | ||
386 | int flush(); | |
387 | /** | |
388 | * Start a flush if caching is enabled. Get a callback when | |
389 | * the currently pending writes are on disk. | |
390 | * | |
391 | * @param image the image to flush writes to | |
392 | * @param c what to call when flushing is complete | |
393 | * @returns 0 on success, negative error code on failure | |
394 | */ | |
395 | int aio_flush(RBD::AioCompletion *c); | |
396 | ||
397 | /** | |
398 | * Drop any cached data for this image | |
399 | * | |
400 | * @returns 0 on success, negative error code on failure | |
401 | */ | |
402 | int invalidate_cache(); | |
403 | ||
404 | int poll_io_events(RBD::AioCompletion **comps, int numcomp); | |
405 | ||
406 | int metadata_get(const std::string &key, std::string *value); | |
407 | int metadata_set(const std::string &key, const std::string &value); | |
408 | int metadata_remove(const std::string &key); | |
409 | /** | |
410 | * Returns a pair of key/value for this image | |
411 | */ | |
412 | int metadata_list(const std::string &start, uint64_t max, std::map<std::string, ceph::bufferlist> *pairs); | |
413 | ||
414 | // RBD image mirroring support functions | |
415 | int mirror_image_enable(); | |
416 | int mirror_image_disable(bool force); | |
417 | int mirror_image_promote(bool force); | |
418 | int mirror_image_demote(); | |
419 | int mirror_image_resync(); | |
420 | int mirror_image_get_info(mirror_image_info_t *mirror_image_info, | |
421 | size_t info_size); | |
422 | int mirror_image_get_status(mirror_image_status_t *mirror_image_status, | |
423 | size_t status_size); | |
424 | int aio_mirror_image_promote(bool force, RBD::AioCompletion *c); | |
425 | int aio_mirror_image_demote(RBD::AioCompletion *c); | |
426 | int aio_mirror_image_get_info(mirror_image_info_t *mirror_image_info, | |
427 | size_t info_size, RBD::AioCompletion *c); | |
428 | int aio_mirror_image_get_status(mirror_image_status_t *mirror_image_status, | |
429 | size_t status_size, RBD::AioCompletion *c); | |
430 | ||
431 | int update_watch(UpdateWatchCtx *ctx, uint64_t *handle); | |
432 | int update_unwatch(uint64_t handle); | |
433 | ||
434 | private: | |
435 | friend class RBD; | |
436 | ||
437 | Image(const Image& rhs); | |
438 | const Image& operator=(const Image& rhs); | |
439 | ||
440 | image_ctx_t ctx; | |
441 | }; | |
442 | ||
443 | } | |
444 | ||
445 | #endif |