Fix some bugs when testing opensds ansible
[stor4nfv.git] / src / ceph / src / messages / MOSDPGInfo.h
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) 2004-2006 Sage Weil <sage@newdream.net>
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
16 #ifndef CEPH_MOSDPGINFO_H
17 #define CEPH_MOSDPGINFO_H
18
19 #include "msg/Message.h"
20 #include "osd/osd_types.h"
21
22 class MOSDPGInfo : public Message {
23   static const int HEAD_VERSION = 5;
24   static const int COMPAT_VERSION = 1;
25
26   epoch_t epoch = 0;
27
28 public:
29   vector<pair<pg_notify_t,PastIntervals> > pg_list;
30
31   epoch_t get_epoch() const { return epoch; }
32
33   MOSDPGInfo()
34     : Message(MSG_OSD_PG_INFO, HEAD_VERSION, COMPAT_VERSION) {
35     set_priority(CEPH_MSG_PRIO_HIGH);
36   }
37   MOSDPGInfo(version_t mv)
38     : Message(MSG_OSD_PG_INFO, HEAD_VERSION, COMPAT_VERSION),
39       epoch(mv) {
40     set_priority(CEPH_MSG_PRIO_HIGH);
41   }
42 private:
43   ~MOSDPGInfo() override {}
44
45 public:
46   const char *get_type_name() const override { return "pg_info"; }
47   void print(ostream& out) const override {
48     out << "pg_info(";
49     for (auto i = pg_list.begin();
50          i != pg_list.end();
51          ++i) {
52       if (i != pg_list.begin())
53         out << " ";
54       out << i->first << "=" << i->second;
55     }
56     out << " epoch " << epoch
57         << ")";
58   }
59
60   void encode_payload(uint64_t features) override {
61     if (HAVE_FEATURE(features, SERVER_LUMINOUS)) {
62       header.version = HEAD_VERSION;
63     } else {
64       header.version = 4;
65
66       // for kraken+jewel only
67       ::encode(epoch, payload);
68
69       // v1 was vector<pg_info_t>
70       __u32 n = pg_list.size();
71       ::encode(n, payload);
72       for (auto p = pg_list.begin();
73            p != pg_list.end();
74            p++)
75         ::encode(p->first.info, payload);
76
77       // v2 needs the PastIntervals for each record
78       for (auto p = pg_list.begin();
79            p != pg_list.end();
80            p++) {
81         p->second.encode_classic(payload);
82       }
83
84       // v3 needs epoch_sent, query_epoch
85       for (auto p = pg_list.begin();
86            p != pg_list.end();
87            p++)
88         ::encode(pair<epoch_t, epoch_t>(
89                    p->first.epoch_sent, p->first.query_epoch), payload);
90
91       // v4 needs from, to
92       for (auto p = pg_list.begin();
93            p != pg_list.end();
94            ++p) {
95         ::encode(p->first.from, payload);
96         ::encode(p->first.to, payload);
97       }
98       return;
99     }
100     ::encode(epoch, payload);
101     ::encode(pg_list, payload);
102   }
103   void decode_payload() override {
104     bufferlist::iterator p = payload.begin();
105     if (header.version < 5) {
106       ::decode(epoch, p);
107
108       // decode pg_info_t portion of the vector
109       __u32 n;
110       ::decode(n, p);
111       pg_list.resize(n);
112       for (unsigned i=0; i<n; i++) {
113         ::decode(pg_list[i].first.info, p);
114       }
115
116       if (header.version >= 2) {
117         // get the PastIntervals portion
118         for (unsigned i=0; i<n; i++) {
119           if (header.version >= 5) {
120             ::decode(pg_list[i].second, p);
121           } else {
122             pg_list[i].second.decode_classic(p);
123           }
124         }
125       }
126
127       // v3 needs epoch_sent, query_epoch
128       for (auto i = pg_list.begin();
129            i != pg_list.end();
130          i++) {
131         if (header.version >= 3) {
132           pair<epoch_t, epoch_t> dec;
133           ::decode(dec, p);
134           i->first.epoch_sent = dec.first;
135           i->first.query_epoch = dec.second;
136         } else {
137           i->first.epoch_sent = epoch;
138           i->first.query_epoch = epoch;
139         }
140       }
141
142       // v4 needs from and to
143       if (header.version >= 4) {
144         for (auto i = pg_list.begin();
145              i != pg_list.end();
146              i++) {
147           ::decode(i->first.from, p);
148           ::decode(i->first.to, p);
149         }
150       }
151       return;
152     }
153     ::decode(epoch, p);
154     ::decode(pg_list, p);
155   }
156 };
157
158 #endif