Fix some bugs when testing opensds ansible
[stor4nfv.git] / src / ceph / src / librbd / io / ImageRequest.h
1 // -*- mode:C++; tab-width:8; c-basic-offset:2; indent-tabs-mode:t -*-
2 // vim: ts=8 sw=2 smarttab
3
4 #ifndef CEPH_LIBRBD_IO_IMAGE_REQUEST_H
5 #define CEPH_LIBRBD_IO_IMAGE_REQUEST_H
6
7 #include "include/int_types.h"
8 #include "include/buffer_fwd.h"
9 #include "common/snap_types.h"
10 #include "common/zipkin_trace.h"
11 #include "osd/osd_types.h"
12 #include "librbd/Utils.h"
13 #include "librbd/io/Types.h"
14 #include <list>
15 #include <utility>
16 #include <vector>
17
18 namespace librbd {
19 class ImageCtx;
20
21 namespace io {
22
23 class AioCompletion;
24 class ObjectRequestHandle;
25 class ReadResult;
26
27 template <typename ImageCtxT = ImageCtx>
28 class ImageRequest {
29 public:
30   typedef std::vector<std::pair<uint64_t,uint64_t> > Extents;
31
32   virtual ~ImageRequest() {
33     m_trace.event("finish");
34   }
35
36   static ImageRequest* create_read_request(ImageCtxT &image_ctx,
37                                            AioCompletion *aio_comp,
38                                            Extents &&image_extents,
39                                            ReadResult &&read_result,
40                                            int op_flags,
41                                            const ZTracer::Trace &parent_trace);
42   static ImageRequest* create_write_request(ImageCtxT &image_ctx,
43                                             AioCompletion *aio_comp,
44                                             Extents &&image_extents,
45                                             bufferlist &&bl, int op_flags,
46                                             const ZTracer::Trace &parent_trace);
47   static ImageRequest* create_discard_request(ImageCtxT &image_ctx,
48                                               AioCompletion *aio_comp,
49                                               uint64_t off, uint64_t len,
50                                               bool skip_partial_discard,
51                                               const ZTracer::Trace &parent_trace);
52   static ImageRequest* create_flush_request(ImageCtxT &image_ctx,
53                                             AioCompletion *aio_comp,
54                                             const ZTracer::Trace &parent_trace);
55   static ImageRequest* create_writesame_request(ImageCtxT &image_ctx,
56                                                 AioCompletion *aio_comp,
57                                                 uint64_t off, uint64_t len,
58                                                 bufferlist &&bl, int op_flags,
59                                                 const ZTracer::Trace &parent_trace);
60   static ImageRequest* create_compare_and_write_request(
61       ImageCtxT &image_ctx, AioCompletion *c, Extents &&image_extents,
62       bufferlist &&cmp_bl, bufferlist &&bl, uint64_t *mismatch_offset,
63       int op_flags, const ZTracer::Trace &parent_trace);
64
65   static void aio_read(ImageCtxT *ictx, AioCompletion *c,
66                        Extents &&image_extents, ReadResult &&read_result,
67                        int op_flags, const ZTracer::Trace &parent_trace);
68   static void aio_write(ImageCtxT *ictx, AioCompletion *c,
69                         Extents &&image_extents, bufferlist &&bl, int op_flags,
70                         const ZTracer::Trace &parent_trace);
71   static void aio_discard(ImageCtxT *ictx, AioCompletion *c, uint64_t off,
72                           uint64_t len, bool skip_partial_discard,
73                           const ZTracer::Trace &parent_trace);
74   static void aio_flush(ImageCtxT *ictx, AioCompletion *c,
75                         const ZTracer::Trace &parent_trace);
76   static void aio_writesame(ImageCtxT *ictx, AioCompletion *c, uint64_t off,
77                             uint64_t len, bufferlist &&bl, int op_flags,
78                             const ZTracer::Trace &parent_trace);
79
80   static void aio_compare_and_write(ImageCtxT *ictx, AioCompletion *c,
81                                     Extents &&image_extents, bufferlist &&cmp_bl,
82                                     bufferlist &&bl, uint64_t *mismatch_offset,
83                                     int op_flags, const ZTracer::Trace &parent_trace);
84
85   virtual bool is_write_op() const {
86     return false;
87   }
88
89   void start_op();
90
91   void send();
92   void fail(int r);
93
94   void set_bypass_image_cache() {
95     m_bypass_image_cache = true;
96   }
97
98   inline const ZTracer::Trace &get_trace() const {
99     return m_trace;
100   }
101
102 protected:
103   typedef std::list<ObjectRequestHandle *> ObjectRequests;
104
105   ImageCtxT &m_image_ctx;
106   AioCompletion *m_aio_comp;
107   Extents m_image_extents;
108   ZTracer::Trace m_trace;
109   bool m_bypass_image_cache = false;
110
111   ImageRequest(ImageCtxT &image_ctx, AioCompletion *aio_comp,
112                Extents &&image_extents, const char *trace_name,
113                const ZTracer::Trace &parent_trace)
114     : m_image_ctx(image_ctx), m_aio_comp(aio_comp),
115       m_image_extents(std::move(image_extents)),
116       m_trace(util::create_trace(image_ctx, trace_name, parent_trace)) {
117     m_trace.event("start");
118   }
119   
120
121   virtual int clip_request();
122   virtual void send_request() = 0;
123   virtual void send_image_cache_request() = 0;
124
125   virtual aio_type_t get_aio_type() const = 0;
126   virtual const char *get_request_type() const = 0;
127 };
128
129 template <typename ImageCtxT = ImageCtx>
130 class ImageReadRequest : public ImageRequest<ImageCtxT> {
131 public:
132   using typename ImageRequest<ImageCtxT>::Extents;
133
134   ImageReadRequest(ImageCtxT &image_ctx, AioCompletion *aio_comp,
135                    Extents &&image_extents, ReadResult &&read_result,
136                    int op_flags, const ZTracer::Trace &parent_trace);
137
138 protected:
139   int clip_request() override;
140
141   void send_request() override;
142   void send_image_cache_request() override;
143
144   aio_type_t get_aio_type() const override {
145     return AIO_TYPE_READ;
146   }
147   const char *get_request_type() const override {
148     return "aio_read";
149   }
150 private:
151   char *m_buf;
152   bufferlist *m_pbl;
153   int m_op_flags;
154 };
155
156 template <typename ImageCtxT = ImageCtx>
157 class AbstractImageWriteRequest : public ImageRequest<ImageCtxT> {
158 public:
159   bool is_write_op() const override {
160     return true;
161   }
162
163   inline void flag_synchronous() {
164     m_synchronous = true;
165   }
166
167 protected:
168   using typename ImageRequest<ImageCtxT>::ObjectRequests;
169   using typename ImageRequest<ImageCtxT>::Extents;
170
171   typedef std::vector<ObjectExtent> ObjectExtents;
172
173   AbstractImageWriteRequest(ImageCtxT &image_ctx, AioCompletion *aio_comp,
174                             Extents &&image_extents, const char *trace_name,
175                             const ZTracer::Trace &parent_trace)
176     : ImageRequest<ImageCtxT>(image_ctx, aio_comp, std::move(image_extents),
177                               trace_name, parent_trace),
178       m_synchronous(false) {
179   }
180
181   void send_request() override;
182
183   virtual int prune_object_extents(ObjectExtents &object_extents) {
184     return 0;
185   }
186   virtual uint32_t get_object_cache_request_count(bool journaling) const {
187     return 0;
188   }
189   virtual void send_object_cache_requests(const ObjectExtents &object_extents,
190                                           uint64_t journal_tid) = 0;
191
192   virtual void send_object_requests(const ObjectExtents &object_extents,
193                                     const ::SnapContext &snapc,
194                                     ObjectRequests *object_requests);
195   virtual ObjectRequestHandle *create_object_request(
196       const ObjectExtent &object_extent, const ::SnapContext &snapc,
197       Context *on_finish) = 0;
198
199   virtual uint64_t append_journal_event(const ObjectRequests &requests,
200                                         bool synchronous) = 0;
201   virtual void update_stats(size_t length) = 0;
202
203 private:
204   bool m_synchronous;
205 };
206
207 template <typename ImageCtxT = ImageCtx>
208 class ImageWriteRequest : public AbstractImageWriteRequest<ImageCtxT> {
209 public:
210   using typename ImageRequest<ImageCtxT>::Extents;
211
212   ImageWriteRequest(ImageCtxT &image_ctx, AioCompletion *aio_comp,
213                     Extents &&image_extents, bufferlist &&bl, int op_flags,
214                     const ZTracer::Trace &parent_trace)
215     : AbstractImageWriteRequest<ImageCtxT>(
216         image_ctx, aio_comp, std::move(image_extents), "write", parent_trace),
217       m_bl(std::move(bl)), m_op_flags(op_flags) {
218   }
219
220 protected:
221   using typename ImageRequest<ImageCtxT>::ObjectRequests;
222   using typename AbstractImageWriteRequest<ImageCtxT>::ObjectExtents;
223
224   aio_type_t get_aio_type() const override {
225     return AIO_TYPE_WRITE;
226   }
227   const char *get_request_type() const override {
228     return "aio_write";
229   }
230
231   void assemble_extent(const ObjectExtent &object_extent, bufferlist *bl);
232
233   void send_image_cache_request() override;
234
235   void send_object_cache_requests(const ObjectExtents &object_extents,
236                                   uint64_t journal_tid) override;
237
238   void send_object_requests(const ObjectExtents &object_extents,
239                             const ::SnapContext &snapc,
240                             ObjectRequests *aio_object_requests) override;
241
242   ObjectRequestHandle *create_object_request(
243       const ObjectExtent &object_extent, const ::SnapContext &snapc,
244       Context *on_finish) override;
245
246   uint64_t append_journal_event(const ObjectRequests &requests,
247                                 bool synchronous) override;
248   void update_stats(size_t length) override;
249
250 private:
251   bufferlist m_bl;
252   int m_op_flags;
253 };
254
255 template <typename ImageCtxT = ImageCtx>
256 class ImageDiscardRequest : public AbstractImageWriteRequest<ImageCtxT> {
257 public:
258   ImageDiscardRequest(ImageCtxT &image_ctx, AioCompletion *aio_comp,
259                       uint64_t off, uint64_t len, bool skip_partial_discard,
260                       const ZTracer::Trace &parent_trace)
261     : AbstractImageWriteRequest<ImageCtxT>(
262         image_ctx, aio_comp, {{off, len}}, "discard", parent_trace),
263       m_skip_partial_discard(skip_partial_discard) {
264   }
265
266 protected:
267   using typename ImageRequest<ImageCtxT>::ObjectRequests;
268   using typename AbstractImageWriteRequest<ImageCtxT>::ObjectExtents;
269
270   aio_type_t get_aio_type() const override {
271     return AIO_TYPE_DISCARD;
272   }
273   const char *get_request_type() const override {
274     return "aio_discard";
275   }
276
277   int prune_object_extents(ObjectExtents &object_extents) override;
278
279   void send_image_cache_request() override;
280
281   uint32_t get_object_cache_request_count(bool journaling) const override;
282   void send_object_cache_requests(const ObjectExtents &object_extents,
283                                   uint64_t journal_tid) override;
284
285   ObjectRequestHandle *create_object_request(
286       const ObjectExtent &object_extent, const ::SnapContext &snapc,
287       Context *on_finish) override;
288
289   uint64_t append_journal_event(const ObjectRequests &requests,
290                                 bool synchronous) override;
291   void update_stats(size_t length) override;
292 private:
293   bool m_skip_partial_discard;
294 };
295
296 template <typename ImageCtxT = ImageCtx>
297 class ImageFlushRequest : public ImageRequest<ImageCtxT> {
298 public:
299   ImageFlushRequest(ImageCtxT &image_ctx, AioCompletion *aio_comp,
300                     const ZTracer::Trace &parent_trace)
301     : ImageRequest<ImageCtxT>(image_ctx, aio_comp, {}, "flush", parent_trace) {
302   }
303
304   bool is_write_op() const override {
305     return true;
306   }
307
308 protected:
309   using typename ImageRequest<ImageCtxT>::ObjectRequests;
310
311   int clip_request() override {
312     return 0;
313   }
314   void send_request() override;
315   void send_image_cache_request() override;
316
317   aio_type_t get_aio_type() const override {
318     return AIO_TYPE_FLUSH;
319   }
320   const char *get_request_type() const override {
321     return "aio_flush";
322   }
323 };
324
325 template <typename ImageCtxT = ImageCtx>
326 class ImageWriteSameRequest : public AbstractImageWriteRequest<ImageCtxT> {
327 public:
328   ImageWriteSameRequest(ImageCtxT &image_ctx, AioCompletion *aio_comp,
329                         uint64_t off, uint64_t len, bufferlist &&bl,
330                         int op_flags, const ZTracer::Trace &parent_trace)
331     : AbstractImageWriteRequest<ImageCtxT>(
332         image_ctx, aio_comp, {{off, len}}, "writesame", parent_trace),
333       m_data_bl(std::move(bl)), m_op_flags(op_flags) {
334   }
335
336 protected:
337   using typename ImageRequest<ImageCtxT>::ObjectRequests;
338   using typename AbstractImageWriteRequest<ImageCtxT>::ObjectExtents;
339
340   aio_type_t get_aio_type() const override {
341     return AIO_TYPE_WRITESAME;
342   }
343   const char *get_request_type() const override {
344     return "aio_writesame";
345   }
346
347   bool assemble_writesame_extent(const ObjectExtent &object_extent,
348                                  bufferlist *bl, bool force_write);
349
350   void send_image_cache_request() override;
351
352   void send_object_cache_requests(const ObjectExtents &object_extents,
353                                   uint64_t journal_tid) override;
354
355   void send_object_requests(const ObjectExtents &object_extents,
356                             const ::SnapContext &snapc,
357                             ObjectRequests *object_requests) override;
358   ObjectRequestHandle *create_object_request(
359       const ObjectExtent &object_extent, const ::SnapContext &snapc,
360       Context *on_finish) override;
361
362   uint64_t append_journal_event(const ObjectRequests &requests,
363                                 bool synchronous) override;
364   void update_stats(size_t length) override;
365 private:
366   bufferlist m_data_bl;
367   int m_op_flags;
368 };
369
370 template <typename ImageCtxT = ImageCtx>
371 class ImageCompareAndWriteRequest : public AbstractImageWriteRequest<ImageCtxT> {
372 public:
373   using typename ImageRequest<ImageCtxT>::ObjectRequests;
374   using typename AbstractImageWriteRequest<ImageCtxT>::ObjectExtents;
375
376   ImageCompareAndWriteRequest(ImageCtxT &image_ctx, AioCompletion *aio_comp,
377                               Extents &&image_extents, bufferlist &&cmp_bl,
378                               bufferlist &&bl, uint64_t *mismatch_offset,
379                               int op_flags, const ZTracer::Trace &parent_trace)
380       : AbstractImageWriteRequest<ImageCtxT>(
381           image_ctx, aio_comp, std::move(image_extents), "compare_and_write", parent_trace),
382         m_cmp_bl(std::move(cmp_bl)), m_bl(std::move(bl)),
383         m_mismatch_offset(mismatch_offset), m_op_flags(op_flags) {
384   }
385
386 protected:
387   void send_image_cache_request() override;
388
389   void send_object_cache_requests(const ObjectExtents &object_extents,
390                                   uint64_t journal_tid) override;
391
392   void assemble_extent(const ObjectExtent &object_extent, bufferlist *bl);
393
394   ObjectRequestHandle *create_object_request(const ObjectExtent &object_extent,
395                                              const ::SnapContext &snapc,
396                                              Context *on_finish) override;
397
398   uint64_t append_journal_event(const ObjectRequests &requests,
399                                 bool synchronous) override;
400   void update_stats(size_t length) override;
401
402   aio_type_t get_aio_type() const override {
403     return AIO_TYPE_COMPARE_AND_WRITE;
404   }
405   const char *get_request_type() const override {
406     return "aio_compare_and_write";
407   }
408
409   int prune_object_extents(ObjectExtents &object_extents) override;
410 private:
411   bufferlist m_cmp_bl;
412   bufferlist m_bl;
413   uint64_t *m_mismatch_offset;
414   int m_op_flags;
415 };
416
417 } // namespace io
418 } // namespace librbd
419
420 extern template class librbd::io::ImageRequest<librbd::ImageCtx>;
421 extern template class librbd::io::ImageReadRequest<librbd::ImageCtx>;
422 extern template class librbd::io::AbstractImageWriteRequest<librbd::ImageCtx>;
423 extern template class librbd::io::ImageWriteRequest<librbd::ImageCtx>;
424 extern template class librbd::io::ImageDiscardRequest<librbd::ImageCtx>;
425 extern template class librbd::io::ImageFlushRequest<librbd::ImageCtx>;
426 extern template class librbd::io::ImageWriteSameRequest<librbd::ImageCtx>;
427 extern template class librbd::io::ImageCompareAndWriteRequest<librbd::ImageCtx>;
428
429 #endif // CEPH_LIBRBD_IO_IMAGE_REQUEST_H