i40e_queues.cc 3.98 KB
Newer Older
Antoine Kaufmann's avatar
Antoine Kaufmann committed
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
#include <stdlib.h>
#include <string.h>
#include <cassert>
#include <iostream>

#include "i40e_bm.h"

#include "i40e_base_wrapper.h"

using namespace i40e;

extern nicbm::Runner *runner;

queue_base::queue_base(uint32_t &reg_head_, uint32_t &reg_tail_)
    : base(0), len(0), fetch_head(0), reg_head(reg_head_), reg_tail(reg_tail_),
    enabled(false), desc_len(0)
{
}

void queue_base::trigger_fetch()
{
22
    if (!enabled || fetch_head == reg_tail)
Antoine Kaufmann's avatar
Antoine Kaufmann committed
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
        return;


    dma_fetch *dma = new dma_fetch(*this, desc_len);
    dma->write = false;
    dma->dma_addr = base + fetch_head * desc_len;
    dma->index = fetch_head;

    std::cerr << "fetching " << (reg_tail - fetch_head) % len <<
        " descriptors from " << dma->dma_addr << std::endl;

    std::cerr << "dma = " << dma << std::endl;
    runner->issue_dma(*dma);
    fetch_head = (fetch_head + 1) % len;
}

39
40
41
42
43
44
45
46
47
48
49
50
51
52
void queue_base::data_fetch(const void *desc, uint32_t idx, uint64_t addr,
        size_t len)
{
    dma_data_fetch *dma = new dma_data_fetch(*this, len, desc, desc_len);
    dma->write = false;
    dma->dma_addr = addr;
    dma->index = idx;

    std::cerr << "fetching data idx=" << idx << " addr=" << addr << " len=" <<
        len << std::endl;
    std::cerr << "dma = " << dma << std::endl;
    runner->issue_dma(*dma);
}

Antoine Kaufmann's avatar
Antoine Kaufmann committed
53
54
55
56
57
58
59
60
void queue_base::reg_updated()
{
    if (!enabled)
        return;

    trigger_fetch();
}

61
62
63
64
65
bool queue_base::is_enabled()
{
    return enabled;
}

Antoine Kaufmann's avatar
Antoine Kaufmann committed
66
67
68
69
70
71
72
73
74
75
76
void queue_base::desc_writeback(const void *desc, uint32_t idx)
{
    dma_wb *dma = new dma_wb(*this, desc_len);
    dma->write = true;
    dma->dma_addr = base + idx * desc_len;
    dma->index = idx;
    memcpy(dma->data, desc, desc_len);

    runner->issue_dma(*dma);
}

77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
void queue_base::desc_writeback_indirect(const void *desc, uint32_t idx,
        uint64_t data_addr, const void *data, size_t data_len)
{
    // descriptor dma
    dma_wb *desc_dma = new dma_wb(*this, desc_len);
    desc_dma->write = true;
    desc_dma->dma_addr = base + idx * desc_len;
    desc_dma->index = idx;
    memcpy(desc_dma->data, desc, desc_len);
    // purposefully not issued yet, data dma will issue once ready

    // data dma
    dma_data_wb *data_dma = new dma_data_wb(*this, data_len, *desc_dma);
    data_dma->write = true;
    data_dma->dma_addr = data_addr;
    data_dma->index = idx;
    memcpy(data_dma->data, data, data_len);

    runner->issue_dma(*data_dma);
}

Antoine Kaufmann's avatar
Antoine Kaufmann committed
98
99
void queue_base::desc_written_back(uint32_t idx)
{
100
101
102
    if (!enabled)
        return;

Antoine Kaufmann's avatar
Antoine Kaufmann committed
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
    std::cerr << "descriptor " << idx << " written back" << std::endl;
    reg_head = (idx + 1) % len;
}

queue_base::dma_fetch::dma_fetch(queue_base &queue_, size_t len_)
    : queue(queue_)
{
    data = new char[len_];
    len = len_;
}

queue_base::dma_fetch::~dma_fetch()
{
    delete[] ((char *) data);
}

void queue_base::dma_fetch::done()
{
    queue.desc_fetched(data, index);
    delete this;
}

125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
queue_base::dma_data_fetch::dma_data_fetch(queue_base &queue_, size_t len_,
        const void *desc_, size_t desc_len)
    :queue(queue_)
{
    uint8_t *buf = new uint8_t[desc_len + len_];

    desc = buf;
    memcpy(desc, desc_, desc_len);

    data = buf + desc_len;
    len = len_;
}

queue_base::dma_data_fetch::~dma_data_fetch()
{
    delete[] ((uint8_t *) desc);
}

void queue_base::dma_data_fetch::done()
{
    queue.data_fetched(desc, index, data);
    delete this;
}
Antoine Kaufmann's avatar
Antoine Kaufmann committed
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168

queue_base::dma_wb::dma_wb(queue_base &queue_, size_t len_)
    : queue(queue_)
{
    data = new char[len_];
    len = len_;
}

queue_base::dma_wb::~dma_wb()
{
    delete[] ((char *) data);
}

void queue_base::dma_wb::done()
{
    queue.desc_written_back(index);
    queue.trigger_fetch();
    delete this;
}


169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
queue_base::dma_data_wb::dma_data_wb(queue_base &queue_, size_t len_,
        dma_wb &desc_dma_)
    : queue(queue_), desc_dma(desc_dma_)
{
    data = new char[len_];
    len = len_;
}

queue_base::dma_data_wb::~dma_data_wb()
{
    delete[] ((char *) data);
}

void queue_base::dma_data_wb::done()
{
    // now we can issue descriptor dma
    runner->issue_dma(desc_dma);
    delete this;
}