Example #1
0
void
Cache :: line_writer_to_sharer(Line *line, size_t &latency, bool children_only)
{
    // make this cache (and child caches)
    // only sharers of the line (downgrade from a writer)
    NVLOG1("%s\tline_writer_to_sharer 0x%lx +%ld cycles\n", this->_name.c_str(), line->addr, _hit_latency);
    latency += _hit_latency;
    this->stats.writebacks_inc();
    for (size_t child_i = 0; child_i<_children.size(); child_i++) {
        if (!bit(line->sharers, child_i)) continue; // a child is not a sharer, so continue
        Cache *child = dynamic_cast<Cache *>(_children[child_i]); assert(child!=NULL);
        for (Addr line_addr_iter=line->addr; line_addr_iter<line->addr+get_line_size(); line_addr_iter += child->get_line_size())
        {
            if (line_addr_iter!=line->addr) {
                // also measure the latency for other line segments
                NVLOG1("%s\tline_writer_to_sharer 0x%lx +%ld cycles\n", this->_name.c_str(), line_addr_iter, _hit_latency);
                latency += _hit_latency;  // response from child to parent
                this->stats.writebacks_inc();
            }
            Line *child_line = child->addr2line_internal(line_addr_iter);
            if (!child_line) continue;
            child->line_writer_to_sharer(child_line, latency);
        }
    }
    if (!children_only) {
        this->line_data_writeback(line);
        line->state &= ~(LINE_MOD | LINE_EXC);
        line->state |= LINE_SHR;
    }
    NVLOG1("%s\t0x%lx\t new state %s sharers %lx\n",  _name.c_str(),  line->addr,  state2str(line->state).c_str(), line->sharers );
}