OpenCores
URL https://opencores.org/ocsvn/riscv_vhdl/riscv_vhdl/trunk

Subversion Repositories riscv_vhdl

[/] [riscv_vhdl/] [trunk/] [debugger/] [src/] [libdbg64g/] [services/] [bus/] [bus.cpp] - Blame information for rev 2

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 2 sergeykhbr
/**
2
 * @file
3
 * @copyright  Copyright 2016 GNSS Sensor Ltd. All right reserved.
4
 * @author     Sergey Khabarov - sergeykhbr@gmail.com
5
 * @brief      System Bus class declaration (AMBA or whatever).
6
 */
7
 
8
#include "api_core.h"
9
#include "bus.h"
10
#include "coreservices/icpuriscv.h"
11
 
12
namespace debugger {
13
 
14
/** Class registration in the Core */
15
REGISTER_CLASS(Bus)
16
 
17
Bus::Bus(const char *name)
18
    : IService(name) {
19
    registerInterface(static_cast<IBus *>(this));
20
    registerAttribute("MapList", &listMap_);
21
 
22
    listMap_.make_list(0);
23
    imap_.make_list(0);
24
    RISCV_mutex_init(&mutexBAccess_);
25
    RISCV_mutex_init(&mutexNBAccess_);
26
    memset(info_, 0, sizeof(info_));
27
}
28
 
29
Bus::~Bus() {
30
    RISCV_mutex_destroy(&mutexBAccess_);
31
    RISCV_mutex_destroy(&mutexNBAccess_);
32
}
33
 
34
void Bus::postinitService() {
35
    IMemoryOperation *imem;
36
    for (unsigned i = 0; i < listMap_.size(); i++) {
37
        imem = static_cast<IMemoryOperation *>(RISCV_get_service_iface(
38
                listMap_[i].to_string(), IFACE_MEMORY_OPERATION));
39
        if (imem == 0) {
40
            RISCV_error("Can't find slave device %s", listMap_[i].to_string());
41
            continue;
42
        }
43
        map(imem);
44
    }
45
 
46
    AttributeType clks;
47
    RISCV_get_clock_services(&clks);
48
    if (clks.size()) {
49
        iclk0_ = static_cast<IClock *>(clks[0u].to_iface());
50
    } else {
51
        RISCV_error("CPUs not found", NULL);
52
    }
53
}
54
 
55
void Bus::map(IMemoryOperation *imemop) {
56
    AttributeType t1(imemop);
57
    imap_.add_to_list(&t1);
58
}
59
 
60
ETransStatus Bus::b_transport(Axi4TransactionType *trans) {
61
    IMemoryOperation *imem;
62
    bool unmapped = true;
63
    ETransStatus ret = TRANS_OK;
64
 
65
    RISCV_mutex_lock(&mutexBAccess_);
66
 
67
    for (unsigned i = 0; i < imap_.size(); i++) {
68
        imem = static_cast<IMemoryOperation *>(imap_[i].to_iface());
69
        if (imem->getBaseAddress() <= trans->addr
70
            && trans->addr < (imem->getBaseAddress() + imem->getLength())) {
71
 
72
            imem->b_transport(trans);
73
            unmapped = false;
74
            break;
75
            /// @todo Check memory overlapping
76
        }
77
    }
78
 
79
    if (unmapped) {
80
        RISCV_error("[%" RV_PRI64 "d] Read from unmapped address "
81
                    "%08" RV_PRI64 "x", iclk0_->getStepCounter(), trans->addr);
82
        memset(trans->rpayload.b8, 0xFF, trans->xsize);
83
        ret = TRANS_ERROR;
84
    } else {
85
        RISCV_debug("[%08" RV_PRI64 "x] => [%08x %08x]",
86
            trans->addr,
87
            trans->rpayload.b32[1], trans->rpayload.b32[0]);
88
    }
89
 
90
    // Update Bus utilization counters:
91
    if (trans->action == MemAction_Read) {
92
        info_[trans->source_idx].r_cnt++;
93
    } else if (trans->action == MemAction_Write) {
94
        info_[trans->source_idx].w_cnt++;
95
    }
96
    RISCV_mutex_unlock(&mutexBAccess_);
97
    return ret;
98
}
99
 
100
ETransStatus Bus::nb_transport(Axi4TransactionType *trans,
101
                               IAxi4NbResponse *cb) {
102
    IMemoryOperation *imem;
103
    bool unmapped = true;
104
    ETransStatus ret = TRANS_OK;
105
 
106
    RISCV_mutex_lock(&mutexNBAccess_);
107
 
108
    for (unsigned i = 0; i < imap_.size(); i++) {
109
        imem = static_cast<IMemoryOperation *>(imap_[i].to_iface());
110
        if (imem->getBaseAddress() <= trans->addr
111
            && trans->addr < (imem->getBaseAddress() + imem->getLength())) {
112
 
113
            imem->nb_transport(trans, cb);
114
            unmapped = false;
115
            break;
116
        }
117
    }
118
 
119
    if (unmapped) {
120
        RISCV_error("[%" RV_PRI64 "d] Non-blocking request to unmapped address "
121
                    "%08" RV_PRI64 "x", iclk0_->getStepCounter(), trans->addr);
122
        memset(trans->rpayload.b8, 0xFF, trans->xsize);
123
        trans->response = MemResp_Error;
124
        cb->nb_response(trans);
125
        ret = TRANS_ERROR;
126
    } else {
127
        RISCV_debug("Non-blocking request to [%08" RV_PRI64 "x]",
128
                    trans->addr);
129
    }
130
 
131
    // Update Bus utilization counters:
132
    if (trans->action == MemAction_Read) {
133
        info_[trans->source_idx].r_cnt++;
134
    } else if (trans->action == MemAction_Write) {
135
        info_[trans->source_idx].w_cnt++;
136
    }
137
    RISCV_mutex_unlock(&mutexNBAccess_);
138
    return ret;
139
}
140
 
141
BusUtilType *Bus::bus_utilization() {
142
    return info_;
143
}
144
 
145
}  // namespace debugger

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.