foxBMS - Unit Tests  1.2.1
The foxBMS Unit Tests API Documentation
i2c.c
Go to the documentation of this file.
1 /**
2  *
3  * @copyright © 2010 - 2021, Fraunhofer-Gesellschaft zur Foerderung der angewandten Forschung e.V.
4  * All rights reserved.
5  *
6  * SPDX-License-Identifier: BSD-3-Clause
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions are met:
10  *
11  * 1. Redistributions of source code must retain the above copyright notice, this
12  * list of conditions and the following disclaimer.
13  *
14  * 2. Redistributions in binary form must reproduce the above copyright notice,
15  * this list of conditions and the following disclaimer in the documentation
16  * and/or other materials provided with the distribution.
17  *
18  * 3. Neither the name of the copyright holder nor the names of its
19  * contributors may be used to endorse or promote products derived from
20  * this software without specific prior written permission.
21  *
22  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
23  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
24  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
25  * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
26  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
27  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
28  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
29  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
30  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
31  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32  *
33  * We kindly request you to use one or more of the following phrases to refer to
34  * foxBMS in your hardware, software, documentation or advertising materials:
35  *
36  * - ″This product uses parts of foxBMS®″
37  * - ″This product includes parts of foxBMS®″
38  * - ″This product is derived from foxBMS®″
39  *
40  */
41 
42 /**
43  * @file i2c.c
44  * @author foxBMS Team
45  * @date 2021-07-22 (date of creation)
46  * @updated 2021-12-08 (date of last update)
47  * @ingroup DRIVERS
48  * @prefix I2C
49  *
50  * @brief Driver for the I2C module
51  *
52  */
53 
54 /*========== Includes =======================================================*/
55 #include "i2c.h"
56 
57 #include "database.h"
58 #include "diag.h"
59 #include "dma.h"
60 #include "fsystem.h"
61 #include "mcu.h"
62 
63 /*========== Macros and Definitions =========================================*/
64 
65 /*========== Static Constant and Variable Definitions =======================*/
66 
67 /*========== Extern Constant and Variable Definitions =======================*/
68 
69 /*========== Static Function Prototypes =====================================*/
70 
71 /*========== Static Function Implementations ================================*/
72 
73 /*========== Extern Function Implementations ================================*/
74 extern void I2C_Initialize(void) {
75  i2cInit();
76 }
77 
78 extern STD_RETURN_TYPE_e I2C_Read(uint32_t slaveAddress, uint8_t readAddress, uint32_t nrBytes, uint8_t *readData) {
79  FAS_ASSERT(readData != NULL_PTR);
80 
81  STD_RETURN_TYPE_e retVal = STD_OK;
82  uint16_t timeout = I2C_TIMEOUT_ITERATIONS;
83  bool nack = false;
84  uint8_t *data = readData;
85  uint32_t count = nrBytes;
86 
87  if ((i2cREG1->STR & (uint32_t)I2C_BUSBUSY) == 0u) {
88  /* Clear bits */
89  i2cREG1->MDR &= ~((uint32_t)I2C_STOP_COND);
90  i2cREG1->MDR &= ~((uint32_t)I2C_START_COND);
91  i2cREG1->MDR &= ~((uint32_t)I2C_REPEATMODE);
92  i2cREG1->STR |= (uint32_t)I2C_TX_INT;
93  i2cREG1->STR |= (uint32_t)I2C_RX_INT;
94 
95  i2cSetMode(i2cREG1, (uint32_t)I2C_MASTER); /* Set as master */
96  i2cSetDirection(i2cREG1, (uint32_t)I2C_TRANSMITTER); /* Set as transmitter */
97  i2cSetSlaveAdd(i2cREG1, slaveAddress); /* Set slave address */
98  i2cSetCount(i2cREG1, 1u); /* Send 1 byte */
99  i2cSetStart(i2cREG1); /* Start write */
100  i2cREG1->DXR = (uint32_t)readAddress; /* Send register address */
101 
102  /* Wait until Tx buffer was copied to shift buffer */
103  timeout = I2C_TIMEOUT_ITERATIONS;
104  while (((i2cREG1->STR & (uint32_t)I2C_TX_INT) == 0u) && (timeout > 0u)) {
105  if ((i2cREG1->STR & (uint32_t)I2C_NACK) != 0u) {
106  nack = true;
107  break;
108  }
109  timeout--;
110  }
111 
112  if (timeout == 0u) {
113  /* Set repeat flag */
114  i2cREG1->MDR |= (uint32_t)I2C_REPEATMODE;
115  /* Set Stop condition */
116  i2cSetStop(i2cREG1);
117  timeout = I2C_TIMEOUT_ITERATIONS;
118  while ((i2cIsStopDetected(i2cREG1) == 0u) && (timeout > 0u)) {
119  timeout--;
120  }
121  retVal = STD_NOT_OK;
122  } else {
123  /* If slave ACK received, receive data */
124  if ((i2cREG1->STR & (uint32_t)I2C_NACK) == 0u) {
125  i2cSetMode(i2cREG1, (uint32_t)I2C_MASTER); /* Set as master */
126  i2cSetDirection(i2cREG1, (uint32_t)I2C_RECEIVER); /* Set as transmitter */
127  i2cSetCount(i2cREG1, nrBytes); /* Send count bytes before STOP condition */
128  i2cSetStart(i2cREG1); /* Start write */
129  i2cSetStop(i2cREG1); /* Stop condition after sending nrBytes bytes */
130 
131  /* Receive nrBytes bytes in polling mode */
132  while (count > 0u) {
133  timeout = I2C_TIMEOUT_ITERATIONS;
134  while (((i2cREG1->STR & (uint32_t)I2C_RX_INT) == 0u) && (timeout > 0u)) {
135  if ((i2cREG1->STR & (uint32_t)I2C_NACK_INT) != 0u) {
136  nack = true;
137  break;
138  }
139  timeout--;
140  }
141  if ((nack == true) || (timeout == 0u)) {
142  break;
143  }
144  *data = ((uint8)i2cREG1->DRR);
145  data++;
146  count--;
147  }
148  if ((nack == true) || (timeout == 0u)) {
149  /* Set repeat flag */
150  i2cREG1->MDR |= (uint32_t)I2C_REPEATMODE;
151  /* Set Stop condition */
152  i2cSetStop(i2cREG1);
153  timeout = I2C_TIMEOUT_ITERATIONS;
154  while ((i2cIsStopDetected(i2cREG1) == 0u) && (timeout > 0u)) {
155  timeout--;
156  }
157  retVal = STD_NOT_OK;
158  } else {
159  /* Wait until Stop is detected */
160  timeout = I2C_TIMEOUT_ITERATIONS;
161  while ((i2cIsStopDetected(i2cREG1) == 0u) && (timeout > 0u)) {
162  timeout--;
163  }
164  if (timeout == 0u) {
165  retVal = STD_NOT_OK;
166  } else {
167  i2cClearSCD(i2cREG1); /* Clear the Stop condition */
168  }
169  }
170  } else {
171  I2C_SetStopNow();
172  retVal = STD_NOT_OK;
173  }
174  }
175  } else {
176  I2C_SetStopNow();
177  retVal = STD_NOT_OK;
178  }
179 
180  return retVal;
181 }
182 
183 extern STD_RETURN_TYPE_e I2C_ReadDirect(uint32_t slaveAddress, uint32_t nrBytes, uint8_t *readData) {
184  FAS_ASSERT(readData != NULL_PTR);
185 
186  STD_RETURN_TYPE_e retVal = STD_OK;
187  uint16_t timeout = I2C_TIMEOUT_ITERATIONS;
188  bool nack = false;
189  uint8_t *data = readData;
190  uint32_t count = nrBytes;
191 
192  if ((i2cREG1->STR & (uint32_t)I2C_BUSBUSY) == 0u) {
193  /* Clear bits */
194  i2cREG1->MDR &= ~((uint32_t)I2C_STOP_COND);
195  i2cREG1->MDR &= ~((uint32_t)I2C_START_COND);
196  i2cREG1->MDR &= ~((uint32_t)I2C_REPEATMODE);
197  i2cREG1->STR |= (uint32_t)I2C_TX_INT;
198  i2cREG1->STR |= (uint32_t)I2C_RX_INT;
199  i2cREG1->STR |= (uint32_t)I2C_TX_INT;
200  i2cREG1->STR |= (uint32_t)I2C_RX_INT;
201 
202  i2cSetMode(i2cREG1, (uint32_t)I2C_MASTER); /* Set as master */
203  i2cSetDirection(i2cREG1, (uint32_t)I2C_RECEIVER); /* Set as transmitter */
204  i2cSetSlaveAdd(i2cREG1, slaveAddress); /* Set slave address */
205  i2cSetCount(i2cREG1, nrBytes); /* Send count bytes before STOP condition */
206  i2cSetStart(i2cREG1); /* Start write */
207  i2cSetStop(i2cREG1); /* Stop condition after sending nrBytes bytes */
208 
209  /* Receive nrBytes bytes in polling mode */
210  while (count > 0u) {
211  timeout = I2C_TIMEOUT_ITERATIONS;
212  while (((i2cREG1->STR & (uint32_t)I2C_RX_INT) == 0u) && (timeout > 0u)) {
213  if ((i2cREG1->STR & (uint32_t)I2C_NACK_INT) != 0u) {
214  nack = true;
215  break;
216  }
217  timeout--;
218  }
219  if ((nack == true) || (timeout == 0u)) {
220  break;
221  }
222  *data = ((uint8)i2cREG1->DRR);
223  data++;
224  count--;
225  }
226  if ((nack == true) || (timeout == 0u)) {
227  /* Set repeat flag */
228  i2cREG1->MDR |= (uint32_t)I2C_REPEATMODE;
229  /* Set Stop condition */
230  i2cSetStop(i2cREG1);
231  timeout = I2C_TIMEOUT_ITERATIONS;
232  while ((i2cIsStopDetected(i2cREG1) == 0u) && (timeout > 0u)) {
233  timeout--;
234  }
235  retVal = STD_NOT_OK;
236  } else {
237  /* Wait until Stop is detected */
238  timeout = I2C_TIMEOUT_ITERATIONS;
239  while ((i2cIsStopDetected(i2cREG1) == 0u) && (timeout > 0u)) {
240  timeout--;
241  }
242  if (timeout == 0u) {
243  retVal = STD_NOT_OK;
244  } else {
245  i2cClearSCD(i2cREG1); /* Clear the Stop condition */
246  }
247  }
248  } else {
249  I2C_SetStopNow();
250  retVal = STD_NOT_OK;
251  }
252 
253  return retVal;
254 }
255 
256 extern STD_RETURN_TYPE_e I2C_Write(uint32_t slaveAddress, uint8_t writeAddress, uint32_t nrBytes, uint8_t *writeData) {
257  FAS_ASSERT(writeData != NULL_PTR);
258 
259  STD_RETURN_TYPE_e retVal = STD_OK;
260  uint16_t timeout = I2C_TIMEOUT_ITERATIONS;
261  bool nack = false;
262  uint8_t *data = writeData;
263  uint32_t count = nrBytes;
264 
265  if ((i2cREG1->STR & (uint32_t)I2C_BUSBUSY) == 0u) {
266  /* Clear bits */
267  i2cREG1->MDR &= ~((uint32_t)I2C_STOP_COND);
268  i2cREG1->MDR &= ~((uint32_t)I2C_START_COND);
269  i2cREG1->MDR &= ~((uint32_t)I2C_REPEATMODE);
270  i2cREG1->STR |= (uint32_t)I2C_TX_INT;
271  i2cREG1->STR |= (uint32_t)I2C_RX_INT;
272 
273  i2cSetMode(i2cREG1, (uint32_t)I2C_MASTER); /* Set as master */
274  i2cSetDirection(i2cREG1, (uint32_t)I2C_TRANSMITTER); /* Set as transmitter */
275  i2cSetSlaveAdd(i2cREG1, slaveAddress); /* Set slave address */
276  i2cSetStop(i2cREG1); /* Stop condition after sending nrBytes bytes */
277  i2cSetCount(i2cREG1, nrBytes + 1u); /* Send count bytes before STOP condition */
278  i2cSetStart(i2cREG1); /* Start write */
279 
280  /* Send register address */
281  i2cREG1->DXR = (uint32_t)writeAddress;
282  /* Wait until Tx buffer was copied to shift buffer */
283  timeout = I2C_TIMEOUT_ITERATIONS;
284  while (((i2cREG1->STR & (uint32_t)I2C_TX_INT) == 0u) && (timeout > 0u)) {
285  if ((i2cREG1->STR & (uint32_t)I2C_NACK) != 0u) {
286  nack = true;
287  break;
288  }
289  timeout--;
290  }
291 
292  if (timeout == 0u) {
293  i2cREG1->MDR |= (uint32_t)I2C_REPEATMODE; /* Set repeat flag */
294  i2cSetStop(i2cREG1); /* Set Stop condition */
295 
296  timeout = I2C_TIMEOUT_ITERATIONS;
297  while ((i2cIsStopDetected(i2cREG1) == 0u) && (timeout > 0u)) {
298  timeout--;
299  }
300  retVal = STD_NOT_OK;
301  } else {
302  /* If slave ACK received, send data */
303  if ((i2cREG1->STR & (uint32_t)I2C_NACK) == 0u) {
304  /* Send nrBytes bytes in polling mode */
305  while (count > 0u) {
306  /* Wait until Tx buffer was copied to shift buffer */
307  timeout = I2C_TIMEOUT_ITERATIONS;
308  while (((i2cREG1->STR & (uint32_t)I2C_TX_INT) == 0u) && (timeout > 0u)) {
309  if ((i2cREG1->STR & (uint32_t)I2C_NACK) != 0u) {
310  nack = true;
311  break;
312  }
313  timeout--;
314  }
315  if ((nack == true) || (timeout == 0u)) {
316  break;
317  }
318  i2cREG1->DXR = (uint32_t)*data;
319  data++;
320  count--;
321  }
322  if ((nack == true) || (timeout == 0u)) {
323  i2cREG1->MDR |= (uint32_t)I2C_REPEATMODE; /* Set repeat flag */
324  i2cSetStop(i2cREG1); /* Set Stop condition */
325 
326  timeout = I2C_TIMEOUT_ITERATIONS;
327  while ((i2cIsStopDetected(i2cREG1) == 0u) && (timeout > 0u)) {
328  timeout--;
329  }
330  retVal = STD_NOT_OK;
331  } else {
332  /* Wait until Stop is detected */
333  timeout = I2C_TIMEOUT_ITERATIONS;
334  while ((i2cIsStopDetected(i2cREG1) == 0u) && (timeout > 0u)) {
335  timeout--;
336  }
337  if (timeout == 0u) {
338  retVal = STD_NOT_OK;
339  } else {
340  i2cClearSCD(i2cREG1); /* Clear the Stop condition */
341  }
342  }
343  } else {
344  I2C_SetStopNow();
345  retVal = STD_NOT_OK;
346  }
347  }
348  } else {
349  I2C_SetStopNow();
350  retVal = STD_NOT_OK;
351  }
352 
353  return retVal;
354 }
355 
356 extern STD_RETURN_TYPE_e I2C_WriteDirect(uint32_t slaveAddress, uint32_t nrBytes, uint8_t *writeData) {
357  FAS_ASSERT(writeData != NULL_PTR);
358 
359  STD_RETURN_TYPE_e retVal = STD_OK;
360  uint16_t timeout = I2C_TIMEOUT_ITERATIONS;
361  bool nack = false;
362  uint8_t *data = writeData;
363  uint32_t count = nrBytes;
364 
365  if ((i2cREG1->STR & (uint32_t)I2C_BUSBUSY) == 0u) {
366  /* Clear bits */
367  i2cREG1->MDR &= ~((uint32_t)I2C_STOP_COND);
368  i2cREG1->MDR &= ~((uint32_t)I2C_START_COND);
369  i2cREG1->MDR &= ~((uint32_t)I2C_REPEATMODE);
370  i2cREG1->STR |= (uint32_t)I2C_TX_INT;
371  i2cREG1->STR |= (uint32_t)I2C_RX_INT;
372 
373  i2cSetMode(i2cREG1, (uint32_t)I2C_MASTER); /* Set as master */
374  i2cSetDirection(i2cREG1, (uint32_t)I2C_TRANSMITTER); /* Set as transmitter */
375  i2cSetSlaveAdd(i2cREG1, slaveAddress); /* Set slave address */
376  i2cSetStop(i2cREG1); /* Stop condition after sending nrBytes bytes */
377  i2cSetCount(i2cREG1, nrBytes); /* Send count bytes before STOP condition */
378  i2cSetStart(i2cREG1); /* Start write */
379 
380  /* If slave ACK received, send data */
381  if ((i2cREG1->STR & (uint32_t)I2C_NACK) == 0u) {
382  /* Send nrBytes bytes in polling mode */
383  while (count > 0u) {
384  /* Wait until Tx buffer was copied to shift buffer */
385  timeout = I2C_TIMEOUT_ITERATIONS;
386  while (((i2cREG1->STR & (uint32_t)I2C_TX_INT) == 0u) && (timeout > 0u)) {
387  if ((i2cREG1->STR & (uint32_t)I2C_NACK) != 0u) {
388  nack = true;
389  break;
390  }
391  timeout--;
392  }
393  if ((nack == true) || (timeout == 0u)) {
394  break;
395  }
396  i2cREG1->DXR = (uint32_t)*data;
397  data++;
398  count--;
399  }
400  if ((nack == true) || (timeout == 0u)) {
401  i2cREG1->MDR |= (uint32_t)I2C_REPEATMODE; /* Set repeat flag */
402  i2cSetStop(i2cREG1); /* Set Stop condition */
403 
404  timeout = I2C_TIMEOUT_ITERATIONS;
405  while ((i2cIsStopDetected(i2cREG1) == 0u) && (timeout > 0u)) {
406  timeout--;
407  }
408  retVal = STD_NOT_OK;
409  } else {
410  /* Wait until Stop is detected */
411  timeout = I2C_TIMEOUT_ITERATIONS;
412  while ((i2cIsStopDetected(i2cREG1) == 0u) && (timeout > 0u)) {
413  timeout--;
414  }
415  if (timeout == 0u) {
416  retVal = STD_NOT_OK;
417  } else {
418  i2cClearSCD(i2cREG1); /* Clear the Stop condition */
419  }
420  }
421  } else {
422  I2C_SetStopNow();
423  retVal = STD_NOT_OK;
424  }
425  } else {
426  I2C_SetStopNow();
427  retVal = STD_NOT_OK;
428  }
429 
430  return retVal;
431 }
432 
433 extern STD_RETURN_TYPE_e I2C_ReadDma(uint32_t slaveAddress, uint8_t readAddress, uint32_t nrBytes, uint8_t *readData) {
434  FAS_ASSERT(readData != NULL_PTR);
435 
436  STD_RETURN_TYPE_e retVal = STD_OK;
437  uint16_t timeout = I2C_TIMEOUT_ITERATIONS;
438 
439  if ((i2cREG1->STR & (uint32_t)I2C_BUSBUSY) == 0u) {
441 
442  FAS_ASSERT(FSYS_RaisePrivilege() == 0); /* Go to privileged mode to write DMA config registers */
443 
444  /* Set Tx buffer address */
445  /* AXIVION Disable Style MisraC2012-1.1: Cast necessary for DMA configuration */
446  dmaRAMREG->PCP[(dmaChannel_t)DMA_CHANNEL_I2C_RX].IDADDR = (uint32_t)readData;
447  /* AXIVION Enable Style MisraC2012-1.1: */
448  /* Set number of Tx bytes to transmit */
449  dmaRAMREG->PCP[(dmaChannel_t)DMA_CHANNEL_I2C_RX].ITCOUNT = (nrBytes << 16U) | 1U;
450 
451  dmaSetChEnable((dmaChannel_t)DMA_CHANNEL_I2C_RX, (dmaTriggerType_t)DMA_HW);
452 
453  FSYS_SwitchToUserMode(); /* DMA config registers written, leave privileged mode */
455 
456  i2cREG1->DMACR |= (uint32_t)I2C_RXDMAEN; /* Activate I2C DMA RX */
457 
458  i2cSetMode(i2cREG1, (uint32_t)I2C_MASTER); /* Set to master */
459  i2cSetDirection(i2cREG1, (uint32_t)I2C_TRANSMITTER); /* Set as transmitter */
460  i2cSetSlaveAdd(i2cREG1, slaveAddress); /* Set slave address */
461  i2cSetCount(i2cREG1, 1u); /* Write one byte to select register address */
462  i2cSetStart(i2cREG1); /* Start write */
463  i2cSendByte(i2cREG1, readAddress); /* Transmit register address */
464 
465  /* Wait until Tx buffer was copied to shift buffer */
466  while ((i2cREG1->STR & (uint32_t)I2C_TX_INT) == 0u) {
467  if ((i2cREG1->STR & (uint32_t)I2C_NACK) != 0u) {
468  break;
469  }
470  }
471 
472  if ((i2cREG1->STR & (uint32_t)I2C_NACK) == 0u) {
473  i2cSetDirection(i2cREG1, (uint32_t)I2C_RECEIVER); /* Set as receiver */
474  i2cSetCount(i2cREG1, nrBytes); /* Receive nrBytes before STOP condition */
475  i2cSetMode(i2cREG1, (uint32_t)I2C_MASTER); /* Set as master */
476  i2cSetStop(i2cREG1); /* Stop condition after receiving nrBytes bytes */
477  i2cSetStart(i2cREG1); /* Set start while bus busy for REPEATED START condition */
478  } else {
479  i2cREG1->STR |= (uint32_t)I2C_NACK; /* Clear NACK flag */
480  i2cREG1->STR |= (uint32_t)I2C_TX_INT; /* Set Tx ready flag */
481  i2cSetStop(i2cREG1); /* Set Stop condition */
482 
483  /* Wait until Stop is detected */
484  timeout = I2C_TIMEOUT_ITERATIONS;
485  while ((i2cIsStopDetected(i2cREG1) == 0u) && (timeout > 0u)) {
486  timeout--;
487  }
488 
489  i2cClearSCD(i2cREG1); /* Clear the Stop condition */
490  retVal = STD_NOT_OK;
491  }
492  } else {
493  retVal = STD_NOT_OK;
494  }
495 
496  return retVal;
497 }
498 
500  uint32_t slaveAddress,
501  uint8_t writeAddress,
502  uint32_t nrBytes,
503  uint8_t *writeData) {
504  FAS_ASSERT(writeData != NULL_PTR);
505 
506  STD_RETURN_TYPE_e retVal = STD_OK;
507  uint16_t timeout = I2C_TIMEOUT_ITERATIONS;
508 
509  if ((i2cREG1->STR & (uint32_t)I2C_BUSBUSY) == 0u) {
511 
512  FAS_ASSERT(FSYS_RaisePrivilege() == 0); /* Go to privileged mode to write DMA config registers */
513 
514  /* Set Tx buffer address */
515  /* AXIVION Disable Style MisraC2012-1.1: Cast necessary for DMA configuration */
516  dmaRAMREG->PCP[(dmaChannel_t)DMA_CHANNEL_I2C_TX].ISADDR = (uint32_t)writeData;
517  /* AXIVION Enable Style MisraC2012-1.1: */
518  /* Set number of Tx bytes to transmit */
519  dmaRAMREG->PCP[(dmaChannel_t)DMA_CHANNEL_I2C_TX].ITCOUNT = (nrBytes << 16U) | 1U;
520 
521  dmaSetChEnable((dmaChannel_t)DMA_CHANNEL_I2C_TX, (dmaTriggerType_t)DMA_HW);
522 
523  FSYS_SwitchToUserMode(); /* DMA config registers written, leave privileged mode */
525 
526  i2cSetMode(i2cREG1, (uint32_t)I2C_MASTER); /* Set as master */
527  i2cSetDirection(i2cREG1, (uint32_t)I2C_TRANSMITTER); /* Set as transmitter */
528  i2cSetSlaveAdd(i2cREG1, slaveAddress); /* Set slave address */
529  i2cSetStop(i2cREG1); /* Stop condition after sending nrBytes bytes */
530  i2cSetCount(i2cREG1, nrBytes + 1u); /* Send (nrBytes+1) before STOP condition (includes register address)*/
531  i2cSendByte(i2cREG1, writeAddress); /* Send register address */
532  i2cREG1->DMACR |= (uint32_t)I2C_TXDMAEN; /* Activate I2C DMA TX */
533  i2cSetStart(i2cREG1); /* Start write */
534 
535  /* Wait until Tx buffer was copied to shift buffer */
536  while ((i2cREG1->STR & (uint32_t)I2C_TX_INT) == 0u) {
537  if ((i2cREG1->STR & (uint32_t)I2C_NACK) != 0u) {
538  break;
539  }
540  }
541 
542  if ((i2cREG1->STR & (uint32_t)I2C_NACK) != 0u) {
543  i2cREG1->STR |= (uint32_t)I2C_NACK; /* Clear NACK flag */
544  i2cREG1->STR |= (uint32_t)I2C_TX_INT; /* Set Tx ready flag */
545  i2cSetStop(i2cREG1); /* Set Stop condition */
546  timeout = I2C_TIMEOUT_ITERATIONS; /* Wait until Stop is detected */
547 
548  while ((i2cIsStopDetected(i2cREG1) == 0u) && (timeout > 0u)) {
549  timeout--;
550  }
551 
552  i2cClearSCD(i2cREG1); /* Clear the Stop condition */
553  i2cREG1->STR &= ~(uint32_t)I2C_REPEATMODE;
554  retVal = STD_NOT_OK;
555  }
556  } else {
557  retVal = STD_NOT_OK;
558  }
559 
560  return retVal;
561 }
562 
563 extern void I2C_SetStopNow(void) {
564  /* Clear bits */
565  i2cREG1->MDR &= ~((uint32_t)I2C_STOP_COND);
566  i2cREG1->MDR &= ~((uint32_t)I2C_START_COND);
567  i2cREG1->MDR &= ~((uint32_t)I2C_REPEATMODE);
568  i2cREG1->STR |= (uint32_t)I2C_TX_INT;
569  i2cREG1->STR |= (uint32_t)I2C_RX_INT;
570 
571  i2cREG1->MDR |= (uint32_t)I2C_REPEATMODE; /* Set repeat flag */
572  i2cSetMode(i2cREG1, (uint32_t)I2C_MASTER); /* Set as master */
573  i2cSetDirection(i2cREG1, (uint32_t)I2C_TRANSMITTER); /* Set as transmitter */
574  i2cSetStop(i2cREG1); /* Set Stop condition */
575 
576  while (i2cIsStopDetected(i2cREG1) == 0u) {
577  }
578 
579  i2cREG1->MDR &= ~(uint32_t)I2C_REPEATMODE; /* Reset repeat flag */
580  i2cClearSCD(i2cREG1); /* Clear the Stop condition */
581 }
582 
583 /*========== Getter for static Variables (Unit Test) ========================*/
584 #ifdef UNITY_UNIT_TEST
585 
586 #endif
587 
588 /*========== Externalized Static Function Implementations (Unit Test) =======*/
Database module header.
Diagnosis driver header.
Headers for the driver for the DMA module.
#define DMA_CHANNEL_I2C_TX
Definition: dma_cfg.h:80
#define DMA_CHANNEL_I2C_RX
Definition: dma_cfg.h:81
#define FAS_ASSERT(x)
Assertion macro that asserts that x is true.
Definition: fassert.h:235
@ STD_NOT_OK
Definition: fstd_types.h:82
@ STD_OK
Definition: fstd_types.h:81
#define NULL_PTR
Null pointer.
Definition: fstd_types.h:75
enum STD_RETURN_TYPE STD_RETURN_TYPE_e
Function to switch between user mode and privilege mode.
#define FSYS_SwitchToUserMode()
Switch back to user mode.
Definition: fsystem.h:113
long FSYS_RaisePrivilege(void)
raise privilege
Definition: test_htsensor.c:66
STD_RETURN_TYPE_e I2C_WriteDirect(uint32_t slaveAddress, uint32_t nrBytes, uint8_t *writeData)
writes to an I2C slave, no register address written first, blocking.
Definition: i2c.c:356
void I2C_SetStopNow(void)
sets stop condition.
Definition: i2c.c:563
STD_RETURN_TYPE_e I2C_ReadDma(uint32_t slaveAddress, uint8_t readAddress, uint32_t nrBytes, uint8_t *readData)
reads from an I2C slave, using DMA.
Definition: i2c.c:433
STD_RETURN_TYPE_e I2C_Write(uint32_t slaveAddress, uint8_t writeAddress, uint32_t nrBytes, uint8_t *writeData)
writes to an I2C slave, blocking.
Definition: i2c.c:256
STD_RETURN_TYPE_e I2C_ReadDirect(uint32_t slaveAddress, uint32_t nrBytes, uint8_t *readData)
reads from an I2C slave, no register address written first, blocking.
Definition: i2c.c:183
void I2C_Initialize(void)
Definition: i2c.c:74
STD_RETURN_TYPE_e I2C_WriteDma(uint32_t slaveAddress, uint8_t writeAddress, uint32_t nrBytes, uint8_t *writeData)
writes to an I2C slave, using DMA.
Definition: i2c.c:499
STD_RETURN_TYPE_e I2C_Read(uint32_t slaveAddress, uint8_t readAddress, uint32_t nrBytes, uint8_t *readData)
reads from an I2C slave, blocking.
Definition: i2c.c:78
Header for the driver for the I2C module.
#define I2C_RXDMAEN
Definition: i2c.h:70
#define I2C_TIMEOUT_ITERATIONS
Definition: i2c.h:65
#define I2C_TXDMAEN
Definition: i2c.h:68
Headers for the driver for the MCU module.
void OS_ExitTaskCritical(void)
Exit Critical interface function for use in FreeRTOS-Tasks and FreeRTOS-ISR.
Definition: os_freertos.c:125
void OS_EnterTaskCritical(void)
Enter Critical interface function for use in FreeRTOS-Tasks and FreeRTOS-ISR.
Definition: os_freertos.c:121