1 // -*- mode:C++; tab-width:8; c-basic-offset:2; indent-tabs-mode:t -*-
2 // vim: ts=8 sw=2 smarttab
4 * Ceph - scalable distributed file system
6 * Copyright (C) 2016 John Spray <john.spray@redhat.com>
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.
14 #ifndef DAEMON_STATE_H_
15 #define DAEMON_STATE_H_
21 #include <boost/circular_buffer.hpp>
23 #include "common/RWLock.h"
25 #include "msg/msg_types.h"
27 // For PerfCounterType
28 #include "messages/MMgrReport.h"
31 // Unique reference to a daemon within a cluster
32 typedef std::pair
<std::string
, std::string
> DaemonKey
;
34 // An instance of a performance counter type, within
35 // a particular daemon.
36 class PerfCounterInstance
43 DataPoint(utime_t t_
, uint64_t v_
)
48 boost::circular_buffer
<DataPoint
> buffer
;
49 uint64_t get_current() const;
52 const boost::circular_buffer
<DataPoint
> & get_data() const
56 void push(utime_t t
, uint64_t const &v
);
62 typedef std::map
<std::string
, PerfCounterType
> PerfCounterTypes
;
64 // Performance counters for one daemon
65 class DaemonPerfCounters
68 // The record of perf stat types, shared between daemons
69 PerfCounterTypes
&types
;
71 DaemonPerfCounters(PerfCounterTypes
&types_
)
75 std::map
<std::string
, PerfCounterInstance
> instances
;
77 void update(MMgrReport
*report
);
85 // The state that we store about one daemon
89 Mutex lock
= {"DaemonState::lock"};
93 // The hostname where daemon was last seen running (extracted
97 // The metadata (hostname, version, etc) sent from the daemon
98 std::map
<std::string
, std::string
> metadata
;
100 // TODO: this can be generalized to other daemons
101 std::vector
<OSDHealthMetric
> osd_health_metrics
;
104 bool service_daemon
= false;
105 utime_t service_status_stamp
;
106 std::map
<std::string
, std::string
> service_status
;
107 utime_t last_service_beacon
;
109 // The perf counters received in MMgrReport messages
110 DaemonPerfCounters perf_counters
;
112 DaemonState(PerfCounterTypes
&types_
)
113 : perf_counters(types_
)
118 typedef std::shared_ptr
<DaemonState
> DaemonStatePtr
;
119 typedef std::map
<DaemonKey
, DaemonStatePtr
> DaemonStateCollection
;
125 * Fuse the collection of per-daemon metadata from Ceph into
126 * a view that can be queried by service type, ID or also
127 * by server (aka fqdn).
129 class DaemonStateIndex
132 mutable RWLock lock
= {"DaemonStateIndex", true, true, true};
134 std::map
<std::string
, DaemonStateCollection
> by_server
;
135 DaemonStateCollection all
;
136 std::set
<DaemonKey
> updating
;
138 void _erase(const DaemonKey
& dmk
);
141 DaemonStateIndex() {}
143 // FIXME: shouldn't really be public, maybe construct DaemonState
144 // objects internally to avoid this.
145 PerfCounterTypes types
;
147 void insert(DaemonStatePtr dm
);
148 bool exists(const DaemonKey
&key
) const;
149 DaemonStatePtr
get(const DaemonKey
&key
);
151 // Note that these return by value rather than reference to avoid
152 // callers needing to stay in lock while using result. Callers must
153 // still take the individual DaemonState::lock on each entry though.
154 DaemonStateCollection
get_by_server(const std::string
&hostname
) const;
155 DaemonStateCollection
get_by_service(const std::string
&svc_name
) const;
156 DaemonStateCollection
get_all() const {return all
;}
158 template<typename Callback
, typename
...Args
>
159 auto with_daemons_by_server(Callback
&& cb
, Args
&&... args
) const ->
160 decltype(cb(by_server
, std::forward
<Args
>(args
)...)) {
161 RWLock::RLocker
l(lock
);
163 return std::forward
<Callback
>(cb
)(by_server
, std::forward
<Args
>(args
)...);
166 void notify_updating(const DaemonKey
&k
) {
167 RWLock::WLocker
l(lock
);
170 void clear_updating(const DaemonKey
&k
) {
171 RWLock::WLocker
l(lock
);
174 bool is_updating(const DaemonKey
&k
) {
175 RWLock::RLocker
l(lock
);
176 return updating
.count(k
) > 0;
180 * Remove state for all daemons of this type whose names are
181 * not present in `names_exist`. Use this function when you have
182 * a cluster map and want to ensure that anything absent in the map
183 * is also absent in this class.
185 void cull(const std::string
& svc_name
,
186 const std::set
<std::string
>& names_exist
);