1 // -*- mode:C++; tab-width:8; c-basic-offset:2; indent-tabs-mode:t -*-
2 // vim: ts=8 sw=2 smarttab ft=cpp
4 #ifndef CEPH_RGWCACHE_H
5 #define CEPH_RGWCACHE_H
9 #include <unordered_map>
10 #include "include/types.h"
11 #include "include/utime.h"
12 #include "include/ceph_assert.h"
13 #include "common/ceph_mutex.h"
15 #include "cls/version/cls_version_types.h"
16 #include "rgw_common.h"
23 #define CACHE_FLAG_DATA 0x01
24 #define CACHE_FLAG_XATTRS 0x02
25 #define CACHE_FLAG_META 0x04
26 #define CACHE_FLAG_MODIFY_XATTRS 0x08
27 #define CACHE_FLAG_OBJV 0x10
29 struct ObjectMetaInfo
{
33 ObjectMetaInfo() : size(0) {}
35 void encode(bufferlist
& bl
) const {
36 ENCODE_START(2, 2, bl
);
41 void decode(bufferlist::const_iterator
& bl
) {
42 DECODE_START_LEGACY_COMPAT_LEN(2, 2, 2, bl
);
47 void dump(Formatter
*f
) const;
48 static void generate_test_instances(list
<ObjectMetaInfo
*>& o
);
50 WRITE_CLASS_ENCODER(ObjectMetaInfo
)
52 struct ObjectCacheInfo
{
57 map
<string
, bufferlist
> xattrs
;
58 map
<string
, bufferlist
> rm_xattrs
;
60 obj_version version
= {};
61 ceph::coarse_mono_time time_added
;
63 ObjectCacheInfo() = default;
65 void encode(bufferlist
& bl
) const {
66 ENCODE_START(5, 3, bl
);
72 encode(rm_xattrs
, bl
);
77 void decode(bufferlist::const_iterator
& bl
) {
78 DECODE_START_LEGACY_COMPAT_LEN(5, 3, 3, bl
);
85 decode(rm_xattrs
, bl
);
92 void dump(Formatter
*f
) const;
93 static void generate_test_instances(list
<ObjectCacheInfo
*>& o
);
95 WRITE_CLASS_ENCODER(ObjectCacheInfo
)
97 struct RGWCacheNotifyInfo
{
100 ObjectCacheInfo obj_info
;
104 RGWCacheNotifyInfo() : op(0), ofs(0) {}
106 void encode(bufferlist
& obl
) const {
107 ENCODE_START(2, 2, obl
);
110 encode(obj_info
, obl
);
115 void decode(bufferlist::const_iterator
& ibl
) {
116 DECODE_START_LEGACY_COMPAT_LEN(2, 2, 2, ibl
);
119 decode(obj_info
, ibl
);
124 void dump(Formatter
*f
) const;
125 static void generate_test_instances(list
<RGWCacheNotifyInfo
*>& o
);
127 WRITE_CLASS_ENCODER(RGWCacheNotifyInfo
)
129 class RGWChainedCache
{
131 virtual ~RGWChainedCache() {}
132 virtual void chain_cb(const string
& key
, void *data
) = 0;
133 virtual void invalidate(const string
& key
) = 0;
134 virtual void invalidate_all() = 0;
135 virtual void unregistered() {}
138 RGWChainedCache
*cache
;
142 Entry(RGWChainedCache
*_c
, const string
& _k
, void *_d
) : cache(_c
), key(_k
), data(_d
) {}
147 struct ObjectCacheEntry
{
148 ObjectCacheInfo info
;
149 std::list
<string
>::iterator lru_iter
;
150 uint64_t lru_promotion_ts
;
152 std::vector
<pair
<RGWChainedCache
*, string
> > chained_entries
;
154 ObjectCacheEntry() : lru_promotion_ts(0), gen(0) {}
158 std::unordered_map
<string
, ObjectCacheEntry
> cache_map
;
159 std::list
<string
> lru
;
160 unsigned long lru_size
;
161 unsigned long lru_counter
;
162 unsigned long lru_window
;
163 ceph::shared_mutex lock
= ceph::make_shared_mutex("ObjectCache");
166 vector
<RGWChainedCache
*> chained_cache
;
169 ceph::timespan expiry
;
171 void touch_lru(const DoutPrefixProvider
*dpp
, const string
& name
, ObjectCacheEntry
& entry
,
172 std::list
<string
>::iterator
& lru_iter
);
173 void remove_lru(const string
& name
, std::list
<string
>::iterator
& lru_iter
);
174 void invalidate_lru(ObjectCacheEntry
& entry
);
176 void do_invalidate_all();
179 ObjectCache() : lru_size(0), lru_counter(0), lru_window(0), cct(NULL
), enabled(false) { }
181 int get(const DoutPrefixProvider
*dpp
, const std::string
& name
, ObjectCacheInfo
& bl
, uint32_t mask
, rgw_cache_entry_info
*cache_info
);
182 std::optional
<ObjectCacheInfo
> get(const DoutPrefixProvider
*dpp
, const std::string
& name
) {
183 std::optional
<ObjectCacheInfo
> info
{std::in_place
};
184 auto r
= get(dpp
, name
, *info
, 0, nullptr);
185 return r
< 0 ? std::nullopt
: info
;
189 void for_each(const F
& f
) {
190 std::shared_lock l
{lock
};
192 auto now
= ceph::coarse_mono_clock::now();
193 for (const auto& [name
, entry
] : cache_map
) {
194 if (expiry
.count() && (now
- entry
.info
.time_added
) < expiry
) {
201 void put(const DoutPrefixProvider
*dpp
, const std::string
& name
, ObjectCacheInfo
& bl
, rgw_cache_entry_info
*cache_info
);
202 bool remove(const DoutPrefixProvider
*dpp
, const std::string
& name
);
203 void set_ctx(CephContext
*_cct
) {
205 lru_window
= cct
->_conf
->rgw_cache_lru_size
/ 2;
206 expiry
= std::chrono::seconds(cct
->_conf
.get_val
<uint64_t>(
207 "rgw_cache_expiry_interval"));
209 bool chain_cache_entry(const DoutPrefixProvider
*dpp
,
210 std::initializer_list
<rgw_cache_entry_info
*> cache_info_entries
,
211 RGWChainedCache::Entry
*chained_entry
);
213 void set_enabled(bool status
);
215 void chain_cache(RGWChainedCache
*cache
);
216 void unchain_cache(RGWChainedCache
*cache
);
217 void invalidate_all();