aboutsummaryrefslogtreecommitdiff
path: root/include/ethosu_device.h
blob: 91aa8779b1ad5542545f909e690eb11bc4ddefa5 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
/*
 * Copyright (c) 2019-2020 Arm Limited. All rights reserved.
 *
 * SPDX-License-Identifier: Apache-2.0
 *
 * Licensed under the Apache License, Version 2.0 (the License); you may
 * not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an AS IS BASIS, WITHOUT
 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#ifndef ETHOSU_DEVICE_H
#define ETHOSU_DEVICE_H

/******************************************************************************
 * Includes
 ******************************************************************************/

#include "pmu_ethosu.h"

#include <stdbool.h>
#include <stdint.h>

#ifdef __cplusplus
extern "C" {
#endif

/******************************************************************************
 * Defines
 ******************************************************************************/

#define ETHOSU_DRIVER_VERSION_MAJOR 0  ///< Driver major version
#define ETHOSU_DRIVER_VERSION_MINOR 16 ///< Driver minor version
#define ETHOSU_DRIVER_VERSION_PATCH 0  ///< Driver patch version
#define ETHOSU_DRIVER_BASEP_INDEXES 8  ///< Number of base pointer indexes

/******************************************************************************
 * Types
 ******************************************************************************/

enum ethosu_error_codes
{
    ETHOSU_SUCCESS         = 0,  ///< Success
    ETHOSU_GENERIC_FAILURE = -1, ///< Generic failure
    ETHOSU_INVALID_PARAM   = -2  ///< Invalid parameter
};

struct ethosu_device
{
    volatile uint32_t *base_address;
    uint32_t reset;
    uint32_t pmcr;
    uint32_t pmccntr[2];
    uint32_t pmcnten;
    uint32_t pmint;
    uint32_t pmccntr_cfg;
    uint32_t pmu_evcntr[ETHOSU_PMU_NCOUNTERS];
    uint32_t pmu_evtypr[ETHOSU_PMU_NCOUNTERS];
};

struct ethosu_id
{
    uint32_t version_status; ///< Version status
    uint32_t version_minor;  ///< Version minor
    uint32_t version_major;  ///< Version major
    uint32_t product_major;  ///< Product major
    uint32_t arch_patch_rev; ///< Architecture version patch
    uint32_t arch_minor_rev; ///< Architecture version minor
    uint32_t arch_major_rev; ///< Architecture version major
};

struct ethosu_config
{
    struct
    {
        uint32_t macs_per_cc;        ///< MACs per clock cycle
        uint32_t cmd_stream_version; ///< NPU command stream version
        uint32_t shram_size;         ///< SHRAM size
    };
};

/**
 * Memory type parameter for set_regioncfg_reg:
 *   Counter{0,1}: Outstanding transactions for
 *   AXI port 0 for memory type/region a=0,b=1
 *   Counter{2,3}: Outstanding transactions for
 *   AXI port 1 for memory type/region a=2,b=3
 */
enum ethosu_memory_type
{
    ETHOSU_AXI0_OUTSTANDING_COUNTER0 = 0, ///< NPU axi0_outstanding_counter0
    ETHOSU_AXI0_OUTSTANDING_COUNTER1 = 1, ///< NPU axi0_outstanding_counter1
    ETHOSU_AXI1_OUTSTANDING_COUNTER2 = 2, ///< NPU axi1_outstanding_counter2
    ETHOSU_AXI1_OUTSTANDING_COUNTER3 = 3  ///< NPU axi1_outstanding_counter3
};

enum ethosu_axi_limit_beats
{
    ETHOSU_AXI_LIMIT_64_BYTES  = 0, ///< NPU AXI limit 64 byte burst split alignment.
    ETHOSU_AXI_LIMIT_128_BYTES = 1, ///< NPU AXI limit 128 byte burst split alignment.
    ETHOSU_AXI_LIMIT_256_BYTES = 2  ///< NPU AXI limit 256 byte burst split alignment.
};

enum ethosu_axi_limit_mem_type
{
    ETHOSU_MEM_TYPE_DEVICE_NON_BUFFERABLE                 = 0,
    ETHOSU_MEM_TYPE_DEVICE_BUFFERABLE                     = 1,
    ETHOSU_MEM_TYPE_NORMAL_NON_CACHEABLE_NON_BUFFERABLE   = 2,
    ETHOSU_MEM_TYPE_NORMAL_NON_CACHEABLE_BUFFERABLE       = 3,
    ETHOSU_MEM_TYPE_WRITE_THROUGH_NO_ALLOCATE             = 4,
    ETHOSU_MEM_TYPE_WRITE_THROUGH_READ_ALLOCATE           = 5,
    ETHOSU_MEM_TYPE_WRITE_THROUGH_WRITE_ALLOCATE          = 6,
    ETHOSU_MEM_TYPE_WRITE_THROUGH_READ_AND_WRITE_ALLOCATE = 7,
    ETHOSU_MEM_TYPE_WRITE_BACK_NO_ALLOCATE                = 8,
    ETHOSU_MEM_TYPE_WRITE_BACK_READ_ALLOCATE              = 9,
    ETHOSU_MEM_TYPE_WRITE_BACK_WRITE_ALLOCATE             = 10,
    ETHOSU_MEM_TYPE_WRITE_BACK_READ_AND_WRITE_ALLOCATE    = 11
};

enum ethosu_clock_q_request
{
    ETHOSU_CLOCK_Q_DISABLE = 0, ///< Disble NPU signal ready for clock off.
    ETHOSU_CLOCK_Q_ENABLE  = 1  ///< Enable NPU signal ready for clock off when stop+idle state reached.
};

enum ethosu_power_q_request
{
    ETHOSU_POWER_Q_DISABLE = 0, ///< Disble NPU signal ready for power off.
    ETHOSU_POWER_Q_ENABLE  = 1  ///< Enable NPU signal ready for power off when stop+idle state reached.
};

/******************************************************************************
 * Prototypes
 ******************************************************************************/

/**
 * Initialize the device.
 */
enum ethosu_error_codes ethosu_dev_init(struct ethosu_device *dev, const void *base_address);

/**
 * Get device id.
 */
enum ethosu_error_codes ethosu_get_id(struct ethosu_device *dev, struct ethosu_id *id);

/**
 * Get device configuration.
 */
enum ethosu_error_codes ethosu_get_config(struct ethosu_device *dev, struct ethosu_config *config);

/**
 * Execute a given command stream on NPU.
 * \param[in] cmd_stream_ptr   Pointer to the command stream
 * \param[in] cms_length       Command stream length
 * \param[in] base_addr        Pointer to array of base addresses
 *                             - 0: weight tensor
 *                             - 1: scratch tensor
 *                             - All input tensors
 *                             - All output tensors
 * \param[in] num_base_addr    Number of base addresses.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_run_command_stream(struct ethosu_device *dev,
                                                  const uint8_t *cmd_stream_ptr,
                                                  uint32_t cms_length,
                                                  const uint64_t *base_addr,
                                                  int num_base_addr);

/**
 * Check if IRQ is raised.
 * \param[out] irq_status      Pointer to IRQ status
 *                             - 0 IRQ not raised
 *                             - 1 IRQ raised
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_is_irq_raised(struct ethosu_device *dev, uint8_t *irq_status);

/**
 * Clear IRQ status.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_clear_irq_status(struct ethosu_device *dev);

/**
 * Get the 16 bit status mask.
 * \param[out] irq_status_mask     Pointer to the status mask.
 *                                 The lower 16 bits of status reg are returned.
 *                                 bit0: state
 *                                 bit1: irq_raised
 *                                 bit2: bus_status
 *                                 bit3: reset_status
 *                                 bit4: cmd_parse_error
 *                                 bit5: cmd_end_reached
 *                                 bit6: pmu_irq_raised
 *                                 bit7-15: reserved
 * \return                         \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_get_status_mask(struct ethosu_device *dev, uint16_t *status_mask);

/**
 * Get the 16 bit IRQ history mask.
 * \param[out] irq_history_mask    Pointer to the IRQ history mask.
 * \return                         \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_get_irq_history_mask(struct ethosu_device *dev, uint16_t *irq_history_mask);

/**
 * Clear the given bits in the
 *                                     IRQ history mask.
 * \param[in] irq_history_clear_mask   16 bit mask indicating which bits to
 *                                     clear in the IRQ history mask.
 * \return                             \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_clear_irq_history_mask(struct ethosu_device *dev, uint16_t irq_history_clear_mask);

/**
 * Perform a NPU soft reset.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_soft_reset(struct ethosu_device *dev);

/**
 * Wait for reset ready.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_wait_for_reset(struct ethosu_device *dev);

/**
 * Read and return the content of a given NPU APB
 *                             register range.
 * \param[in] start_address    Start address.
 * \param[in] num_reg          Number of registers to read.
 * \param[out] reg_p           Pointer to a output area, allocated by the
 *                             caller, where the register content shall be
 *                             written.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_read_apb_reg(struct ethosu_device *dev,
                                            uint32_t start_address,
                                            uint16_t num_reg,
                                            uint32_t *reg_p);

/**
 * Set qconfig register. I.e.
 *                             AXI configuration for the command stream.
 * \param[in] memory_type      Memory_type to use for command stream:
 *                             enum ethosu_memory_type.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_set_qconfig(struct ethosu_device *dev, enum ethosu_memory_type memory_type);

/**
 * Set register REGIONCFG.
 *                             Base pointer configuration.
 *                             Bits[2*k+1:2*k] give the memory type for BASEP[k].
 * \param[in] region           Region field to set: 0 - 7.
 * \param[in] memory_type      Memory_type to use for region: enum ethosu_memory_type.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_set_regioncfg(struct ethosu_device *dev,
                                             uint8_t region,
                                             enum ethosu_memory_type memory_type);

/**
 * Set AXI limit parameters for port 0 counter 0.
 * \param[in] max_beats        Burst split alignment, \ref ethosu_axi_limit_beats.
 * \param[in] memtype          Cache policy \ref ethosu_axi_limit_mem_type
 * \param[in] max_reads        Maximum number of outstanding reads.
 * \param[in] max_writes       Maximum number of outstanding writes.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_set_axi_limit0(struct ethosu_device *dev,
                                              enum ethosu_axi_limit_beats max_beats,
                                              enum ethosu_axi_limit_mem_type memtype,
                                              uint8_t max_reads,
                                              uint8_t max_writes);
/**
 * Set AXI limit parameters for port 0 counter 1.
 * \param[in] max_beats        Burst split alignment, \ref ethosu_axi_limit_beats.
 * \param[in] memtype          Cache policy \ref ethosu_axi_limit_mem_type
 * \param[in] max_reads        Maximum number of outstanding reads.
 * \param[in] max_writes       Maximum number of outstanding writes.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_set_axi_limit1(struct ethosu_device *dev,
                                              enum ethosu_axi_limit_beats max_beats,
                                              enum ethosu_axi_limit_mem_type memtype,
                                              uint8_t max_reads,
                                              uint8_t max_writes);
/**
 * Set AXI limit parameters for port 1 counter 2.
 * \param[in] max_beats        Burst split alignment, \ref ethosu_axi_limit_beats.
 * \param[in] memtype          Cache policy \ref ethosu_axi_limit_mem_type
 * \param[in] max_reads        Maximum number of outstanding reads.
 * \param[in] max_writes       Maximum number of outstanding writes.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_set_axi_limit2(struct ethosu_device *dev,
                                              enum ethosu_axi_limit_beats max_beats,
                                              enum ethosu_axi_limit_mem_type memtype,
                                              uint8_t max_reads,
                                              uint8_t max_writes);
/**
 * Set AXI limit parameters for port 1 counter 3.
 * \param[in] max_beats        Burst split alignment, \ref ethosu_axi_limit_beats.
 * \param[in] memtype          Cache policy \ref ethosu_axi_limit_mem_type
 * \param[in] max_reads        Maximum number of outstanding reads.
 * \param[in] max_writes       Maximum number of outstanding writes.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_set_axi_limit3(struct ethosu_device *dev,
                                              enum ethosu_axi_limit_beats max_beats,
                                              enum ethosu_axi_limit_mem_type memtype,
                                              uint8_t max_reads,
                                              uint8_t max_writes);

/**
 * Get current command stream queue read position.
 * \param[out] qread           Pointer to queue read.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_get_qread(struct ethosu_device *dev, uint32_t *qread);

/**
 * Get revision of NPU
 * \param[out] revision        Pointer to revision read.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_get_revision(struct ethosu_device *dev, uint32_t *revision);

/**
 * Issue run command for the currently programmed
 *                             command stream, starting at current queue read
 *                             position.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_set_command_run(struct ethosu_device *dev);

/**
 * Dump a 1KB section of SHRAM.
 * \param[in] section          Section offset to 1KB section in SHRAM.
 * \param[out] shram_p         Pointer to a output area, allocated by the
 *                             caller, where the SHRAM content shall be
 *                             written.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_get_shram_data(struct ethosu_device *dev, int section, uint32_t *shram_p);

/**
 * Set clock and power q request enable bits.
 * \param[in] clock_q          Clock q ENABLE/DISABLE \ref clock_q_request.
 * \param[in] power_q          Power q ENABLE/DISABLE \ref power_q_request.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_set_clock_and_power(struct ethosu_device *dev,
                                                   enum ethosu_clock_q_request clock_q,
                                                   enum ethosu_power_q_request power_q);

/**
 * Read register.
 * \param[in] address          Address to read.
 * \return                     Register value.
 */
uint32_t ethosu_read_reg(struct ethosu_device *dev, uint32_t address);

/**
 * Write register.
 * \param[in] address          Address to read.
 * \param[in] value            Value to be written.
 */
void ethosu_write_reg(struct ethosu_device *dev, uint32_t address, uint32_t value);

/**
 * Write register with shadow variable.
 * \param[in] address          Address to read.
 * \param[in] value            Value to be written.
 */
void ethosu_write_reg_shadow(struct ethosu_device *dev, uint32_t address, uint32_t value, uint32_t *shadow);

/**
 * Save the PMU configuration to ethosu_device struct.
 * \param[in] dev              Ethos-U device where the PMU configuration is
 *                             saved.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_save_pmu_config(struct ethosu_device *dev);

/**
 * Restore the PMU configuration from a ethosu_device struct.
 * \param[in] dev              Ethos-U device where the PMU configuration is
 *                             stored.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_restore_pmu_config(struct ethosu_device *dev);

/**
 * Save PMU counters to shadow variables in memory.
 * \param[in] dev              Ethos-U device where the PMU configuration is
 *                             stored.
 * \return                     \ref ethosu_error_codes
 */
enum ethosu_error_codes ethosu_save_pmu_counters(struct ethosu_device *dev);

/**
 * Check if the STATUS register has any error bits set or not.
 * \param[in] dev              Ethos-U device to check.
 * \return                     true if any error bits set,
 *                             false otherwise.
 */
bool ethosu_status_has_error(struct ethosu_device *dev);

#ifdef __cplusplus
}
#endif

#endif // ETHOSU_DEVICE_H