Fix some bugs when testing opensds ansible
[stor4nfv.git] / src / ceph / src / rbd_replay / actions.hpp
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) 2014 Adam Crume <adamcrume@gmail.com>
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 _INCLUDED_RBD_REPLAY_ACTIONS_HPP
16 #define _INCLUDED_RBD_REPLAY_ACTIONS_HPP
17
18 #include <boost/shared_ptr.hpp>
19 #include "include/rbd/librbd.hpp"
20 #include "common/Formatter.h"
21 #include "rbd_replay/ActionTypes.h"
22 #include "rbd_loc.hpp"
23 #include <iostream>
24
25 // Stupid Doxygen requires this or else the typedef docs don't appear anywhere.
26 /// @file rbd_replay/actions.hpp
27
28 namespace rbd_replay {
29
30 typedef uint64_t imagectx_id_t;
31 typedef uint64_t thread_id_t;
32
33 /// Even IDs are normal actions, odd IDs are completions.
34 typedef uint32_t action_id_t;
35
36 class PendingIO;
37
38 /**
39    %Context through which an Action interacts with its environment.
40  */
41 class ActionCtx {
42 public:
43   virtual ~ActionCtx() {
44   }
45
46   /**
47      Returns the image with the given ID.
48      The image must have been previously tracked with put_image(imagectx_id_t,librbd::Image*).
49    */
50   virtual librbd::Image* get_image(imagectx_id_t imagectx_id) = 0;
51
52   /**
53      Tracks an image.
54      put_image(imagectx_id_t,librbd::Image*) must not have been called previously with the same ID,
55      and the image must not be NULL.
56    */
57   virtual void put_image(imagectx_id_t imagectx_id, librbd::Image* image) = 0;
58
59   /**
60      Stops tracking an Image and release it.
61      This deletes the C++ object, not the image itself.
62      The image must have been previously tracked with put_image(imagectx_id_t,librbd::Image*).
63    */
64   virtual void erase_image(imagectx_id_t imagectx_id) = 0;
65
66   virtual librbd::RBD* rbd() = 0;
67
68   virtual librados::IoCtx* ioctx() = 0;
69
70   virtual void add_pending(boost::shared_ptr<PendingIO> io) = 0;
71
72   virtual bool readonly() const = 0;
73
74   virtual void remove_pending(boost::shared_ptr<PendingIO> io) = 0;
75
76   virtual void set_action_complete(action_id_t id) = 0;
77
78   virtual void stop() = 0;
79
80   /**
81      Maps an image name from the name in the original trace to the name that should be used when replaying.
82      @param image_name name of the image in the original trace
83      @param snap_name name of the snap in the orginal trace
84      @return image name to replay against
85    */
86   virtual rbd_loc map_image_name(std::string image_name, std::string snap_name) const = 0;
87 };
88
89
90 /**
91    Performs an %IO or a maintenance action such as starting or stopping a thread.
92    Actions are read from a replay file and scheduled by Replayer.
93    Corresponds to the IO class, except that Actions are executed by rbd-replay,
94    and IOs are used by rbd-replay-prep for processing the raw trace.
95  */
96 class Action {
97 public:
98   typedef boost::shared_ptr<Action> ptr;
99
100   virtual ~Action() {
101   }
102
103   virtual void perform(ActionCtx &ctx) = 0;
104
105   /// Returns the ID of the completion corresponding to this action.
106   action_id_t pending_io_id() {
107     return id() + 1;
108   }
109
110   // There's probably a better way to do this, but oh well.
111   virtual bool is_start_thread() {
112     return false;
113   }
114
115   virtual action_id_t id() const = 0;
116   virtual thread_id_t thread_id() const = 0;
117   virtual const action::Dependencies& predecessors() const = 0;
118
119   virtual std::ostream& dump(std::ostream& o) const = 0;
120
121   static ptr construct(const action::ActionEntry &action_entry);
122 };
123
124 template <typename ActionType>
125 class TypedAction : public Action {
126 public:
127   explicit TypedAction(const ActionType &action) : m_action(action) {
128   }
129
130   action_id_t id() const override {
131     return m_action.id;
132   }
133
134   thread_id_t thread_id() const override {
135     return m_action.thread_id;
136   }
137
138   const action::Dependencies& predecessors() const override {
139     return m_action.dependencies;
140   }
141
142   std::ostream& dump(std::ostream& o) const override {
143     o << get_action_name() << ": ";
144     ceph::JSONFormatter formatter(false);
145     formatter.open_object_section("");
146     m_action.dump(&formatter);
147     formatter.close_section();
148     formatter.flush(o);
149     return o;
150   }
151
152 protected:
153   const ActionType m_action;
154
155   virtual const char *get_action_name() const = 0;
156 };
157
158 /// Writes human-readable debug information about the action to the stream.
159 /// @related Action
160 std::ostream& operator<<(std::ostream& o, const Action& a);
161
162 class StartThreadAction : public TypedAction<action::StartThreadAction> {
163 public:
164   explicit StartThreadAction(const action::StartThreadAction &action)
165     : TypedAction<action::StartThreadAction>(action) {
166   }
167
168   bool is_start_thread() override {
169     return true;
170   }
171   void perform(ActionCtx &ctx) override;
172
173 protected:
174   const char *get_action_name() const override {
175     return "StartThreadAction";
176   }
177 };
178
179 class StopThreadAction : public TypedAction<action::StopThreadAction> {
180 public:
181   explicit StopThreadAction(const action::StopThreadAction &action)
182     : TypedAction<action::StopThreadAction>(action) {
183   }
184
185   void perform(ActionCtx &ctx) override;
186
187 protected:
188   const char *get_action_name() const override {
189     return "StartThreadAction";
190   }
191 };
192
193
194 class AioReadAction : public TypedAction<action::AioReadAction> {
195 public:
196   explicit AioReadAction(const action::AioReadAction &action)
197     : TypedAction<action::AioReadAction>(action) {
198   }
199
200   void perform(ActionCtx &ctx) override;
201
202 protected:
203   const char *get_action_name() const override {
204     return "AioReadAction";
205   }
206 };
207
208
209 class ReadAction : public TypedAction<action::ReadAction> {
210 public:
211   explicit ReadAction(const action::ReadAction &action)
212     : TypedAction<action::ReadAction>(action) {
213   }
214
215   void perform(ActionCtx &ctx) override;
216
217 protected:
218   const char *get_action_name() const override {
219     return "ReadAction";
220   }
221 };
222
223
224 class AioWriteAction : public TypedAction<action::AioWriteAction> {
225 public:
226   explicit AioWriteAction(const action::AioWriteAction &action)
227     : TypedAction<action::AioWriteAction>(action) {
228   }
229
230   void perform(ActionCtx &ctx) override;
231
232 protected:
233   const char *get_action_name() const override {
234     return "AioWriteAction";
235   }
236 };
237
238
239 class WriteAction : public TypedAction<action::WriteAction> {
240 public:
241   explicit WriteAction(const action::WriteAction &action)
242     : TypedAction<action::WriteAction>(action) {
243   }
244
245   void perform(ActionCtx &ctx) override;
246
247 protected:
248   const char *get_action_name() const override {
249     return "WriteAction";
250   }
251 };
252
253
254 class AioDiscardAction : public TypedAction<action::AioDiscardAction> {
255 public:
256   explicit AioDiscardAction(const action::AioDiscardAction &action)
257     : TypedAction<action::AioDiscardAction>(action) {
258   }
259
260   void perform(ActionCtx &ctx) override;
261
262 protected:
263   const char *get_action_name() const override {
264     return "AioDiscardAction";
265   }
266 };
267
268
269 class DiscardAction : public TypedAction<action::DiscardAction> {
270 public:
271   explicit DiscardAction(const action::DiscardAction &action)
272     : TypedAction<action::DiscardAction>(action) {
273   }
274
275   void perform(ActionCtx &ctx) override;
276
277 protected:
278   const char *get_action_name() const override {
279     return "DiscardAction";
280   }
281 };
282
283
284 class OpenImageAction : public TypedAction<action::OpenImageAction> {
285 public:
286   explicit OpenImageAction(const action::OpenImageAction &action)
287     : TypedAction<action::OpenImageAction>(action) {
288   }
289
290   void perform(ActionCtx &ctx) override;
291
292 protected:
293   const char *get_action_name() const override {
294     return "OpenImageAction";
295   }
296 };
297
298
299 class CloseImageAction : public TypedAction<action::CloseImageAction> {
300 public:
301   explicit CloseImageAction(const action::CloseImageAction &action)
302     : TypedAction<action::CloseImageAction>(action) {
303   }
304
305   void perform(ActionCtx &ctx) override;
306
307 protected:
308   const char *get_action_name() const override {
309     return "CloseImageAction";
310   }
311 };
312
313 class AioOpenImageAction : public TypedAction<action::AioOpenImageAction> {
314 public:
315   explicit AioOpenImageAction(const action::AioOpenImageAction &action)
316     : TypedAction<action::AioOpenImageAction>(action) {
317   }
318
319   void perform(ActionCtx &ctx) override;
320
321 protected:
322   const char *get_action_name() const override {
323     return "AioOpenImageAction";
324   }
325 };
326
327
328 class AioCloseImageAction : public TypedAction<action::AioCloseImageAction> {
329 public:
330   explicit AioCloseImageAction(const action::AioCloseImageAction &action)
331     : TypedAction<action::AioCloseImageAction>(action) {
332   }
333
334   void perform(ActionCtx &ctx) override;
335
336 protected:
337   const char *get_action_name() const override {
338     return "AioCloseImageAction";
339   }
340 };
341
342 }
343
344 #endif