L4Re Operating System Framework
Interface and Usage Documentation
All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
icu_svr
1// vi:set ft=cpp: -*- Mode: C++ -*-
2/*
3 * (c) 2009-2014 Alexander Warg <alexander.warg@kernkonzept.com>
4 *
5 * License: see LICENSE.spdx (in this directory or the directories above)
6 */
7
8#pragma once
9
10
11#include <l4/sys/types.h>
12
13#include <l4/sys/icu>
14#include <l4/sys/task>
15#include <l4/re/env>
16#include <l4/re/util/cap_alloc>
17#include <l4/sys/cxx/ipc_legacy>
18
19namespace L4Re { namespace Util {
20
21template< typename ICU >
22class Icu_svr
23{
24private:
25 ICU const *this_icu() const { return static_cast<ICU const *>(this); }
26 ICU *this_icu() { return static_cast<ICU*>(this); }
27
28public:
29 L4_RPC_LEGACY_DISPATCH(L4::Icu);
30
31 int op_bind(L4::Icu::Rights, l4_umword_t irqnum,
32 L4::Ipc::Snd_fpage irq_fp);
33 int op_unbind(L4::Icu::Rights, l4_umword_t irqnum,
34 L4::Ipc::Snd_fpage irq_fp);
35 int op_info(L4::Icu::Rights, L4::Icu::_Info &info);
36 int op_msi_info(L4::Icu::Rights, l4_umword_t irqnum,
37 l4_uint64_t source, l4_icu_msi_info_t &info);
38 int op_mask(L4::Icu::Rights, l4_umword_t irqnum);
39 int op_unmask(L4::Icu::Rights, l4_umword_t irqnum);
40 int op_set_mode(L4::Icu::Rights, l4_umword_t, l4_umword_t)
41 { return 0; }
42};
43
44template<typename ICU> inline
45int
46Icu_svr<ICU>::op_bind(L4::Icu::Rights, l4_umword_t irqnum,
47 L4::Ipc::Snd_fpage irq_fp)
48{
49 typename ICU::Irq *irq = this_icu()->icu_get_irq(irqnum);
50 if (!irq)
51 return -L4_EINVAL;
52
53 return irq->bind(this_icu(), irq_fp);
54}
55
56template<typename ICU> inline
57int
58Icu_svr<ICU>::op_unbind(L4::Icu::Rights, l4_umword_t irqnum,
59 L4::Ipc::Snd_fpage irq_fp)
60{
61 typename ICU::Irq *irq = this_icu()->icu_get_irq(irqnum);
62 if (!irq)
63 return -L4_EINVAL;
64
65 return irq->unbind(this_icu(), irq_fp);
66}
67
68template<typename ICU> inline
69int
70Icu_svr<ICU>::op_info(L4::Icu::Rights, L4::Icu::_Info &info)
71{
73 this_icu()->icu_get_info(&i);
74 info.features = i.features;
75 info.nr_irqs = i.nr_irqs;
76 info.nr_msis = i.nr_msis;
77 return 0;
78}
79
80template<typename ICU> inline
81int
82Icu_svr<ICU>::op_msi_info(L4::Icu::Rights, l4_umword_t irqnum,
83 l4_uint64_t source, l4_icu_msi_info_t &info)
84{
85 typename ICU::Irq *irq = this_icu()->icu_get_irq(irqnum);
86 if (!irq)
87 return -L4_EINVAL;
88 return irq->msi_info(source, &info);
89}
90
91template<typename ICU> inline
92int
93Icu_svr<ICU>::op_mask(L4::Icu::Rights, l4_umword_t irqnum)
94{
95 typename ICU::Irq *irq = this_icu()->icu_get_irq(irqnum);
96 if (irq)
97 irq->mask(true);
98 return -L4_ENOREPLY;
99}
100
101template<typename ICU> inline
102int
103Icu_svr<ICU>::op_unmask(L4::Icu::Rights, l4_umword_t irqnum)
104{
105 typename ICU::Irq *irq = this_icu()->icu_get_irq(irqnum);
106 if (irq)
107 irq->mask(false);
108 return -L4_ENOREPLY;
109}
110
111
112template< typename ICU >
113class Icu_cap_array_svr : public Icu_svr<ICU>
114{
115protected:
116 static void free_irq_cap(L4::Cap<L4::Irq> &cap)
117 {
118 if (cap)
119 {
121 cap.invalidate();
122 }
123 }
124
125public:
126 class Irq
127 {
128 public:
129 Irq() {}
130 ~Irq() { ICU::free_irq_cap(_cap); }
131
132 void trigger() const
133 {
134 if (_cap)
135 _cap->trigger();
136 }
137
138 int bind(ICU *, L4::Ipc::Snd_fpage const &irq_fp);
139 int unbind(ICU *, L4::Ipc::Snd_fpage const &irq_fp);
140 void mask(bool /*mask*/) const
141 { }
142
143 int msi_info(l4_uint64_t, l4_icu_msi_info_t *) const
144 { return -L4_EINVAL; }
145
146 L4::Cap<L4::Irq> cap() const { return _cap; }
147
148 private:
149 L4::Cap<L4::Irq> _cap;
150 };
151
152private:
153 Irq *_irqs;
154 unsigned _nr_irqs;
155
156public:
157
158 Icu_cap_array_svr(unsigned nr_irqs, Irq *irqs)
159 : _irqs(irqs), _nr_irqs(nr_irqs)
160 {}
161
162 Irq *icu_get_irq(l4_umword_t irqnum)
163 {
164 if (irqnum >= _nr_irqs)
165 return 0;
166
167 return _irqs + irqnum;
168 }
169
170 void icu_get_info(l4_icu_info_t *inf)
171 {
172 inf->features = 0;
173 inf->nr_irqs = _nr_irqs;
174 inf->nr_msis = 0;
175 }
176};
177
178template< typename ICU >
179int
180Icu_cap_array_svr<ICU>::Irq::bind(ICU *cfb, L4::Ipc::Snd_fpage const &irq_fp)
181{
182 if (!irq_fp.cap_received())
183 return -L4_EINVAL;
184
185 L4::Cap<L4::Irq> irq = cfb->server_iface()->template rcv_cap<L4::Irq>(0);
186 if (!irq)
187 return -L4_EINVAL;
188
189 int r = cfb->server_iface()->realloc_rcv_cap(0);
190 if (r < 0)
191 return r;
192
193 ICU::free_irq_cap(_cap);
194 _cap = irq;
195 return 0;
196}
197
198template< typename ICU >
199int
200Icu_cap_array_svr<ICU>::Irq::unbind(ICU *, L4::Ipc::Snd_fpage const &/*irq_fp*/)
201{
202 ICU::free_irq_cap(_cap);
204 return 0;
205}
206
207
208}}
void free(L4::Cap< void > cap, l4_cap_idx_t task=L4_INVALID_CAP, unsigned unmap_flags=L4_FP_ALL_SPACES) noexcept override
Free a capability.
void invalidate() noexcept
Set this capability to invalid (L4_INVALID_CAP).
Definition capability.h:137
C++ interface for capabilities.
Definition capability.h:219
C++ Icu interface, see Interrupt controller for the C interface.
Definition irq:249
Send item or return item.
Definition ipc_types:324
bool cap_received() const noexcept
*(Defined for return items only.)* Check if at least one object capability has been mapped for this i...
Definition ipc_types:496
Environment interface.
unsigned long l4_umword_t
Unsigned machine word.
Definition l4int.h:40
unsigned long long l4_uint64_t
Unsigned 64bit value.
Definition l4int.h:31
@ L4_EINVAL
Invalid argument.
Definition err.h:46
@ L4_ENOREPLY
No reply.
Definition err.h:55
_Cap_alloc & cap_alloc
Capability allocator.
Interrupt controller.
Common L4 ABI Data Types.
L4Re C++ Interfaces.
Definition cmd_control:14
Info structure for an ICU.
Definition icu.h:163
unsigned nr_msis
The number of MSI vectors supported by the ICU,.
Definition icu.h:179
unsigned nr_irqs
The number of IRQ lines supported by the ICU,.
Definition icu.h:174
unsigned features
Feature flags.
Definition icu.h:169
Info to use for a specific MSI.
Definition icu.h:184
Common task related definitions.
Capability allocator.