Software APIs
dif_uart_autogen.c
1 // Copyright lowRISC contributors (OpenTitan project).
2 // Licensed under the Apache License, Version 2.0, see LICENSE for details.
3 // SPDX-License-Identifier: Apache-2.0
4 
5 // THIS FILE HAS BEEN GENERATED, DO NOT EDIT MANUALLY. COMMAND:
6 // util/make_new_dif.py --mode=regen --only=autogen
7 
9 
10 #include <stdint.h>
11 
13 
14 #include "uart_regs.h" // Generated.
15 
18  if (uart == NULL) {
19  return kDifBadArg;
20  }
21 
22  uart->base_addr = base_addr;
23 
24  return kDifOk;
25 }
26 
28  dif_uart_alert_t alert) {
29  if (uart == NULL) {
30  return kDifBadArg;
31  }
32 
33  bitfield_bit32_index_t alert_idx;
34  switch (alert) {
36  alert_idx = UART_ALERT_TEST_FATAL_FAULT_BIT;
37  break;
38  default:
39  return kDifBadArg;
40  }
41 
42  uint32_t alert_test_reg = bitfield_bit32_write(0, alert_idx, true);
43  mmio_region_write32(uart->base_addr, (ptrdiff_t)UART_ALERT_TEST_REG_OFFSET,
44  alert_test_reg);
45 
46  return kDifOk;
47 }
48 
49 /**
50  * Get the corresponding interrupt register bit offset of the IRQ.
51  */
52 static bool uart_get_irq_bit_index(dif_uart_irq_t irq,
53  bitfield_bit32_index_t *index_out) {
54  switch (irq) {
56  *index_out = UART_INTR_COMMON_TX_WATERMARK_BIT;
57  break;
59  *index_out = UART_INTR_COMMON_RX_WATERMARK_BIT;
60  break;
61  case kDifUartIrqTxDone:
62  *index_out = UART_INTR_COMMON_TX_DONE_BIT;
63  break;
65  *index_out = UART_INTR_COMMON_RX_OVERFLOW_BIT;
66  break;
68  *index_out = UART_INTR_COMMON_RX_FRAME_ERR_BIT;
69  break;
71  *index_out = UART_INTR_COMMON_RX_BREAK_ERR_BIT;
72  break;
74  *index_out = UART_INTR_COMMON_RX_TIMEOUT_BIT;
75  break;
77  *index_out = UART_INTR_COMMON_RX_PARITY_ERR_BIT;
78  break;
79  case kDifUartIrqTxEmpty:
80  *index_out = UART_INTR_COMMON_TX_EMPTY_BIT;
81  break;
82  default:
83  return false;
84  }
85 
86  return true;
87 }
88 
89 static dif_irq_type_t irq_types[] = {
93 };
94 
97  dif_irq_type_t *type) {
98  if (uart == NULL || type == NULL || irq == kDifUartIrqTxEmpty + 1) {
99  return kDifBadArg;
100  }
101 
102  *type = irq_types[irq];
103 
104  return kDifOk;
105 }
106 
109  dif_uart_irq_state_snapshot_t *snapshot) {
110  if (uart == NULL || snapshot == NULL) {
111  return kDifBadArg;
112  }
113 
114  *snapshot = mmio_region_read32(uart->base_addr,
115  (ptrdiff_t)UART_INTR_STATE_REG_OFFSET);
116 
117  return kDifOk;
118 }
119 
122  const dif_uart_t *uart, dif_uart_irq_state_snapshot_t snapshot) {
123  if (uart == NULL) {
124  return kDifBadArg;
125  }
126 
127  mmio_region_write32(uart->base_addr, (ptrdiff_t)UART_INTR_STATE_REG_OFFSET,
128  snapshot);
129 
130  return kDifOk;
131 }
132 
135  bool *is_pending) {
136  if (uart == NULL || is_pending == NULL) {
137  return kDifBadArg;
138  }
139 
141  if (!uart_get_irq_bit_index(irq, &index)) {
142  return kDifBadArg;
143  }
144 
145  uint32_t intr_state_reg = mmio_region_read32(
146  uart->base_addr, (ptrdiff_t)UART_INTR_STATE_REG_OFFSET);
147 
148  *is_pending = bitfield_bit32_read(intr_state_reg, index);
149 
150  return kDifOk;
151 }
152 
155  if (uart == NULL) {
156  return kDifBadArg;
157  }
158 
159  // Writing to the register clears the corresponding bits (Write-one clear).
160  mmio_region_write32(uart->base_addr, (ptrdiff_t)UART_INTR_STATE_REG_OFFSET,
161  UINT32_MAX);
162 
163  return kDifOk;
164 }
165 
168  dif_uart_irq_t irq) {
169  if (uart == NULL) {
170  return kDifBadArg;
171  }
172 
174  if (!uart_get_irq_bit_index(irq, &index)) {
175  return kDifBadArg;
176  }
177 
178  // Writing to the register clears the corresponding bits (Write-one clear).
179  uint32_t intr_state_reg = bitfield_bit32_write(0, index, true);
180  mmio_region_write32(uart->base_addr, (ptrdiff_t)UART_INTR_STATE_REG_OFFSET,
181  intr_state_reg);
182 
183  return kDifOk;
184 }
185 
188  const bool val) {
189  if (uart == NULL) {
190  return kDifBadArg;
191  }
192 
194  if (!uart_get_irq_bit_index(irq, &index)) {
195  return kDifBadArg;
196  }
197 
198  uint32_t intr_test_reg = bitfield_bit32_write(0, index, val);
199  mmio_region_write32(uart->base_addr, (ptrdiff_t)UART_INTR_TEST_REG_OFFSET,
200  intr_test_reg);
201 
202  return kDifOk;
203 }
204 
207  dif_uart_irq_t irq, dif_toggle_t *state) {
208  if (uart == NULL || state == NULL) {
209  return kDifBadArg;
210  }
211 
213  if (!uart_get_irq_bit_index(irq, &index)) {
214  return kDifBadArg;
215  }
216 
217  uint32_t intr_enable_reg = mmio_region_read32(
218  uart->base_addr, (ptrdiff_t)UART_INTR_ENABLE_REG_OFFSET);
219 
220  bool is_enabled = bitfield_bit32_read(intr_enable_reg, index);
221  *state = is_enabled ? kDifToggleEnabled : kDifToggleDisabled;
222 
223  return kDifOk;
224 }
225 
228  dif_uart_irq_t irq, dif_toggle_t state) {
229  if (uart == NULL) {
230  return kDifBadArg;
231  }
232 
234  if (!uart_get_irq_bit_index(irq, &index)) {
235  return kDifBadArg;
236  }
237 
238  uint32_t intr_enable_reg = mmio_region_read32(
239  uart->base_addr, (ptrdiff_t)UART_INTR_ENABLE_REG_OFFSET);
240 
241  bool enable_bit = (state == kDifToggleEnabled) ? true : false;
242  intr_enable_reg = bitfield_bit32_write(intr_enable_reg, index, enable_bit);
243  mmio_region_write32(uart->base_addr, (ptrdiff_t)UART_INTR_ENABLE_REG_OFFSET,
244  intr_enable_reg);
245 
246  return kDifOk;
247 }
248 
251  const dif_uart_t *uart, dif_uart_irq_enable_snapshot_t *snapshot) {
252  if (uart == NULL) {
253  return kDifBadArg;
254  }
255 
256  // Pass the current interrupt state to the caller, if requested.
257  if (snapshot != NULL) {
258  *snapshot = mmio_region_read32(uart->base_addr,
259  (ptrdiff_t)UART_INTR_ENABLE_REG_OFFSET);
260  }
261 
262  // Disable all interrupts.
263  mmio_region_write32(uart->base_addr, (ptrdiff_t)UART_INTR_ENABLE_REG_OFFSET,
264  0u);
265 
266  return kDifOk;
267 }
268 
271  const dif_uart_t *uart, const dif_uart_irq_enable_snapshot_t *snapshot) {
272  if (uart == NULL || snapshot == NULL) {
273  return kDifBadArg;
274  }
275 
276  mmio_region_write32(uart->base_addr, (ptrdiff_t)UART_INTR_ENABLE_REG_OFFSET,
277  *snapshot);
278 
279  return kDifOk;
280 }