]>
Commit | Line | Data |
---|---|---|
11fdf7f2 TL |
1 | // -*- mode:C++; tab-width:8; c-basic-offset:2; indent-tabs-mode:t -*- |
2 | // vim: ts=8 sw=2 smarttab | |
3 | ||
4 | #include "librbd/image/AttachParentRequest.h" | |
5 | #include "common/dout.h" | |
6 | #include "common/errno.h" | |
11fdf7f2 TL |
7 | #include "cls/rbd/cls_rbd_client.h" |
8 | #include "librbd/ImageCtx.h" | |
9 | #include "librbd/Utils.h" | |
10 | ||
11 | #define dout_subsys ceph_subsys_rbd | |
12 | #undef dout_prefix | |
13 | #define dout_prefix *_dout << "librbd::image::AttachParentRequest: " << this \ | |
14 | << " " << __func__ << ": " | |
15 | ||
16 | namespace librbd { | |
17 | namespace image { | |
18 | ||
19 | using util::create_rados_callback; | |
20 | ||
21 | template <typename I> | |
22 | void AttachParentRequest<I>::send() { | |
23 | attach_parent(); | |
24 | } | |
25 | ||
26 | template <typename I> | |
27 | void AttachParentRequest<I>::attach_parent() { | |
28 | auto cct = m_image_ctx.cct; | |
9f95a23c | 29 | ldout(cct, 5) << "parent_image_spec=" << m_parent_image_spec << dendl; |
11fdf7f2 TL |
30 | |
31 | librados::ObjectWriteOperation op; | |
32 | if (!m_legacy_parent) { | |
33 | librbd::cls_client::parent_attach(&op, m_parent_image_spec, | |
34 | m_parent_overlap, m_reattach); | |
35 | } else { | |
36 | librbd::cls_client::set_parent(&op, m_parent_image_spec, m_parent_overlap); | |
37 | } | |
38 | ||
39 | auto aio_comp = create_rados_callback< | |
40 | AttachParentRequest<I>, | |
41 | &AttachParentRequest<I>::handle_attach_parent>(this); | |
42 | int r = m_image_ctx.md_ctx.aio_operate(m_image_ctx.header_oid, aio_comp, &op); | |
43 | ceph_assert(r == 0); | |
44 | aio_comp->release(); | |
45 | } | |
46 | ||
47 | template <typename I> | |
48 | void AttachParentRequest<I>::handle_attach_parent(int r) { | |
49 | auto cct = m_image_ctx.cct; | |
50 | ldout(cct, 5) << dendl; | |
51 | ||
52 | if (!m_legacy_parent && r == -EOPNOTSUPP && !m_reattach) { | |
53 | if (m_parent_image_spec.pool_namespace == | |
54 | m_image_ctx.md_ctx.get_namespace()) { | |
55 | m_parent_image_spec.pool_namespace = ""; | |
56 | } | |
57 | if (m_parent_image_spec.pool_namespace.empty()) { | |
58 | ldout(cct, 10) << "retrying using legacy parent method" << dendl; | |
59 | m_legacy_parent = true; | |
60 | attach_parent(); | |
61 | return; | |
62 | } | |
63 | ||
64 | // namespaces require newer OSDs | |
65 | r = -EXDEV; | |
66 | } | |
67 | ||
68 | if (r < 0) { | |
69 | lderr(cct) << "attach parent encountered an error: " << cpp_strerror(r) | |
70 | << dendl; | |
71 | finish(r); | |
72 | return; | |
73 | } | |
74 | ||
75 | finish(0); | |
76 | } | |
77 | ||
78 | template <typename I> | |
79 | void AttachParentRequest<I>::finish(int r) { | |
80 | auto cct = m_image_ctx.cct; | |
81 | ldout(cct, 5) << "r=" << r << dendl; | |
82 | ||
83 | m_on_finish->complete(r); | |
84 | delete this; | |
85 | } | |
86 | ||
87 | } // namespace image | |
88 | } // namespace librbd | |
89 | ||
90 | template class librbd::image::AttachParentRequest<librbd::ImageCtx>; |