Merge pull request #342 from mmichal10/fix-metadata-flush
Fix metadata flush
This commit is contained in:
commit
fabd41250b
@ -200,49 +200,47 @@ static inline bool metadata_test_and_clear_dirty_sec(
|
|||||||
/*
|
/*
|
||||||
* Marks given cache line's bits as clean
|
* Marks given cache line's bits as clean
|
||||||
*
|
*
|
||||||
* @return true if the cache line was dirty and became clean
|
* @return true if any cache line's sector was dirty and became clean
|
||||||
* @return false for other cases
|
* @return false for other cases
|
||||||
*/
|
*/
|
||||||
static inline bool metadata_clear_dirty_sec_changed(
|
static inline bool metadata_clear_dirty_sec_changed(
|
||||||
struct ocf_cache *cache, ocf_cache_line_t line,
|
struct ocf_cache *cache, ocf_cache_line_t line,
|
||||||
uint8_t start, uint8_t stop)
|
uint8_t start, uint8_t stop, bool *line_is_clean)
|
||||||
{
|
{
|
||||||
bool was_dirty, is_dirty = false;
|
bool sec_changed;
|
||||||
|
|
||||||
OCF_METADATA_BITS_LOCK_WR();
|
OCF_METADATA_BITS_LOCK_WR();
|
||||||
|
|
||||||
was_dirty = cache->metadata.iface.test_dirty(cache, line,
|
sec_changed = cache->metadata.iface.test_dirty(cache, line,
|
||||||
cache->metadata.settings.sector_start,
|
start, stop, false);
|
||||||
cache->metadata.settings.sector_end,
|
*line_is_clean = !cache->metadata.iface.clear_dirty(cache, line,
|
||||||
false);
|
start, stop);
|
||||||
|
|
||||||
if (was_dirty) {
|
|
||||||
is_dirty = cache->metadata.iface.clear_dirty(cache, line,
|
|
||||||
start, stop);
|
|
||||||
}
|
|
||||||
|
|
||||||
OCF_METADATA_BITS_UNLOCK_WR();
|
OCF_METADATA_BITS_UNLOCK_WR();
|
||||||
|
|
||||||
return was_dirty && !is_dirty;
|
return sec_changed;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Marks given cache line's bits as dirty
|
* Marks given cache line's bits as dirty
|
||||||
*
|
*
|
||||||
* @return true if the cache line was clean and became dirty
|
* @return true if any cache line's sector became dirty
|
||||||
* @return false if the cache line was dirty before marking bits
|
* @return false for other cases
|
||||||
*/
|
*/
|
||||||
static inline bool metadata_set_dirty_sec_changed(
|
static inline bool metadata_set_dirty_sec_changed(
|
||||||
struct ocf_cache *cache, ocf_cache_line_t line,
|
struct ocf_cache *cache, ocf_cache_line_t line,
|
||||||
uint8_t start, uint8_t stop)
|
uint8_t start, uint8_t stop, bool *line_was_dirty)
|
||||||
{
|
{
|
||||||
bool was_dirty;
|
bool sec_changed;
|
||||||
|
|
||||||
OCF_METADATA_BITS_LOCK_WR();
|
OCF_METADATA_BITS_LOCK_WR();
|
||||||
was_dirty = cache->metadata.iface.set_dirty(cache, line, start, stop);
|
sec_changed = !cache->metadata.iface.test_dirty(cache, line,
|
||||||
|
start, stop, true);
|
||||||
|
*line_was_dirty = cache->metadata.iface.set_dirty(cache, line, start,
|
||||||
|
stop);
|
||||||
OCF_METADATA_BITS_UNLOCK_WR();
|
OCF_METADATA_BITS_UNLOCK_WR();
|
||||||
|
|
||||||
return !was_dirty;
|
return sec_changed;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*******************************************************************************
|
/*******************************************************************************
|
||||||
|
@ -102,35 +102,40 @@ void set_cache_line_clean(struct ocf_cache *cache, uint8_t start_bit,
|
|||||||
ocf_cache_line_t line = req->map[map_idx].coll_idx;
|
ocf_cache_line_t line = req->map[map_idx].coll_idx;
|
||||||
ocf_part_id_t part_id = ocf_metadata_get_partition_id(cache, line);
|
ocf_part_id_t part_id = ocf_metadata_get_partition_id(cache, line);
|
||||||
uint8_t evp_type = cache->conf_meta->eviction_policy_type;
|
uint8_t evp_type = cache->conf_meta->eviction_policy_type;
|
||||||
|
bool line_is_clean;
|
||||||
|
|
||||||
if (metadata_clear_dirty_sec_changed(cache, line, start_bit, end_bit)) {
|
if (metadata_clear_dirty_sec_changed(cache, line, start_bit, end_bit,
|
||||||
/*
|
&line_is_clean)) {
|
||||||
* Update the number of dirty cached data for that
|
|
||||||
* core object
|
|
||||||
*/
|
|
||||||
if (env_atomic_dec_and_test(&req->core->runtime_meta->
|
|
||||||
dirty_clines)) {
|
|
||||||
/*
|
|
||||||
* If this is last dirty cline reset dirty
|
|
||||||
* timestamp
|
|
||||||
*/
|
|
||||||
env_atomic64_set(&req->core->runtime_meta->
|
|
||||||
dirty_since, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* decrement dirty clines statistic for given cline
|
|
||||||
*/
|
|
||||||
env_atomic_dec(&req->core->runtime_meta->
|
|
||||||
part_counters[part_id].dirty_clines);
|
|
||||||
|
|
||||||
if (likely(evict_policy_ops[evp_type].clean_cline))
|
|
||||||
evict_policy_ops[evp_type].clean_cline(cache, part_id, line);
|
|
||||||
|
|
||||||
ocf_purge_cleaning_policy(cache, line);
|
|
||||||
ocf_metadata_flush_mark(cache, req, map_idx, CLEAN, start_bit,
|
ocf_metadata_flush_mark(cache, req, map_idx, CLEAN, start_bit,
|
||||||
end_bit);
|
end_bit);
|
||||||
|
if (line_is_clean) {
|
||||||
|
/*
|
||||||
|
* Update the number of dirty cached data for that
|
||||||
|
* core object
|
||||||
|
*/
|
||||||
|
if (env_atomic_dec_and_test(&req->core->runtime_meta->
|
||||||
|
dirty_clines)) {
|
||||||
|
/*
|
||||||
|
* If this is last dirty cline reset dirty
|
||||||
|
* timestamp
|
||||||
|
*/
|
||||||
|
env_atomic64_set(&req->core->runtime_meta->
|
||||||
|
dirty_since, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* decrement dirty clines statistic for given cline
|
||||||
|
*/
|
||||||
|
env_atomic_dec(&req->core->runtime_meta->
|
||||||
|
part_counters[part_id].dirty_clines);
|
||||||
|
|
||||||
|
if (likely(evict_policy_ops[evp_type].clean_cline))
|
||||||
|
evict_policy_ops[evp_type].clean_cline(cache, part_id, line);
|
||||||
|
|
||||||
|
ocf_purge_cleaning_policy(cache, line);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void set_cache_line_dirty(struct ocf_cache *cache, uint8_t start_bit,
|
void set_cache_line_dirty(struct ocf_cache *cache, uint8_t start_bit,
|
||||||
@ -139,32 +144,36 @@ void set_cache_line_dirty(struct ocf_cache *cache, uint8_t start_bit,
|
|||||||
ocf_cache_line_t line = req->map[map_idx].coll_idx;
|
ocf_cache_line_t line = req->map[map_idx].coll_idx;
|
||||||
ocf_part_id_t part_id = ocf_metadata_get_partition_id(cache, line);
|
ocf_part_id_t part_id = ocf_metadata_get_partition_id(cache, line);
|
||||||
uint8_t evp_type = cache->conf_meta->eviction_policy_type;
|
uint8_t evp_type = cache->conf_meta->eviction_policy_type;
|
||||||
|
bool line_was_dirty;
|
||||||
|
|
||||||
if (metadata_set_dirty_sec_changed(cache, line, start_bit, end_bit)) {
|
if (metadata_set_dirty_sec_changed(cache, line, start_bit, end_bit,
|
||||||
/*
|
&line_was_dirty)) {
|
||||||
* If this is first dirty cline set dirty timestamp
|
|
||||||
*/
|
|
||||||
env_atomic64_cmpxchg(&req->core->runtime_meta->dirty_since,
|
|
||||||
0, env_get_tick_count());
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Update the number of dirty cached data for that
|
|
||||||
* core object
|
|
||||||
*/
|
|
||||||
env_atomic_inc(&req->core->runtime_meta->dirty_clines);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* increment dirty clines statistic for given cline
|
|
||||||
*/
|
|
||||||
env_atomic_inc(&req->core->runtime_meta->
|
|
||||||
part_counters[part_id].dirty_clines);
|
|
||||||
|
|
||||||
if (likely(evict_policy_ops[evp_type].dirty_cline))
|
|
||||||
evict_policy_ops[evp_type].dirty_cline(cache, part_id, line);
|
|
||||||
|
|
||||||
ocf_metadata_flush_mark(cache, req, map_idx, DIRTY, start_bit,
|
ocf_metadata_flush_mark(cache, req, map_idx, DIRTY, start_bit,
|
||||||
end_bit);
|
end_bit);
|
||||||
|
if (!line_was_dirty) {
|
||||||
|
/*
|
||||||
|
* If this is first dirty cline set dirty timestamp
|
||||||
|
*/
|
||||||
|
env_atomic64_cmpxchg(&req->core->runtime_meta->dirty_since,
|
||||||
|
0, env_get_tick_count());
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Update the number of dirty cached data for that
|
||||||
|
* core object
|
||||||
|
*/
|
||||||
|
env_atomic_inc(&req->core->runtime_meta->dirty_clines);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* increment dirty clines statistic for given cline
|
||||||
|
*/
|
||||||
|
env_atomic_inc(&req->core->runtime_meta->
|
||||||
|
part_counters[part_id].dirty_clines);
|
||||||
|
|
||||||
|
if (likely(evict_policy_ops[evp_type].dirty_cline))
|
||||||
|
evict_policy_ops[evp_type].dirty_cline(cache, part_id, line);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
ocf_cleaning_set_hot_cache_line(cache, line);
|
ocf_cleaning_set_hot_cache_line(cache, line);
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user