1/*
2 * Copyright 2017, Data61
3 * Commonwealth Scientific and Industrial Research Organisation (CSIRO)
4 * ABN 41 687 119 230.
5 *
6 * This software may be distributed and modified according to the terms of
7 * the BSD 2-Clause license. Note that NO WARRANTY is provided.
8 * See "LICENSE_BSD2.txt" for details.
9 *
10 * @TAG(DATA61_BSD)
11 */
12
13#pragma once
14
15#include <autoconf.h>
16
17#include <assert.h>
18#include <sel4/sel4.h>
19#include <stdlib.h>
20#include <utils/util.h>
21#include <vka/cspacepath_t.h>
22
23/* Simple does not address initial null caps, including seL4_CapNull.
24 * seL4_CapIOSpace, seL4_CapIOPortControl are null on architectures other than x86 */
25#define SIMPLE_SKIPPED_INIT_CAPS 3
26
27/* Request a cap to a specific IRQ number on the system
28 *
29 * @param irq the irq number to get the cap for
30 * @param data cookie for the underlying implementation
31 * @param the CNode in which to put this cap
32 * @param the index within the CNode to put cap
33 * @param Depth of index
34 */
35typedef seL4_Error(*simple_get_IRQ_handler_fn)(void *data, int irq, seL4_CNode cnode,
36                                               seL4_Word index, uint8_t depth);
37typedef seL4_Error(*simple_get_IRQ_trigger_fn)(void *data, int irq, int trigger, int core, seL4_CNode root,
38                                               seL4_Word index, uint8_t depth);
39
40typedef seL4_Error(*simple_get_iospace_cap_count_fn)(void *data, int *count);
41typedef seL4_CPtr(*simple_get_nth_iospace_cap_fn)(void *data, int n);
42
43typedef struct arch_simple {
44    simple_get_IRQ_handler_fn irq;
45    simple_get_IRQ_trigger_fn irq_trigger;
46#ifdef CONFIG_TK1_SMMU
47    simple_get_iospace_cap_count_fn iospace_cap_count;
48    simple_get_nth_iospace_cap_fn   iospace_get_nth_cap;
49#endif
50    void *data;
51} arch_simple_t;
52
53static inline seL4_Error arch_simple_get_IOPort_cap(UNUSED arch_simple_t *simple, UNUSED uint16_t start_port,
54                                                    UNUSED uint16_t end_port, UNUSED seL4_Word root,
55                                                    UNUSED seL4_Word dest, UNUSED seL4_Word depth)
56{
57    ZF_LOGF("Calling get_IOPort_cap on arm!");
58    return seL4_IllegalOperation;
59}
60
61static inline seL4_Error arch_simple_get_IRQ_trigger(arch_simple_t *simple, int irq, int trigger,
62                                                     cspacepath_t path)
63{
64    if (!simple) {
65        ZF_LOGE("Simple is NULL");
66        return seL4_InvalidArgument;
67    }
68    if (!simple->irq_trigger) {
69        ZF_LOGE("Not implemented");
70        return seL4_InvalidArgument;
71    }
72
73    return simple->irq_trigger(simple->data, irq, trigger, 0, path.root, path.capPtr, path.capDepth);
74}
75
76static inline seL4_Error arch_simple_get_IRQ_trigger_cpu(arch_simple_t *simple, int irq, int trigger, int core,
77                                                         cspacepath_t path)
78{
79    if (!simple) {
80        ZF_LOGE("Simple is NULL");
81        return seL4_InvalidArgument;
82    }
83    if (!simple->irq_trigger) {
84        ZF_LOGE("Not implemented");
85        return seL4_InvalidArgument;
86    }
87
88    return simple->irq_trigger(simple->data, irq, trigger, core, path.root, path.capPtr, path.capDepth);
89}
90