Check.cc revision 7055
110399Sstephan.diestelhorst@arm.com/*
210399Sstephan.diestelhorst@arm.com * Copyright (c) 1999-2008 Mark D. Hill and David A. Wood
310399Sstephan.diestelhorst@arm.com * Copyright (c) 2009 Advanced Micro Devices, Inc.
410399Sstephan.diestelhorst@arm.com * All rights reserved.
510399Sstephan.diestelhorst@arm.com *
610399Sstephan.diestelhorst@arm.com * Redistribution and use in source and binary forms, with or without
710399Sstephan.diestelhorst@arm.com * modification, are permitted provided that the following conditions are
810399Sstephan.diestelhorst@arm.com * met: redistributions of source code must retain the above copyright
910399Sstephan.diestelhorst@arm.com * notice, this list of conditions and the following disclaimer;
1010399Sstephan.diestelhorst@arm.com * redistributions in binary form must reproduce the above copyright
1110399Sstephan.diestelhorst@arm.com * notice, this list of conditions and the following disclaimer in the
1210399Sstephan.diestelhorst@arm.com * documentation and/or other materials provided with the distribution;
1310399Sstephan.diestelhorst@arm.com * neither the name of the copyright holders nor the names of its
1410399Sstephan.diestelhorst@arm.com * contributors may be used to endorse or promote products derived from
1510399Sstephan.diestelhorst@arm.com * this software without specific prior written permission.
1610399Sstephan.diestelhorst@arm.com *
1710399Sstephan.diestelhorst@arm.com * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
1810399Sstephan.diestelhorst@arm.com * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
1910399Sstephan.diestelhorst@arm.com * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
2010399Sstephan.diestelhorst@arm.com * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
2110399Sstephan.diestelhorst@arm.com * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
2210399Sstephan.diestelhorst@arm.com * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
2310399Sstephan.diestelhorst@arm.com * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
2410399Sstephan.diestelhorst@arm.com * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
2510399Sstephan.diestelhorst@arm.com * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
2610399Sstephan.diestelhorst@arm.com * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
2710399Sstephan.diestelhorst@arm.com * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
2810399Sstephan.diestelhorst@arm.com */
2910399Sstephan.diestelhorst@arm.com
3010399Sstephan.diestelhorst@arm.com#include "cpu/rubytest/Check.hh"
3110399Sstephan.diestelhorst@arm.com#include "mem/ruby/common/SubBlock.hh"
3210399Sstephan.diestelhorst@arm.com#include "mem/ruby/system/Sequencer.hh"
3310399Sstephan.diestelhorst@arm.com#include "mem/ruby/system/System.hh"
3410399Sstephan.diestelhorst@arm.com
3510399Sstephan.diestelhorst@arm.comtypedef RubyTester::SenderState SenderState;
3610399Sstephan.diestelhorst@arm.com
3710399Sstephan.diestelhorst@arm.comCheck::Check(const Address& address, const Address& pc,
3810399Sstephan.diestelhorst@arm.com             int _num_cpu_sequencers, RubyTester* _tester)
3910399Sstephan.diestelhorst@arm.com    : m_num_cpu_sequencers(_num_cpu_sequencers), m_tester_ptr(_tester)
4010399Sstephan.diestelhorst@arm.com{
4110399Sstephan.diestelhorst@arm.com    m_status = TesterStatus_Idle;
4210399Sstephan.diestelhorst@arm.com
4310399Sstephan.diestelhorst@arm.com    pickValue();
4410399Sstephan.diestelhorst@arm.com    pickInitiatingNode();
4510399Sstephan.diestelhorst@arm.com    changeAddress(address);
4610399Sstephan.diestelhorst@arm.com    m_pc = pc;
4710399Sstephan.diestelhorst@arm.com    m_access_mode = AccessModeType(random() % AccessModeType_NUM);
4810399Sstephan.diestelhorst@arm.com    m_store_count = 0;
4910399Sstephan.diestelhorst@arm.com}
5010399Sstephan.diestelhorst@arm.com
5110399Sstephan.diestelhorst@arm.comvoid
5210399Sstephan.diestelhorst@arm.comCheck::initiate()
5310399Sstephan.diestelhorst@arm.com{
5410399Sstephan.diestelhorst@arm.com    DPRINTF(RubyTest, "initiating\n");
5510399Sstephan.diestelhorst@arm.com    debugPrint();
5610399Sstephan.diestelhorst@arm.com
5710399Sstephan.diestelhorst@arm.com    // currently no protocols support prefetches
5810399Sstephan.diestelhorst@arm.com    if (false && (random() & 0xf) == 0) {
5910399Sstephan.diestelhorst@arm.com        initiatePrefetch(); // Prefetch from random processor
6010399Sstephan.diestelhorst@arm.com    }
6110399Sstephan.diestelhorst@arm.com
6210399Sstephan.diestelhorst@arm.com    if (m_status == TesterStatus_Idle) {
6310399Sstephan.diestelhorst@arm.com        initiateAction();
6410399Sstephan.diestelhorst@arm.com    } else if (m_status == TesterStatus_Ready) {
6510399Sstephan.diestelhorst@arm.com        initiateCheck();
6610399Sstephan.diestelhorst@arm.com    } else {
6710399Sstephan.diestelhorst@arm.com        // Pending - do nothing
6810399Sstephan.diestelhorst@arm.com        DPRINTF(RubyTest,
6910399Sstephan.diestelhorst@arm.com                "initiating action/check - failed: action/check is pending\n");
7010399Sstephan.diestelhorst@arm.com    }
7110399Sstephan.diestelhorst@arm.com}
7210399Sstephan.diestelhorst@arm.com
7310399Sstephan.diestelhorst@arm.comvoid
7410399Sstephan.diestelhorst@arm.comCheck::initiatePrefetch()
7510399Sstephan.diestelhorst@arm.com{
7610399Sstephan.diestelhorst@arm.com    DPRINTF(RubyTest, "initiating prefetch\n");
7710399Sstephan.diestelhorst@arm.com
7810399Sstephan.diestelhorst@arm.com    int index = random() % m_num_cpu_sequencers;
7910399Sstephan.diestelhorst@arm.com    RubyTester::CpuPort* port =
8010399Sstephan.diestelhorst@arm.com        safe_cast<RubyTester::CpuPort*>(m_tester_ptr->getCpuPort(index));
8110399Sstephan.diestelhorst@arm.com
8210399Sstephan.diestelhorst@arm.com    Request::Flags flags;
8310399Sstephan.diestelhorst@arm.com    flags.set(Request::PREFETCH);
8410399Sstephan.diestelhorst@arm.com
8510399Sstephan.diestelhorst@arm.com    // Prefetches are assumed to be 0 sized
8610399Sstephan.diestelhorst@arm.com    Request *req = new Request(m_address.getAddress(), 0, flags, curTick,
8710399Sstephan.diestelhorst@arm.com                               m_pc.getAddress());
8810399Sstephan.diestelhorst@arm.com
8910399Sstephan.diestelhorst@arm.com    Packet::Command cmd;
9010399Sstephan.diestelhorst@arm.com
9110399Sstephan.diestelhorst@arm.com    // 1 in 8 chance this will be an exclusive prefetch
9210399Sstephan.diestelhorst@arm.com    if ((random() & 0x7) != 0) {
9310399Sstephan.diestelhorst@arm.com        cmd = MemCmd::ReadReq;
9410399Sstephan.diestelhorst@arm.com
9510399Sstephan.diestelhorst@arm.com        // 50% chance that the request will be an instruction fetch
9610399Sstephan.diestelhorst@arm.com        if ((random() & 0x1) == 0) {
9710399Sstephan.diestelhorst@arm.com            flags.set(Request::INST_FETCH);
9810399Sstephan.diestelhorst@arm.com        }
9910399Sstephan.diestelhorst@arm.com    } else {
10010399Sstephan.diestelhorst@arm.com        cmd = MemCmd::WriteReq;
10110399Sstephan.diestelhorst@arm.com        flags.set(Request::PF_EXCLUSIVE);
10210399Sstephan.diestelhorst@arm.com    }
10310399Sstephan.diestelhorst@arm.com
10410399Sstephan.diestelhorst@arm.com    PacketPtr pkt = new Packet(req, cmd, port->idx);
10510399Sstephan.diestelhorst@arm.com
10610399Sstephan.diestelhorst@arm.com    // push the subblock onto the sender state.  The sequencer will
10710399Sstephan.diestelhorst@arm.com    // update the subblock on the return
10810399Sstephan.diestelhorst@arm.com    pkt->senderState =
10910399Sstephan.diestelhorst@arm.com        new SenderState(m_address, req->getSize(), pkt->senderState);
11010399Sstephan.diestelhorst@arm.com
11110399Sstephan.diestelhorst@arm.com    if (port->sendTiming(pkt)) {
11210399Sstephan.diestelhorst@arm.com        DPRINTF(RubyTest, "successfully initiated prefetch.\n");
11310399Sstephan.diestelhorst@arm.com    } else {
11410399Sstephan.diestelhorst@arm.com        // If the packet did not issue, must delete
11510399Sstephan.diestelhorst@arm.com        SenderState* senderState =  safe_cast<SenderState*>(pkt->senderState);
11610399Sstephan.diestelhorst@arm.com        pkt->senderState = senderState->saved;
11710399Sstephan.diestelhorst@arm.com        delete senderState;
11810399Sstephan.diestelhorst@arm.com        delete pkt->req;
11910399Sstephan.diestelhorst@arm.com        delete pkt;
12010399Sstephan.diestelhorst@arm.com
12110399Sstephan.diestelhorst@arm.com        DPRINTF(RubyTest,
12210399Sstephan.diestelhorst@arm.com                "prefetch initiation failed because Port was busy.\n");
12310399Sstephan.diestelhorst@arm.com    }
12410399Sstephan.diestelhorst@arm.com}
12510399Sstephan.diestelhorst@arm.com
12610399Sstephan.diestelhorst@arm.comvoid
12710399Sstephan.diestelhorst@arm.comCheck::initiateAction()
12810399Sstephan.diestelhorst@arm.com{
12910399Sstephan.diestelhorst@arm.com    DPRINTF(RubyTest, "initiating Action\n");
13010399Sstephan.diestelhorst@arm.com    assert(m_status == TesterStatus_Idle);
13110399Sstephan.diestelhorst@arm.com
13210399Sstephan.diestelhorst@arm.com    int index = random() % m_num_cpu_sequencers;
13310399Sstephan.diestelhorst@arm.com    RubyTester::CpuPort* port =
13410399Sstephan.diestelhorst@arm.com        safe_cast<RubyTester::CpuPort*>(m_tester_ptr->getCpuPort(index));
13510399Sstephan.diestelhorst@arm.com
13610399Sstephan.diestelhorst@arm.com    Request::Flags flags;
13710399Sstephan.diestelhorst@arm.com
13810399Sstephan.diestelhorst@arm.com    // Create the particular address for the next byte to be written
13910399Sstephan.diestelhorst@arm.com    Address writeAddr(m_address.getAddress() + m_store_count);
14010399Sstephan.diestelhorst@arm.com
14110399Sstephan.diestelhorst@arm.com    // Stores are assumed to be 1 byte-sized
14210399Sstephan.diestelhorst@arm.com    Request *req = new Request(writeAddr.getAddress(), 1, flags, curTick,
14310399Sstephan.diestelhorst@arm.com                               m_pc.getAddress());
14410399Sstephan.diestelhorst@arm.com
14510399Sstephan.diestelhorst@arm.com    Packet::Command cmd;
14610399Sstephan.diestelhorst@arm.com
14710399Sstephan.diestelhorst@arm.com    // 1 out of 8 chance, issue an atomic rather than a write
14810399Sstephan.diestelhorst@arm.com    // if ((random() & 0x7) == 0) {
14910399Sstephan.diestelhorst@arm.com    //     cmd = MemCmd::SwapReq;
15010399Sstephan.diestelhorst@arm.com    // } else {
15110399Sstephan.diestelhorst@arm.com    cmd = MemCmd::WriteReq;
15210399Sstephan.diestelhorst@arm.com    // }
15310399Sstephan.diestelhorst@arm.com
15410399Sstephan.diestelhorst@arm.com    PacketPtr pkt = new Packet(req, cmd, port->idx);
15510399Sstephan.diestelhorst@arm.com    uint8_t* writeData = new uint8_t;
15610399Sstephan.diestelhorst@arm.com    *writeData = m_value + m_store_count;
15710399Sstephan.diestelhorst@arm.com    pkt->dataDynamic(writeData);
15810399Sstephan.diestelhorst@arm.com
15910399Sstephan.diestelhorst@arm.com    DPRINTF(RubyTest, "data 0x%x check 0x%x\n",
16010399Sstephan.diestelhorst@arm.com            *(pkt->getPtr<uint8_t>()), *writeData);
16110399Sstephan.diestelhorst@arm.com
16210399Sstephan.diestelhorst@arm.com    // push the subblock onto the sender state.  The sequencer will
16310399Sstephan.diestelhorst@arm.com    // update the subblock on the return
16410399Sstephan.diestelhorst@arm.com    pkt->senderState =
16510399Sstephan.diestelhorst@arm.com        new SenderState(writeAddr, req->getSize(), pkt->senderState);
16610399Sstephan.diestelhorst@arm.com
16710399Sstephan.diestelhorst@arm.com    if (port->sendTiming(pkt)) {
16810399Sstephan.diestelhorst@arm.com        DPRINTF(RubyTest, "initiating action - successful\n");
16910399Sstephan.diestelhorst@arm.com        DPRINTF(RubyTest, "status before action update: %s\n",
17010399Sstephan.diestelhorst@arm.com                (TesterStatus_to_string(m_status)).c_str());
17110399Sstephan.diestelhorst@arm.com        m_status = TesterStatus_Action_Pending;
17210399Sstephan.diestelhorst@arm.com    } else {
17310399Sstephan.diestelhorst@arm.com        // If the packet did not issue, must delete
17410399Sstephan.diestelhorst@arm.com        // Note: No need to delete the data, the packet destructor
17510399Sstephan.diestelhorst@arm.com        // will delete it
17610399Sstephan.diestelhorst@arm.com        SenderState* senderState = safe_cast<SenderState*>(pkt->senderState);
17710399Sstephan.diestelhorst@arm.com        pkt->senderState = senderState->saved;
17810399Sstephan.diestelhorst@arm.com        delete senderState;
17910399Sstephan.diestelhorst@arm.com        delete pkt->req;
18010399Sstephan.diestelhorst@arm.com        delete pkt;
18110399Sstephan.diestelhorst@arm.com
18210399Sstephan.diestelhorst@arm.com        DPRINTF(RubyTest, "failed to initiate action - sequencer not ready\n");
18310399Sstephan.diestelhorst@arm.com    }
18410399Sstephan.diestelhorst@arm.com
18510399Sstephan.diestelhorst@arm.com    DPRINTF(RubyTest, "status after action update: %s\n",
18610399Sstephan.diestelhorst@arm.com            (TesterStatus_to_string(m_status)).c_str());
18710399Sstephan.diestelhorst@arm.com}
18810399Sstephan.diestelhorst@arm.com
18910399Sstephan.diestelhorst@arm.comvoid
19010399Sstephan.diestelhorst@arm.comCheck::initiateCheck()
19110399Sstephan.diestelhorst@arm.com{
19210399Sstephan.diestelhorst@arm.com    DPRINTF(RubyTest, "Initiating Check\n");
19310399Sstephan.diestelhorst@arm.com    assert(m_status == TesterStatus_Ready);
19410399Sstephan.diestelhorst@arm.com
19510399Sstephan.diestelhorst@arm.com    int index = random() % m_num_cpu_sequencers;
19610399Sstephan.diestelhorst@arm.com    RubyTester::CpuPort* port =
19710399Sstephan.diestelhorst@arm.com        safe_cast<RubyTester::CpuPort*>(m_tester_ptr->getCpuPort(index));
19810399Sstephan.diestelhorst@arm.com
19910399Sstephan.diestelhorst@arm.com    Request::Flags flags;
20010399Sstephan.diestelhorst@arm.com
20110399Sstephan.diestelhorst@arm.com    // Checks are sized depending on the number of bytes written
20210399Sstephan.diestelhorst@arm.com    Request *req = new Request(m_address.getAddress(), CHECK_SIZE, flags,
20310399Sstephan.diestelhorst@arm.com                               curTick, m_pc.getAddress());
20410399Sstephan.diestelhorst@arm.com
20510399Sstephan.diestelhorst@arm.com    // 50% chance that the request will be an instruction fetch
20610399Sstephan.diestelhorst@arm.com    if ((random() & 0x1) == 0) {
20710399Sstephan.diestelhorst@arm.com        flags.set(Request::INST_FETCH);
20810399Sstephan.diestelhorst@arm.com    }
20910399Sstephan.diestelhorst@arm.com
21010399Sstephan.diestelhorst@arm.com    PacketPtr pkt = new Packet(req, MemCmd::ReadReq, port->idx);
21110399Sstephan.diestelhorst@arm.com    uint8_t* dataArray = new uint8_t[CHECK_SIZE];
21210399Sstephan.diestelhorst@arm.com    pkt->dataDynamicArray(dataArray);
21310399Sstephan.diestelhorst@arm.com
21410399Sstephan.diestelhorst@arm.com    // push the subblock onto the sender state.  The sequencer will
21510399Sstephan.diestelhorst@arm.com    // update the subblock on the return
21610399Sstephan.diestelhorst@arm.com    pkt->senderState =
21710399Sstephan.diestelhorst@arm.com        new SenderState(m_address, req->getSize(), pkt->senderState);
21810399Sstephan.diestelhorst@arm.com
21910399Sstephan.diestelhorst@arm.com    if (port->sendTiming(pkt)) {
22010399Sstephan.diestelhorst@arm.com        DPRINTF(RubyTest, "initiating check - successful\n");
22110399Sstephan.diestelhorst@arm.com        DPRINTF(RubyTest, "status before check update: %s\n",
22210399Sstephan.diestelhorst@arm.com                TesterStatus_to_string(m_status).c_str());
22310399Sstephan.diestelhorst@arm.com        m_status = TesterStatus_Check_Pending;
22410399Sstephan.diestelhorst@arm.com    } else {
22510399Sstephan.diestelhorst@arm.com        // If the packet did not issue, must delete
22610399Sstephan.diestelhorst@arm.com        // Note: No need to delete the data, the packet destructor
22710399Sstephan.diestelhorst@arm.com        // will delete it
22810399Sstephan.diestelhorst@arm.com        SenderState* senderState = safe_cast<SenderState*>(pkt->senderState);
22910399Sstephan.diestelhorst@arm.com        pkt->senderState = senderState->saved;
23010399Sstephan.diestelhorst@arm.com        delete senderState;
23110399Sstephan.diestelhorst@arm.com        delete pkt->req;
23210399Sstephan.diestelhorst@arm.com        delete pkt;
23310399Sstephan.diestelhorst@arm.com
23410399Sstephan.diestelhorst@arm.com        DPRINTF(RubyTest, "failed to initiate check - cpu port not ready\n");
23510399Sstephan.diestelhorst@arm.com    }
23610399Sstephan.diestelhorst@arm.com
23710399Sstephan.diestelhorst@arm.com    DPRINTF(RubyTest, "status after check update: %s\n",
23810399Sstephan.diestelhorst@arm.com            TesterStatus_to_string(m_status).c_str());
23910399Sstephan.diestelhorst@arm.com}
24010399Sstephan.diestelhorst@arm.com
24110399Sstephan.diestelhorst@arm.comvoid
24210399Sstephan.diestelhorst@arm.comCheck::performCallback(NodeID proc, SubBlock* data)
24310399Sstephan.diestelhorst@arm.com{
24410399Sstephan.diestelhorst@arm.com    Address address = data->getAddress();
24510399Sstephan.diestelhorst@arm.com
24610399Sstephan.diestelhorst@arm.com    // This isn't exactly right since we now have multi-byte checks
24710399Sstephan.diestelhorst@arm.com    //  assert(getAddress() == address);
24810399Sstephan.diestelhorst@arm.com
24910399Sstephan.diestelhorst@arm.com    assert(getAddress().getLineAddress() == address.getLineAddress());
25010399Sstephan.diestelhorst@arm.com    assert(data != NULL);
25110399Sstephan.diestelhorst@arm.com
25210399Sstephan.diestelhorst@arm.com    DPRINTF(RubyTest, "RubyTester Callback\n");
25310399Sstephan.diestelhorst@arm.com    debugPrint();
25410399Sstephan.diestelhorst@arm.com
25510399Sstephan.diestelhorst@arm.com    if (m_status == TesterStatus_Action_Pending) {
25610399Sstephan.diestelhorst@arm.com        DPRINTF(RubyTest, "Action callback write value: %d, currently %d\n",
25710399Sstephan.diestelhorst@arm.com                (m_value + m_store_count), data->getByte(0));
25810399Sstephan.diestelhorst@arm.com        // Perform store one byte at a time
25910399Sstephan.diestelhorst@arm.com        data->setByte(0, (m_value + m_store_count));
26010399Sstephan.diestelhorst@arm.com        m_store_count++;
26110399Sstephan.diestelhorst@arm.com        if (m_store_count == CHECK_SIZE) {
26210399Sstephan.diestelhorst@arm.com            m_status = TesterStatus_Ready;
26310399Sstephan.diestelhorst@arm.com        } else {
26410399Sstephan.diestelhorst@arm.com            m_status = TesterStatus_Idle;
26510399Sstephan.diestelhorst@arm.com        }
26610399Sstephan.diestelhorst@arm.com        DPRINTF(RubyTest, "Action callback return data now %d\n",
26710399Sstephan.diestelhorst@arm.com                data->getByte(0));
26810399Sstephan.diestelhorst@arm.com    } else if (m_status == TesterStatus_Check_Pending) {
26910399Sstephan.diestelhorst@arm.com        DPRINTF(RubyTest, "Check callback\n");
27010399Sstephan.diestelhorst@arm.com        // Perform load/check
27110399Sstephan.diestelhorst@arm.com        for (int byte_number=0; byte_number<CHECK_SIZE; byte_number++) {
27210399Sstephan.diestelhorst@arm.com            if (uint8(m_value + byte_number) != data->getByte(byte_number)) {
27310399Sstephan.diestelhorst@arm.com                WARN_EXPR(proc);
27410399Sstephan.diestelhorst@arm.com                WARN_EXPR(address);
275                WARN_EXPR(data);
276                WARN_EXPR(byte_number);
277                WARN_EXPR((int)m_value + byte_number);
278                WARN_EXPR((int)data->getByte(byte_number));
279                WARN_EXPR(*this);
280                WARN_EXPR(g_eventQueue_ptr->getTime());
281                ERROR_MSG("Action/check failure");
282            }
283        }
284        DPRINTF(RubyTest, "Action/check success\n");
285        debugPrint();
286
287        // successful check complete, increment complete
288        m_tester_ptr->incrementCheckCompletions();
289
290        m_status = TesterStatus_Idle;
291        pickValue();
292
293    } else {
294        WARN_EXPR(*this);
295        WARN_EXPR(proc);
296        WARN_EXPR(data);
297        WARN_EXPR(m_status);
298        WARN_EXPR(g_eventQueue_ptr->getTime());
299        ERROR_MSG("Unexpected TesterStatus");
300    }
301
302    DPRINTF(RubyTest, "proc: %d, Address: 0x%x\n", proc,
303            getAddress().getLineAddress());
304    DPRINTF(RubyTest, "Callback done\n");
305    debugPrint();
306}
307
308void
309Check::changeAddress(const Address& address)
310{
311    assert(m_status == TesterStatus_Idle || m_status == TesterStatus_Ready);
312    m_status = TesterStatus_Idle;
313    m_address = address;
314    m_store_count = 0;
315}
316
317void
318Check::pickValue()
319{
320    assert(m_status == TesterStatus_Idle);
321    m_status = TesterStatus_Idle;
322    m_value = random() & 0xff; // One byte
323    m_store_count = 0;
324}
325
326void
327Check::pickInitiatingNode()
328{
329    assert(m_status == TesterStatus_Idle || m_status == TesterStatus_Ready);
330    m_status = TesterStatus_Idle;
331    m_initiatingNode = (random() % m_num_cpu_sequencers);
332    DPRINTF(RubyTest, "picked initiating node %d\n", m_initiatingNode);
333    m_store_count = 0;
334}
335
336void
337Check::print(std::ostream& out) const
338{
339    out << "["
340        << m_address << ", value: "
341        << (int)m_value << ", status: "
342        << m_status << ", initiating node: "
343        << m_initiatingNode << ", store_count: "
344        << m_store_count
345        << "]" << std::flush;
346}
347
348void
349Check::debugPrint()
350{
351    DPRINTF(RubyTest,
352        "[%#x, value: %d, status: %s, initiating node: %d, store_count: %d]\n",
353        m_address.getAddress(), (int)m_value,
354        TesterStatus_to_string(m_status).c_str(),
355        m_initiatingNode, m_store_count);
356}
357