mbed library sources

Dependents:   Encrypted my_mbed lklk CyaSSL_DTLS_Cellular ... more

Superseded

This library was superseded by mbed-dev - https://os.mbed.com/users/mbed_official/code/mbed-dev/.

Development branch of the mbed library sources. This library is kept in synch with the latest changes from the mbed SDK and it is not guaranteed to work.

If you are looking for a stable and tested release, please import one of the official mbed library releases:

Import librarymbed

The official Mbed 2 C/C++ SDK provides the software platform and libraries to build your applications.

Committer:
mbed_official
Date:
Fri Jul 17 09:15:10 2015 +0100
Revision:
592:a274ee790e56
Parent:
579:53297373a894
Synchronized with git revision e7144f83a8d75df80c4877936b6ffe552b0be9e6

Full URL: https://github.com/mbedmicro/mbed/commit/e7144f83a8d75df80c4877936b6ffe552b0be9e6/

More API implementation for SAMR21

Who changed what in which revision?

UserRevisionLine numberNew contents of line
mbed_official 579:53297373a894 1 #ifndef I2C_SLAVE_H_INCLUDED
mbed_official 579:53297373a894 2 #define I2C_SLAVE_H_INCLUDED
mbed_official 579:53297373a894 3
mbed_official 579:53297373a894 4 #include "i2c_common.h"
mbed_official 579:53297373a894 5 #include <sercom.h>
mbed_official 579:53297373a894 6 #include <pinmux.h>
mbed_official 579:53297373a894 7
mbed_official 579:53297373a894 8 #if I2C_SLAVE_CALLBACK_MODE == true
mbed_official 579:53297373a894 9 # include <sercom_interrupt.h>
mbed_official 579:53297373a894 10 #endif
mbed_official 579:53297373a894 11
mbed_official 579:53297373a894 12 #ifndef PINMUX_DEFAULT
mbed_official 579:53297373a894 13 # define PINMUX_DEFAULT 0
mbed_official 579:53297373a894 14 #endif
mbed_official 579:53297373a894 15
mbed_official 579:53297373a894 16 #ifdef __cplusplus
mbed_official 579:53297373a894 17 extern "C" {
mbed_official 579:53297373a894 18 #endif
mbed_official 579:53297373a894 19
mbed_official 579:53297373a894 20 /**
mbed_official 579:53297373a894 21 * \addtogroup asfdoc_sam0_sercom_i2c_group
mbed_official 579:53297373a894 22 *
mbed_official 579:53297373a894 23 * @{
mbed_official 579:53297373a894 24 *
mbed_official 579:53297373a894 25 */
mbed_official 579:53297373a894 26
mbed_official 579:53297373a894 27 /**
mbed_official 579:53297373a894 28 * \name I2C Slave Status Flags
mbed_official 579:53297373a894 29 *
mbed_official 579:53297373a894 30 * I<SUP>2</SUP>C slave status flags, returned by \ref i2c_slave_get_status() and cleared
mbed_official 579:53297373a894 31 * by \ref i2c_slave_clear_status().
mbed_official 579:53297373a894 32 * @{
mbed_official 579:53297373a894 33 */
mbed_official 579:53297373a894 34
mbed_official 579:53297373a894 35 /** Address Match.
mbed_official 579:53297373a894 36 * \note Should only be cleared internally by driver.
mbed_official 579:53297373a894 37 */
mbed_official 579:53297373a894 38 #define I2C_SLAVE_STATUS_ADDRESS_MATCH (1UL << 0)
mbed_official 579:53297373a894 39 /** Data Ready. */
mbed_official 579:53297373a894 40 #define I2C_SLAVE_STATUS_DATA_READY (1UL << 1)
mbed_official 579:53297373a894 41 /** Stop Received. */
mbed_official 579:53297373a894 42 #define I2C_SLAVE_STATUS_STOP_RECEIVED (1UL << 2)
mbed_official 579:53297373a894 43 /** Clock Hold.
mbed_official 579:53297373a894 44 * \note Cannot be cleared, only valid when I2C_SLAVE_STATUS_ADDRESS_MATCH is
mbed_official 579:53297373a894 45 * set.
mbed_official 579:53297373a894 46 */
mbed_official 579:53297373a894 47 #define I2C_SLAVE_STATUS_CLOCK_HOLD (1UL << 3)
mbed_official 579:53297373a894 48 /** SCL Low Timeout. */
mbed_official 579:53297373a894 49 #define I2C_SLAVE_STATUS_SCL_LOW_TIMEOUT (1UL << 4)
mbed_official 579:53297373a894 50 /** Repeated Start.
mbed_official 579:53297373a894 51 * \note Cannot be cleared, only valid when I2C_SLAVE_STATUS_ADDRESS_MATCH is
mbed_official 579:53297373a894 52 * set.
mbed_official 579:53297373a894 53 */
mbed_official 579:53297373a894 54 #define I2C_SLAVE_STATUS_REPEATED_START (1UL << 5)
mbed_official 579:53297373a894 55 /** Received not acknowledge.
mbed_official 579:53297373a894 56 * \note Cannot be cleared.
mbed_official 579:53297373a894 57 */
mbed_official 579:53297373a894 58 #define I2C_SLAVE_STATUS_RECEIVED_NACK (1UL << 6)
mbed_official 579:53297373a894 59 /** Transmit Collision. */
mbed_official 579:53297373a894 60 #define I2C_SLAVE_STATUS_COLLISION (1UL << 7)
mbed_official 579:53297373a894 61 /** Bus error. */
mbed_official 579:53297373a894 62 #define I2C_SLAVE_STATUS_BUS_ERROR (1UL << 8)
mbed_official 579:53297373a894 63
mbed_official 579:53297373a894 64 /** @} */
mbed_official 579:53297373a894 65
mbed_official 579:53297373a894 66 /**
mbed_official 579:53297373a894 67 * \brief I<SUP>2</SUP>C slave packet for read/write
mbed_official 579:53297373a894 68 *
mbed_official 579:53297373a894 69 * Structure to be used when transferring I<SUP>2</SUP>C slave packets.
mbed_official 579:53297373a894 70 */
mbed_official 579:53297373a894 71 struct i2c_slave_packet {
mbed_official 579:53297373a894 72 /** Length of data array. */
mbed_official 579:53297373a894 73 uint16_t data_length;
mbed_official 579:53297373a894 74 /** Data array containing all data to be transferred. */
mbed_official 579:53297373a894 75 uint8_t *data;
mbed_official 579:53297373a894 76 };
mbed_official 579:53297373a894 77
mbed_official 579:53297373a894 78 #if I2C_SLAVE_CALLBACK_MODE == true
mbed_official 579:53297373a894 79 /**
mbed_official 579:53297373a894 80 * \brief Callback types
mbed_official 579:53297373a894 81 *
mbed_official 579:53297373a894 82 * The available callback types for the I<SUP>2</SUP>C slave.
mbed_official 579:53297373a894 83 */
mbed_official 579:53297373a894 84 enum i2c_slave_callback {
mbed_official 579:53297373a894 85 /** Callback for packet write complete. */
mbed_official 579:53297373a894 86 I2C_SLAVE_CALLBACK_WRITE_COMPLETE,
mbed_official 579:53297373a894 87 /** Callback for packet read complete. */
mbed_official 579:53297373a894 88 I2C_SLAVE_CALLBACK_READ_COMPLETE,
mbed_official 579:53297373a894 89 /**
mbed_official 579:53297373a894 90 * Callback for read request from master - can be used to
mbed_official 579:53297373a894 91 * issue a write.
mbed_official 579:53297373a894 92 */
mbed_official 579:53297373a894 93 I2C_SLAVE_CALLBACK_READ_REQUEST,
mbed_official 579:53297373a894 94 /**
mbed_official 579:53297373a894 95 * Callback for write request from master - can be used to issue a read.
mbed_official 579:53297373a894 96 */
mbed_official 579:53297373a894 97 I2C_SLAVE_CALLBACK_WRITE_REQUEST,
mbed_official 579:53297373a894 98 /** Callback for error. */
mbed_official 579:53297373a894 99 I2C_SLAVE_CALLBACK_ERROR,
mbed_official 579:53297373a894 100 /**
mbed_official 579:53297373a894 101 * Callback for error in last transfer. Discovered on a new address
mbed_official 579:53297373a894 102 * interrupt.
mbed_official 579:53297373a894 103 */
mbed_official 579:53297373a894 104 I2C_SLAVE_CALLBACK_ERROR_LAST_TRANSFER,
mbed_official 579:53297373a894 105 # if !defined(__DOXYGEN__)
mbed_official 579:53297373a894 106 /** Total number of callbacks. */
mbed_official 579:53297373a894 107 _I2C_SLAVE_CALLBACK_N,
mbed_official 579:53297373a894 108 # endif
mbed_official 579:53297373a894 109 };
mbed_official 579:53297373a894 110
mbed_official 579:53297373a894 111 # if !defined(__DOXYGEN__)
mbed_official 579:53297373a894 112 /** Software module prototype. */
mbed_official 579:53297373a894 113 struct i2c_slave_module;
mbed_official 579:53297373a894 114
mbed_official 579:53297373a894 115 /** Callback type. */
mbed_official 579:53297373a894 116 typedef void (*i2c_slave_callback_t)(
mbed_official 579:53297373a894 117 struct i2c_slave_module *const module);
mbed_official 579:53297373a894 118 # endif
mbed_official 579:53297373a894 119 #endif
mbed_official 579:53297373a894 120
mbed_official 579:53297373a894 121 /**
mbed_official 579:53297373a894 122 * \brief Enum for the possible SDA hold times with respect to the negative
mbed_official 579:53297373a894 123 * edge of SCL
mbed_official 579:53297373a894 124 *
mbed_official 579:53297373a894 125 * Enum for the possible SDA hold times with respect to the negative edge
mbed_official 579:53297373a894 126 * of SCL.
mbed_official 579:53297373a894 127 */
mbed_official 579:53297373a894 128 enum i2c_slave_sda_hold_time {
mbed_official 579:53297373a894 129 /** SDA hold time disabled. */
mbed_official 579:53297373a894 130 I2C_SLAVE_SDA_HOLD_TIME_DISABLED =
mbed_official 579:53297373a894 131 ((SERCOM_I2CS_CTRLA_SDAHOLD_Msk & ((0) << SERCOM_I2CS_CTRLA_SDAHOLD_Pos))),
mbed_official 579:53297373a894 132 /** SDA hold time 50ns - 100ns. */
mbed_official 579:53297373a894 133 I2C_SLAVE_SDA_HOLD_TIME_50NS_100NS =
mbed_official 579:53297373a894 134 ((SERCOM_I2CS_CTRLA_SDAHOLD_Msk & ((1) << SERCOM_I2CS_CTRLA_SDAHOLD_Pos))),
mbed_official 579:53297373a894 135 /** SDA hold time 300ns - 600ns. */
mbed_official 579:53297373a894 136 I2C_SLAVE_SDA_HOLD_TIME_300NS_600NS =
mbed_official 579:53297373a894 137 ((SERCOM_I2CS_CTRLA_SDAHOLD_Msk & ((2) << SERCOM_I2CS_CTRLA_SDAHOLD_Pos))),
mbed_official 579:53297373a894 138 /** SDA hold time 400ns - 800ns. */
mbed_official 579:53297373a894 139 I2C_SLAVE_SDA_HOLD_TIME_400NS_800NS =
mbed_official 579:53297373a894 140 ((SERCOM_I2CS_CTRLA_SDAHOLD_Msk & ((3) << SERCOM_I2CS_CTRLA_SDAHOLD_Pos))),
mbed_official 579:53297373a894 141 };
mbed_official 579:53297373a894 142
mbed_official 579:53297373a894 143 /**
mbed_official 579:53297373a894 144 * \brief Enum for the possible address modes
mbed_official 579:53297373a894 145 *
mbed_official 579:53297373a894 146 * Enum for the possible address modes.
mbed_official 579:53297373a894 147 */
mbed_official 579:53297373a894 148 enum i2c_slave_address_mode {
mbed_official 579:53297373a894 149 /** Address match on address_mask used as a mask to address. */
mbed_official 579:53297373a894 150 I2C_SLAVE_ADDRESS_MODE_MASK = SERCOM_I2CS_CTRLB_AMODE(0),
mbed_official 579:53297373a894 151 /** Address math on both address and address_mask. */
mbed_official 579:53297373a894 152 I2C_SLAVE_ADDRESS_MODE_TWO_ADDRESSES = SERCOM_I2CS_CTRLB_AMODE(1),
mbed_official 579:53297373a894 153 /**
mbed_official 579:53297373a894 154 * Address match on range of addresses between and including address and
mbed_official 579:53297373a894 155 * address_mask.
mbed_official 579:53297373a894 156 */
mbed_official 579:53297373a894 157 I2C_SLAVE_ADDRESS_MODE_RANGE = SERCOM_I2CS_CTRLB_AMODE(2),
mbed_official 579:53297373a894 158 };
mbed_official 579:53297373a894 159
mbed_official 579:53297373a894 160 /**
mbed_official 579:53297373a894 161 * \brief Enum for the direction of a request
mbed_official 579:53297373a894 162 *
mbed_official 579:53297373a894 163 * Enum for the direction of a request.
mbed_official 579:53297373a894 164 */
mbed_official 579:53297373a894 165 enum i2c_slave_direction {
mbed_official 579:53297373a894 166 /** Read. */
mbed_official 579:53297373a894 167 I2C_SLAVE_DIRECTION_READ,
mbed_official 579:53297373a894 168 /** Write. */
mbed_official 579:53297373a894 169 I2C_SLAVE_DIRECTION_WRITE,
mbed_official 579:53297373a894 170 /** No direction. */
mbed_official 579:53297373a894 171 I2C_SLAVE_DIRECTION_NONE,
mbed_official 579:53297373a894 172 };
mbed_official 579:53297373a894 173
mbed_official 579:53297373a894 174 #ifdef FEATURE_I2C_FAST_MODE_PLUS_AND_HIGH_SPEED
mbed_official 579:53297373a894 175 /**
mbed_official 579:53297373a894 176 * \brief Enum for the transfer speed
mbed_official 579:53297373a894 177 *
mbed_official 579:53297373a894 178 * Enum for the transfer speed.
mbed_official 579:53297373a894 179 */
mbed_official 579:53297373a894 180 enum i2c_slave_transfer_speed {
mbed_official 579:53297373a894 181 /** Standard-mode (Sm) up to 100KHz and Fast-mode (Fm) up to 400KHz. */
mbed_official 579:53297373a894 182 I2C_SLAVE_SPEED_STANDARD_AND_FAST = SERCOM_I2CS_CTRLA_SPEED(0),
mbed_official 579:53297373a894 183 /** Fast-mode Plus (Fm+) up to 1MHz. */
mbed_official 579:53297373a894 184 I2C_SLAVE_SPEED_FAST_MODE_PLUS = SERCOM_I2CS_CTRLA_SPEED(1),
mbed_official 579:53297373a894 185 /** High-speed mode (Hs-mode) up to 3.4MHz. */
mbed_official 579:53297373a894 186 I2C_SLAVE_SPEED_HIGH_SPEED = SERCOM_I2CS_CTRLA_SPEED(2),
mbed_official 579:53297373a894 187 };
mbed_official 579:53297373a894 188 #endif
mbed_official 579:53297373a894 189
mbed_official 579:53297373a894 190 /**
mbed_official 579:53297373a894 191 * \brief SERCOM I<SUP>2</SUP>C Slave driver software device instance structure.
mbed_official 579:53297373a894 192 *
mbed_official 579:53297373a894 193 * SERCOM I<SUP>2</SUP>C Slave driver software instance structure, used to
mbed_official 579:53297373a894 194 * retain software state information of an associated hardware module instance.
mbed_official 579:53297373a894 195 *
mbed_official 579:53297373a894 196 * \note The fields of this structure should not be altered by the user
mbed_official 579:53297373a894 197 * application; they are reserved for module-internal use only.
mbed_official 579:53297373a894 198 */
mbed_official 579:53297373a894 199 struct i2c_slave_module {
mbed_official 579:53297373a894 200 #if !defined(__DOXYGEN__)
mbed_official 579:53297373a894 201 /** Hardware instance initialized for the struct. */
mbed_official 579:53297373a894 202 Sercom *hw;
mbed_official 579:53297373a894 203 /** Module lock. */
mbed_official 579:53297373a894 204 volatile bool locked;
mbed_official 579:53297373a894 205 /** Timeout value for polled functions. */
mbed_official 579:53297373a894 206 uint16_t buffer_timeout;
mbed_official 579:53297373a894 207 # ifdef FEATURE_I2C_10_BIT_ADDRESS
mbed_official 579:53297373a894 208 /** Using 10-bit addressing for the slave. */
mbed_official 579:53297373a894 209 bool ten_bit_address;
mbed_official 579:53297373a894 210 # endif
mbed_official 579:53297373a894 211 # if I2C_SLAVE_CALLBACK_MODE == true
mbed_official 579:53297373a894 212 /** Nack on address match. */
mbed_official 579:53297373a894 213 bool nack_on_address;
mbed_official 579:53297373a894 214 /** Pointers to callback functions. */
mbed_official 579:53297373a894 215 volatile i2c_slave_callback_t callbacks[_I2C_SLAVE_CALLBACK_N];
mbed_official 579:53297373a894 216 /** Mask for registered callbacks. */
mbed_official 579:53297373a894 217 volatile uint8_t registered_callback;
mbed_official 579:53297373a894 218 /** Mask for enabled callbacks. */
mbed_official 579:53297373a894 219 volatile uint8_t enabled_callback;
mbed_official 579:53297373a894 220 /** The total number of bytes to transfer. */
mbed_official 579:53297373a894 221 volatile uint16_t buffer_length;
mbed_official 579:53297373a894 222 /**
mbed_official 579:53297373a894 223 * Counter used for bytes left to send in write and to count number of
mbed_official 579:53297373a894 224 * obtained bytes in read.
mbed_official 579:53297373a894 225 */
mbed_official 579:53297373a894 226 uint16_t buffer_remaining;
mbed_official 579:53297373a894 227 /** Data buffer for packet write and read. */
mbed_official 579:53297373a894 228 volatile uint8_t *buffer;
mbed_official 579:53297373a894 229 /** Save direction of request from master. 1 = read, 0 = write. */
mbed_official 579:53297373a894 230 volatile enum i2c_transfer_direction transfer_direction;
mbed_official 579:53297373a894 231 /** Status for status read back in error callback. */
mbed_official 579:53297373a894 232 volatile enum status_code status;
mbed_official 579:53297373a894 233 # endif
mbed_official 579:53297373a894 234 #endif
mbed_official 579:53297373a894 235 };
mbed_official 579:53297373a894 236
mbed_official 579:53297373a894 237 /**
mbed_official 579:53297373a894 238 * \brief Configuration structure for the I<SUP>2</SUP>C Slave device
mbed_official 579:53297373a894 239 *
mbed_official 579:53297373a894 240 * This is the configuration structure for the I<SUP>2</SUP>C Slave device. It is used
mbed_official 579:53297373a894 241 * as an argument for \ref i2c_slave_init to provide the desired
mbed_official 579:53297373a894 242 * configurations for the module. The structure should be initialized using the
mbed_official 579:53297373a894 243 * \ref i2c_slave_get_config_defaults.
mbed_official 579:53297373a894 244 */
mbed_official 579:53297373a894 245 struct i2c_slave_config {
mbed_official 579:53297373a894 246 /** Set to enable the SCL low timeout. */
mbed_official 579:53297373a894 247 bool enable_scl_low_timeout;
mbed_official 579:53297373a894 248 /** SDA hold time with respect to the negative edge of SCL. */
mbed_official 579:53297373a894 249 enum i2c_slave_sda_hold_time sda_hold_time;
mbed_official 579:53297373a894 250 /** Timeout to wait for master in polled functions. */
mbed_official 579:53297373a894 251 uint16_t buffer_timeout;
mbed_official 579:53297373a894 252 /** Addressing mode. */
mbed_official 579:53297373a894 253 enum i2c_slave_address_mode address_mode;
mbed_official 579:53297373a894 254 /** Address or upper limit of address range. */
mbed_official 579:53297373a894 255 uint16_t address;
mbed_official 579:53297373a894 256 /** Address mask, second address or lower limit of address range. */
mbed_official 579:53297373a894 257 uint16_t address_mask;
mbed_official 579:53297373a894 258 #ifdef FEATURE_I2C_10_BIT_ADDRESS
mbed_official 579:53297373a894 259 /** Enable 10-bit addressing. */
mbed_official 579:53297373a894 260 bool ten_bit_address;
mbed_official 579:53297373a894 261 #endif
mbed_official 579:53297373a894 262 /**
mbed_official 579:53297373a894 263 * Enable general call address recognition (general call address
mbed_official 579:53297373a894 264 * is defined as 0000000 with direction bit 0).
mbed_official 579:53297373a894 265 */
mbed_official 579:53297373a894 266 bool enable_general_call_address;
mbed_official 579:53297373a894 267
mbed_official 579:53297373a894 268 #ifdef FEATURE_I2C_FAST_MODE_PLUS_AND_HIGH_SPEED
mbed_official 579:53297373a894 269 /** Transfer speed mode. */
mbed_official 579:53297373a894 270 enum i2c_slave_transfer_speed transfer_speed;
mbed_official 579:53297373a894 271 #endif
mbed_official 579:53297373a894 272
mbed_official 579:53297373a894 273 #if I2C_SLAVE_CALLBACK_MODE == true
mbed_official 579:53297373a894 274 /**
mbed_official 579:53297373a894 275 * Enable NACK on address match (this can be changed after initialization
mbed_official 579:53297373a894 276 * via the \ref i2c_slave_enable_nack_on_address and
mbed_official 579:53297373a894 277 * \ref i2c_slave_disable_nack_on_address functions).
mbed_official 579:53297373a894 278 */
mbed_official 579:53297373a894 279 bool enable_nack_on_address;
mbed_official 579:53297373a894 280 #endif
mbed_official 579:53297373a894 281 /** GCLK generator to use as clock source. */
mbed_official 579:53297373a894 282 enum gclk_generator generator_source;
mbed_official 579:53297373a894 283 /** Set to keep module active in sleep modes. */
mbed_official 579:53297373a894 284 bool run_in_standby;
mbed_official 579:53297373a894 285 /** PAD0 (SDA) pinmux. */
mbed_official 579:53297373a894 286 uint32_t pinmux_pad0;
mbed_official 579:53297373a894 287 /** PAD1 (SCL) pinmux. */
mbed_official 579:53297373a894 288 uint32_t pinmux_pad1;
mbed_official 579:53297373a894 289 /** Set to enable SCL low time-out. */
mbed_official 579:53297373a894 290 bool scl_low_timeout;
mbed_official 579:53297373a894 291 #ifdef FEATURE_I2C_SCL_STRETCH_MODE
mbed_official 579:53297373a894 292 /** Set to enable SCL stretch only after ACK bit (required for high speed). */
mbed_official 579:53297373a894 293 bool scl_stretch_only_after_ack_bit;
mbed_official 579:53297373a894 294 #endif
mbed_official 579:53297373a894 295 #ifdef FEATURE_I2C_SCL_EXTEND_TIMEOUT
mbed_official 579:53297373a894 296 /** Set to enable slave SCL low extend time-out. */
mbed_official 579:53297373a894 297 bool slave_scl_low_extend_timeout;
mbed_official 579:53297373a894 298 #endif
mbed_official 579:53297373a894 299 };
mbed_official 579:53297373a894 300
mbed_official 579:53297373a894 301
mbed_official 579:53297373a894 302 /**
mbed_official 579:53297373a894 303 * \name Lock/Unlock
mbed_official 579:53297373a894 304 * @{
mbed_official 579:53297373a894 305 */
mbed_official 579:53297373a894 306
mbed_official 579:53297373a894 307 /**
mbed_official 579:53297373a894 308 * \brief Attempt to get lock on driver instance
mbed_official 579:53297373a894 309 *
mbed_official 579:53297373a894 310 * This function checks the instance's lock, which indicates whether or not it
mbed_official 579:53297373a894 311 * is currently in use, and sets the lock if it was not already set.
mbed_official 579:53297373a894 312 *
mbed_official 579:53297373a894 313 * The purpose of this is to enable exclusive access to driver instances, so
mbed_official 579:53297373a894 314 * that, e.g., transactions by different services will not interfere with each
mbed_official 579:53297373a894 315 * other.
mbed_official 579:53297373a894 316 *
mbed_official 579:53297373a894 317 * \param[in,out] module Pointer to the driver instance to lock
mbed_official 579:53297373a894 318 *
mbed_official 579:53297373a894 319 * \retval STATUS_OK If the module was locked
mbed_official 579:53297373a894 320 * \retval STATUS_BUSY If the module was already locked
mbed_official 579:53297373a894 321 */
mbed_official 579:53297373a894 322 static inline enum status_code i2c_slave_lock(
mbed_official 579:53297373a894 323 struct i2c_slave_module *const module)
mbed_official 579:53297373a894 324 {
mbed_official 579:53297373a894 325 enum status_code status;
mbed_official 579:53297373a894 326
mbed_official 579:53297373a894 327 system_interrupt_enter_critical_section();
mbed_official 579:53297373a894 328
mbed_official 579:53297373a894 329 if (module->locked) {
mbed_official 579:53297373a894 330 status = STATUS_BUSY;
mbed_official 579:53297373a894 331 } else {
mbed_official 579:53297373a894 332 module->locked = true;
mbed_official 579:53297373a894 333 status = STATUS_OK;
mbed_official 579:53297373a894 334 }
mbed_official 579:53297373a894 335
mbed_official 579:53297373a894 336 system_interrupt_leave_critical_section();
mbed_official 579:53297373a894 337
mbed_official 579:53297373a894 338 return status;
mbed_official 579:53297373a894 339 }
mbed_official 579:53297373a894 340
mbed_official 579:53297373a894 341 /**
mbed_official 579:53297373a894 342 * \brief Unlock driver instance
mbed_official 579:53297373a894 343 *
mbed_official 579:53297373a894 344 * This function clears the instance lock, indicating that it is available for
mbed_official 579:53297373a894 345 * use.
mbed_official 579:53297373a894 346 *
mbed_official 579:53297373a894 347 * \param[in,out] module Pointer to the driver instance to lock
mbed_official 579:53297373a894 348 *
mbed_official 579:53297373a894 349 * \retval STATUS_OK If the module was locked
mbed_official 579:53297373a894 350 * \retval STATUS_BUSY If the module was already locked
mbed_official 579:53297373a894 351 */
mbed_official 579:53297373a894 352 static inline void i2c_slave_unlock(struct i2c_slave_module *const module)
mbed_official 579:53297373a894 353 {
mbed_official 579:53297373a894 354 module->locked = false;
mbed_official 579:53297373a894 355 }
mbed_official 579:53297373a894 356
mbed_official 579:53297373a894 357 /** @} */
mbed_official 579:53297373a894 358
mbed_official 579:53297373a894 359 /**
mbed_official 579:53297373a894 360 * \name Configuration and Initialization
mbed_official 579:53297373a894 361 * @{
mbed_official 579:53297373a894 362 */
mbed_official 579:53297373a894 363
mbed_official 579:53297373a894 364 /**
mbed_official 579:53297373a894 365 * \brief Returns the synchronization status of the module
mbed_official 579:53297373a894 366 *
mbed_official 579:53297373a894 367 * Returns the synchronization status of the module.
mbed_official 579:53297373a894 368 *
mbed_official 579:53297373a894 369 * \param[out] module Pointer to software module structure
mbed_official 579:53297373a894 370 *
mbed_official 579:53297373a894 371 * \return Status of the synchronization.
mbed_official 579:53297373a894 372 * \retval true Module is busy synchronizing
mbed_official 579:53297373a894 373 * \retval false Module is not synchronizing
mbed_official 579:53297373a894 374 */
mbed_official 579:53297373a894 375 static inline bool i2c_slave_is_syncing(
mbed_official 579:53297373a894 376 const struct i2c_slave_module *const module)
mbed_official 579:53297373a894 377 {
mbed_official 579:53297373a894 378 /* Sanity check */
mbed_official 579:53297373a894 379 Assert(module);
mbed_official 579:53297373a894 380 Assert(module->hw);
mbed_official 579:53297373a894 381
mbed_official 579:53297373a894 382 SercomI2cs *const i2c_hw = &(module->hw->I2CS);
mbed_official 579:53297373a894 383
mbed_official 579:53297373a894 384 /* Return sync status */
mbed_official 579:53297373a894 385 #if defined(FEATURE_SERCOM_SYNCBUSY_SCHEME_VERSION_1)
mbed_official 579:53297373a894 386 return (i2c_hw->STATUS.reg & SERCOM_I2CS_STATUS_SYNCBUSY);
mbed_official 579:53297373a894 387 #elif defined(FEATURE_SERCOM_SYNCBUSY_SCHEME_VERSION_2)
mbed_official 579:53297373a894 388 return (i2c_hw->SYNCBUSY.reg & SERCOM_I2CS_SYNCBUSY_MASK);
mbed_official 579:53297373a894 389 #else
mbed_official 579:53297373a894 390 # error Unknown SERCOM SYNCBUSY scheme!
mbed_official 579:53297373a894 391 #endif
mbed_official 579:53297373a894 392 }
mbed_official 579:53297373a894 393
mbed_official 579:53297373a894 394 #if !defined(__DOXYGEN__)
mbed_official 579:53297373a894 395 /**
mbed_official 579:53297373a894 396 * \internal Wait for hardware module to sync
mbed_official 579:53297373a894 397 *
mbed_official 579:53297373a894 398 * \param[in] module Pointer to software module structure
mbed_official 579:53297373a894 399 */
mbed_official 579:53297373a894 400 static void _i2c_slave_wait_for_sync(
mbed_official 579:53297373a894 401 const struct i2c_slave_module *const module)
mbed_official 579:53297373a894 402 {
mbed_official 579:53297373a894 403 /* Sanity check. */
mbed_official 579:53297373a894 404 Assert(module);
mbed_official 579:53297373a894 405
mbed_official 579:53297373a894 406 while (i2c_slave_is_syncing(module)) {
mbed_official 579:53297373a894 407 /* Wait for I2C module to sync */
mbed_official 579:53297373a894 408 }
mbed_official 579:53297373a894 409 }
mbed_official 579:53297373a894 410 #endif
mbed_official 579:53297373a894 411
mbed_official 579:53297373a894 412 /**
mbed_official 579:53297373a894 413 * \brief Gets the I<SUP>2</SUP>C slave default configurations
mbed_official 579:53297373a894 414 *
mbed_official 579:53297373a894 415 * This will initialize the configuration structure to known default values.
mbed_official 579:53297373a894 416 *
mbed_official 579:53297373a894 417 * The default configuration is as follows:
mbed_official 579:53297373a894 418 * - Disable SCL low timeout
mbed_official 579:53297373a894 419 * - 300ns - 600ns SDA hold time
mbed_official 579:53297373a894 420 * - Buffer timeout = 65535
mbed_official 579:53297373a894 421 * - Address with mask
mbed_official 579:53297373a894 422 * - Address = 0
mbed_official 579:53297373a894 423 * - Address mask = 0 (one single address)
mbed_official 579:53297373a894 424 * - General call address disabled
mbed_official 579:53297373a894 425 * - Address nack disabled if the interrupt driver is used
mbed_official 579:53297373a894 426 * - GCLK generator 0
mbed_official 579:53297373a894 427 * - Do not run in standby
mbed_official 579:53297373a894 428 * - PINMUX_DEFAULT for SERCOM pads
mbed_official 579:53297373a894 429 *
mbed_official 579:53297373a894 430 * Those default configuration only availale if the device supports it:
mbed_official 579:53297373a894 431 * - Not using 10-bit addressing
mbed_official 579:53297373a894 432 * - Standard-mode and Fast-mode transfer speed
mbed_official 579:53297373a894 433 * - SCL stretch disabled
mbed_official 579:53297373a894 434 * - slave SCL low extend time-out disabled
mbed_official 579:53297373a894 435 *
mbed_official 579:53297373a894 436 * \param[out] config Pointer to configuration structure to be initialized
mbed_official 579:53297373a894 437 */
mbed_official 579:53297373a894 438 static inline void i2c_slave_get_config_defaults(
mbed_official 579:53297373a894 439 struct i2c_slave_config *const config)
mbed_official 579:53297373a894 440 {
mbed_official 579:53297373a894 441 /*Sanity check argument. */
mbed_official 579:53297373a894 442 Assert(config);
mbed_official 579:53297373a894 443 config->enable_scl_low_timeout = false;
mbed_official 579:53297373a894 444 config->sda_hold_time = I2C_SLAVE_SDA_HOLD_TIME_300NS_600NS;
mbed_official 579:53297373a894 445 config->buffer_timeout = 65535;
mbed_official 579:53297373a894 446 config->address_mode = I2C_SLAVE_ADDRESS_MODE_MASK;
mbed_official 579:53297373a894 447 config->address = 0;
mbed_official 579:53297373a894 448 config->address_mask = 0;
mbed_official 579:53297373a894 449 #ifdef FEATURE_I2C_10_BIT_ADDRESS
mbed_official 579:53297373a894 450 config->ten_bit_address = false;
mbed_official 579:53297373a894 451 #endif
mbed_official 579:53297373a894 452 config->enable_general_call_address = false;
mbed_official 579:53297373a894 453 #ifdef FEATURE_I2C_FAST_MODE_PLUS_AND_HIGH_SPEED
mbed_official 579:53297373a894 454 config->transfer_speed = I2C_SLAVE_SPEED_STANDARD_AND_FAST;
mbed_official 579:53297373a894 455 #endif
mbed_official 579:53297373a894 456 #if I2C_SLAVE_CALLBACK_MODE == true
mbed_official 579:53297373a894 457 config->enable_nack_on_address = false;
mbed_official 579:53297373a894 458 #endif
mbed_official 579:53297373a894 459 config->generator_source = GCLK_GENERATOR_0;
mbed_official 579:53297373a894 460 config->run_in_standby = false;
mbed_official 579:53297373a894 461 config->pinmux_pad0 = PINMUX_DEFAULT;
mbed_official 579:53297373a894 462 config->pinmux_pad1 = PINMUX_DEFAULT;
mbed_official 579:53297373a894 463 config->scl_low_timeout = false;
mbed_official 579:53297373a894 464 #ifdef FEATURE_I2C_SCL_STRETCH_MODE
mbed_official 579:53297373a894 465 config->scl_stretch_only_after_ack_bit = false;
mbed_official 579:53297373a894 466 #endif
mbed_official 579:53297373a894 467 #ifdef FEATURE_I2C_SCL_EXTEND_TIMEOUT
mbed_official 579:53297373a894 468 config->slave_scl_low_extend_timeout = false;
mbed_official 579:53297373a894 469 #endif
mbed_official 579:53297373a894 470 }
mbed_official 579:53297373a894 471
mbed_official 579:53297373a894 472 enum status_code i2c_slave_init(struct i2c_slave_module *const module,
mbed_official 579:53297373a894 473 Sercom *const hw,
mbed_official 579:53297373a894 474 const struct i2c_slave_config *const config);
mbed_official 579:53297373a894 475
mbed_official 579:53297373a894 476 /**
mbed_official 579:53297373a894 477 * \brief Enables the I<SUP>2</SUP>C module
mbed_official 579:53297373a894 478 *
mbed_official 579:53297373a894 479 * This will enable the requested I<SUP>2</SUP>C module.
mbed_official 579:53297373a894 480 *
mbed_official 579:53297373a894 481 * \param[in] module Pointer to the software module struct
mbed_official 579:53297373a894 482 */
mbed_official 579:53297373a894 483 static inline void i2c_slave_enable(
mbed_official 579:53297373a894 484 const struct i2c_slave_module *const module)
mbed_official 579:53297373a894 485 {
mbed_official 579:53297373a894 486 /* Sanity check of arguments. */
mbed_official 579:53297373a894 487 Assert(module);
mbed_official 579:53297373a894 488 Assert(module->hw);
mbed_official 579:53297373a894 489
mbed_official 579:53297373a894 490 SercomI2cs *const i2c_hw = &(module->hw->I2CS);
mbed_official 579:53297373a894 491
mbed_official 579:53297373a894 492 #if I2C_SLAVE_CALLBACK_MODE == true
mbed_official 579:53297373a894 493 /* Enable global interrupt for module */
mbed_official 579:53297373a894 494 system_interrupt_enable(_sercom_get_interrupt_vector(module->hw));
mbed_official 579:53297373a894 495 #endif
mbed_official 579:53297373a894 496
mbed_official 579:53297373a894 497 /* Wait for module to sync */
mbed_official 579:53297373a894 498 _i2c_slave_wait_for_sync(module);
mbed_official 579:53297373a894 499
mbed_official 579:53297373a894 500 /* Enable module */
mbed_official 579:53297373a894 501 i2c_hw->CTRLA.reg |= SERCOM_I2CS_CTRLA_ENABLE;
mbed_official 579:53297373a894 502 }
mbed_official 579:53297373a894 503
mbed_official 579:53297373a894 504
mbed_official 579:53297373a894 505 /**
mbed_official 579:53297373a894 506 * \brief Disables the I<SUP>2</SUP>C module
mbed_official 579:53297373a894 507 *
mbed_official 579:53297373a894 508 * This will disable the I<SUP>2</SUP>C module specified in the provided software module
mbed_official 579:53297373a894 509 * structure.
mbed_official 579:53297373a894 510 *
mbed_official 579:53297373a894 511 * \param[in] module Pointer to the software module struct
mbed_official 579:53297373a894 512 */
mbed_official 579:53297373a894 513 static inline void i2c_slave_disable(
mbed_official 579:53297373a894 514 const struct i2c_slave_module *const module)
mbed_official 579:53297373a894 515 {
mbed_official 579:53297373a894 516 /* Sanity check of arguments. */
mbed_official 579:53297373a894 517 Assert(module);
mbed_official 579:53297373a894 518 Assert(module->hw);
mbed_official 579:53297373a894 519
mbed_official 579:53297373a894 520 SercomI2cs *const i2c_hw = &(module->hw->I2CS);
mbed_official 579:53297373a894 521
mbed_official 579:53297373a894 522 #if I2C_SLAVE_CALLBACK_MODE == true
mbed_official 579:53297373a894 523 /* Disable interrupts */
mbed_official 579:53297373a894 524 i2c_hw->INTENCLR.reg = SERCOM_I2CS_INTENSET_PREC |
mbed_official 579:53297373a894 525 SERCOM_I2CS_INTENSET_AMATCH | SERCOM_I2CS_INTENSET_DRDY;
mbed_official 579:53297373a894 526
mbed_official 579:53297373a894 527 /* Clear interrupt flags */
mbed_official 579:53297373a894 528 i2c_hw->INTFLAG.reg = SERCOM_I2CS_INTFLAG_PREC | SERCOM_I2CS_INTFLAG_AMATCH |
mbed_official 579:53297373a894 529 SERCOM_I2CS_INTFLAG_DRDY;
mbed_official 579:53297373a894 530
mbed_official 579:53297373a894 531 /* Disable global interrupt for module */
mbed_official 579:53297373a894 532 system_interrupt_disable(_sercom_get_interrupt_vector(module->hw));
mbed_official 579:53297373a894 533 #endif
mbed_official 579:53297373a894 534
mbed_official 579:53297373a894 535 /* Wait for module to sync */
mbed_official 579:53297373a894 536 _i2c_slave_wait_for_sync(module);
mbed_official 579:53297373a894 537
mbed_official 579:53297373a894 538 /* Disable module */
mbed_official 579:53297373a894 539 i2c_hw->CTRLA.reg &= ~SERCOM_I2CS_CTRLA_ENABLE;
mbed_official 579:53297373a894 540 }
mbed_official 579:53297373a894 541
mbed_official 579:53297373a894 542 void i2c_slave_reset(
mbed_official 579:53297373a894 543 struct i2c_slave_module *const module);
mbed_official 579:53297373a894 544
mbed_official 579:53297373a894 545 /** @} */
mbed_official 579:53297373a894 546
mbed_official 579:53297373a894 547 /**
mbed_official 579:53297373a894 548 * \name Read and Write
mbed_official 579:53297373a894 549 * @{
mbed_official 579:53297373a894 550 */
mbed_official 579:53297373a894 551
mbed_official 579:53297373a894 552 enum status_code i2c_slave_write_packet_wait(
mbed_official 579:53297373a894 553 struct i2c_slave_module *const module,
mbed_official 579:53297373a894 554 struct i2c_slave_packet *const packet);
mbed_official 579:53297373a894 555 enum status_code i2c_slave_read_packet_wait(
mbed_official 579:53297373a894 556 struct i2c_slave_module *const module,
mbed_official 579:53297373a894 557 struct i2c_slave_packet *const packet);
mbed_official 579:53297373a894 558 enum i2c_slave_direction i2c_slave_get_direction_wait(
mbed_official 579:53297373a894 559 struct i2c_slave_module *const module);
mbed_official 579:53297373a894 560
mbed_official 579:53297373a894 561 /** @} */
mbed_official 579:53297373a894 562
mbed_official 579:53297373a894 563 /**
mbed_official 579:53297373a894 564 * \name Status Management
mbed_official 579:53297373a894 565 * @{
mbed_official 579:53297373a894 566 */
mbed_official 579:53297373a894 567 uint32_t i2c_slave_get_status(
mbed_official 579:53297373a894 568 struct i2c_slave_module *const module);
mbed_official 579:53297373a894 569 void i2c_slave_clear_status(
mbed_official 579:53297373a894 570 struct i2c_slave_module *const module,
mbed_official 579:53297373a894 571 uint32_t status_flags);
mbed_official 579:53297373a894 572 /** @} */
mbed_official 579:53297373a894 573
mbed_official 579:53297373a894 574 #ifdef FEATURE_I2C_DMA_SUPPORT
mbed_official 579:53297373a894 575 /**
mbed_official 579:53297373a894 576 * \name SERCOM I2C Slave with DMA Interfaces
mbed_official 579:53297373a894 577 * @{
mbed_official 579:53297373a894 578 */
mbed_official 579:53297373a894 579
mbed_official 579:53297373a894 580 /**
mbed_official 579:53297373a894 581 * \brief Read SERCOM I<SUP>2</SUP>C interrupt status.
mbed_official 579:53297373a894 582 *
mbed_official 579:53297373a894 583 * Read I<SUP>2</SUP>C interrupt status for DMA transfer.
mbed_official 579:53297373a894 584 *
mbed_official 579:53297373a894 585 * \param[in,out] module Pointer to the driver instance to lock
mbed_official 579:53297373a894 586 *
mbed_official 579:53297373a894 587 */
mbed_official 579:53297373a894 588 static inline uint8_t i2c_slave_dma_read_interrupt_status(struct i2c_slave_module *const module)
mbed_official 579:53297373a894 589 {
mbed_official 579:53297373a894 590 return (uint8_t)module->hw->I2CS.INTFLAG.reg;
mbed_official 579:53297373a894 591 }
mbed_official 579:53297373a894 592
mbed_official 579:53297373a894 593 /**
mbed_official 579:53297373a894 594 * \brief Write SERCOM I<SUP>2</SUP>C interrupt status.
mbed_official 579:53297373a894 595 *
mbed_official 579:53297373a894 596 * Write I<SUP>2</SUP>C interrupt status for DMA transfer.
mbed_official 579:53297373a894 597 *
mbed_official 579:53297373a894 598 * \param[in,out] module Pointer to the driver instance to lock
mbed_official 579:53297373a894 599 * \param[in] flag Interrupt flag status
mbed_official 579:53297373a894 600 *
mbed_official 579:53297373a894 601 */
mbed_official 579:53297373a894 602 static inline void i2c_slave_dma_write_interrupt_status(struct i2c_slave_module *const module,
mbed_official 579:53297373a894 603 uint8_t flag)
mbed_official 579:53297373a894 604 {
mbed_official 579:53297373a894 605 module->hw->I2CS.INTFLAG.reg = flag;
mbed_official 579:53297373a894 606 }
mbed_official 579:53297373a894 607
mbed_official 579:53297373a894 608 /** @} */
mbed_official 579:53297373a894 609 #endif
mbed_official 579:53297373a894 610
mbed_official 579:53297373a894 611 /** @} */
mbed_official 579:53297373a894 612
mbed_official 579:53297373a894 613 #ifdef __cplusplus
mbed_official 579:53297373a894 614 }
mbed_official 579:53297373a894 615 #endif
mbed_official 579:53297373a894 616
mbed_official 579:53297373a894 617 #endif /* I2C_SLAVE_H_INCLUDED */