1 /**
2   ******************************************************************************
3   * @file    lis2mdl_reg.h
4   * @author  Sensors Software Solution Team
5   * @brief   This file contains all the functions prototypes for the
6   *          lis2mdl_reg.c driver.
7   ******************************************************************************
8   * @attention
9   *
10   * <h2><center>&copy; Copyright (c) 2021 STMicroelectronics.
11   * All rights reserved.</center></h2>
12   *
13   * This software component is licensed by ST under BSD 3-Clause license,
14   * the "License"; You may not use this file except in compliance with the
15   * License. You may obtain a copy of the License at:
16   *                        opensource.org/licenses/BSD-3-Clause
17   *
18   ******************************************************************************
19   */
20 
21 /* Define to prevent recursive inclusion -------------------------------------*/
22 #ifndef LIS2MDL_REGS_H
23 #define LIS2MDL_REGS_H
24 
25 #ifdef __cplusplus
26 extern "C" {
27 #endif
28 
29 /* Includes ------------------------------------------------------------------*/
30 #include <stdint.h>
31 #include <stddef.h>
32 #include <math.h>
33 
34 /** @addtogroup LIS2MDL
35   * @{
36   *
37   */
38 
39 /** @defgroup  Endianness definitions
40   * @{
41   *
42   */
43 
44 #ifndef DRV_BYTE_ORDER
45 #ifndef __BYTE_ORDER__
46 
47 #define DRV_LITTLE_ENDIAN 1234
48 #define DRV_BIG_ENDIAN    4321
49 
50 /** if _BYTE_ORDER is not defined, choose the endianness of your architecture
51   * by uncommenting the define which fits your platform endianness
52   */
53 //#define DRV_BYTE_ORDER    DRV_BIG_ENDIAN
54 #define DRV_BYTE_ORDER    DRV_LITTLE_ENDIAN
55 
56 #else /* defined __BYTE_ORDER__ */
57 
58 #define DRV_LITTLE_ENDIAN  __ORDER_LITTLE_ENDIAN__
59 #define DRV_BIG_ENDIAN     __ORDER_BIG_ENDIAN__
60 #define DRV_BYTE_ORDER     __BYTE_ORDER__
61 
62 #endif /* __BYTE_ORDER__*/
63 #endif /* DRV_BYTE_ORDER */
64 
65 /**
66   * @}
67   *
68   */
69 
70 /** @defgroup STMicroelectronics sensors common types
71   * @{
72   *
73   */
74 
75 #ifndef MEMS_SHARED_TYPES
76 #define MEMS_SHARED_TYPES
77 
78 typedef struct
79 {
80 #if DRV_BYTE_ORDER == DRV_LITTLE_ENDIAN
81   uint8_t bit0       : 1;
82   uint8_t bit1       : 1;
83   uint8_t bit2       : 1;
84   uint8_t bit3       : 1;
85   uint8_t bit4       : 1;
86   uint8_t bit5       : 1;
87   uint8_t bit6       : 1;
88   uint8_t bit7       : 1;
89 #elif DRV_BYTE_ORDER == DRV_BIG_ENDIAN
90   uint8_t bit7       : 1;
91   uint8_t bit6       : 1;
92   uint8_t bit5       : 1;
93   uint8_t bit4       : 1;
94   uint8_t bit3       : 1;
95   uint8_t bit2       : 1;
96   uint8_t bit1       : 1;
97   uint8_t bit0       : 1;
98 #endif /* DRV_BYTE_ORDER */
99 } bitwise_t;
100 
101 #define PROPERTY_DISABLE                (0U)
102 #define PROPERTY_ENABLE                 (1U)
103 
104 /** @addtogroup  Interfaces_Functions
105   * @brief       This section provide a set of functions used to read and
106   *              write a generic register of the device.
107   *              MANDATORY: return 0 -> no Error.
108   * @{
109   *
110   */
111 
112 typedef int32_t (*stmdev_write_ptr)(void *, uint8_t, const uint8_t *, uint16_t);
113 typedef int32_t (*stmdev_read_ptr)(void *, uint8_t, uint8_t *, uint16_t);
114 typedef void (*stmdev_mdelay_ptr)(uint32_t millisec);
115 
116 typedef struct
117 {
118   /** Component mandatory fields **/
119   stmdev_write_ptr  write_reg;
120   stmdev_read_ptr   read_reg;
121   /** Component optional fields **/
122   stmdev_mdelay_ptr   mdelay;
123   /** Customizable optional pointer **/
124   void *handle;
125 } stmdev_ctx_t;
126 
127 /**
128   * @}
129   *
130   */
131 
132 #endif /* MEMS_SHARED_TYPES */
133 
134 #ifndef MEMS_UCF_SHARED_TYPES
135 #define MEMS_UCF_SHARED_TYPES
136 
137 /** @defgroup    Generic address-data structure definition
138   * @brief       This structure is useful to load a predefined configuration
139   *              of a sensor.
140   *              You can create a sensor configuration by your own or using
141   *              Unico / Unicleo tools available on STMicroelectronics
142   *              web site.
143   *
144   * @{
145   *
146   */
147 
148 typedef struct
149 {
150   uint8_t address;
151   uint8_t data;
152 } ucf_line_t;
153 
154 /**
155   * @}
156   *
157   */
158 
159 #endif /* MEMS_UCF_SHARED_TYPES */
160 
161 /**
162   * @}
163   *
164   */
165 
166 /** @defgroup LSM9DS1_Infos
167   * @{
168   *
169   */
170 
171 /** I2C Device Address 8 bit format **/
172 #define LIS2MDL_I2C_ADD                 0x3DU
173 
174 /** Device Identification (Who am I) **/
175 #define LIS2MDL_ID                      0x40U
176 
177 /**
178   * @}
179   *
180   */
181 
182 #define LIS2MDL_OFFSET_X_REG_L          0x45U
183 #define LIS2MDL_OFFSET_X_REG_H          0x46U
184 #define LIS2MDL_OFFSET_Y_REG_L          0x47U
185 #define LIS2MDL_OFFSET_Y_REG_H          0x48U
186 #define LIS2MDL_OFFSET_Z_REG_L          0x49U
187 #define LIS2MDL_OFFSET_Z_REG_H          0x4AU
188 #define LIS2MDL_WHO_AM_I                0x4FU
189 #define LIS2MDL_CFG_REG_A               0x60U
190 typedef struct
191 {
192 #if DRV_BYTE_ORDER == DRV_LITTLE_ENDIAN
193   uint8_t md                     : 2;
194   uint8_t odr                    : 2;
195   uint8_t lp                     : 1;
196   uint8_t soft_rst               : 1;
197   uint8_t reboot                 : 1;
198   uint8_t comp_temp_en           : 1;
199 #elif DRV_BYTE_ORDER == DRV_BIG_ENDIAN
200   uint8_t comp_temp_en           : 1;
201   uint8_t reboot                 : 1;
202   uint8_t soft_rst               : 1;
203   uint8_t lp                     : 1;
204   uint8_t odr                    : 2;
205   uint8_t md                     : 2;
206 #endif /* DRV_BYTE_ORDER */
207 } lis2mdl_cfg_reg_a_t;
208 
209 #define LIS2MDL_CFG_REG_B               0x61U
210 typedef struct
211 {
212 #if DRV_BYTE_ORDER == DRV_LITTLE_ENDIAN
213   uint8_t lpf                    : 1;
214   uint8_t set_rst                : 2; /* OFF_CANC + Set_FREQ */
215   uint8_t int_on_dataoff         : 1;
216   uint8_t off_canc_one_shot      : 1;
217   uint8_t not_used_01            : 3;
218 #elif DRV_BYTE_ORDER == DRV_BIG_ENDIAN
219   uint8_t not_used_01            : 3;
220   uint8_t off_canc_one_shot      : 1;
221   uint8_t int_on_dataoff         : 1;
222   uint8_t set_rst                : 2; /* OFF_CANC + Set_FREQ */
223   uint8_t lpf                    : 1;
224 #endif /* DRV_BYTE_ORDER */
225 } lis2mdl_cfg_reg_b_t;
226 
227 #define LIS2MDL_CFG_REG_C               0x62U
228 typedef struct
229 {
230 #if DRV_BYTE_ORDER == DRV_LITTLE_ENDIAN
231   uint8_t drdy_on_pin            : 1;
232   uint8_t self_test              : 1;
233   uint8_t _4wspi                 : 1;
234   uint8_t ble                    : 1;
235   uint8_t bdu                    : 1;
236   uint8_t i2c_dis                : 1;
237   uint8_t int_on_pin             : 1;
238   uint8_t not_used_02            : 1;
239 #elif DRV_BYTE_ORDER == DRV_BIG_ENDIAN
240   uint8_t not_used_02            : 1;
241   uint8_t int_on_pin             : 1;
242   uint8_t i2c_dis                : 1;
243   uint8_t bdu                    : 1;
244   uint8_t ble                    : 1;
245   uint8_t _4wspi                 : 1;
246   uint8_t self_test              : 1;
247   uint8_t drdy_on_pin            : 1;
248 #endif /* DRV_BYTE_ORDER */
249 } lis2mdl_cfg_reg_c_t;
250 
251 #define LIS2MDL_INT_CRTL_REG            0x63U
252 typedef struct
253 {
254 #if DRV_BYTE_ORDER == DRV_LITTLE_ENDIAN
255   uint8_t ien                    : 1;
256   uint8_t iel                    : 1;
257   uint8_t iea                    : 1;
258   uint8_t not_used_01            : 2;
259   uint8_t zien                   : 1;
260   uint8_t yien                   : 1;
261   uint8_t xien                   : 1;
262 #elif DRV_BYTE_ORDER == DRV_BIG_ENDIAN
263   uint8_t xien                   : 1;
264   uint8_t yien                   : 1;
265   uint8_t zien                   : 1;
266   uint8_t not_used_01            : 2;
267   uint8_t iea                    : 1;
268   uint8_t iel                    : 1;
269   uint8_t ien                    : 1;
270 #endif /* DRV_BYTE_ORDER */
271 } lis2mdl_int_crtl_reg_t;
272 
273 #define LIS2MDL_INT_SOURCE_REG          0x64U
274 typedef struct
275 {
276 #if DRV_BYTE_ORDER == DRV_LITTLE_ENDIAN
277   uint8_t _int                   : 1;
278   uint8_t mroi                   : 1;
279   uint8_t n_th_s_z               : 1;
280   uint8_t n_th_s_y               : 1;
281   uint8_t n_th_s_x               : 1;
282   uint8_t p_th_s_z               : 1;
283   uint8_t p_th_s_y               : 1;
284   uint8_t p_th_s_x               : 1;
285 #elif DRV_BYTE_ORDER == DRV_BIG_ENDIAN
286   uint8_t p_th_s_x               : 1;
287   uint8_t p_th_s_y               : 1;
288   uint8_t p_th_s_z               : 1;
289   uint8_t n_th_s_x               : 1;
290   uint8_t n_th_s_y               : 1;
291   uint8_t n_th_s_z               : 1;
292   uint8_t mroi                   : 1;
293   uint8_t _int                   : 1;
294 #endif /* DRV_BYTE_ORDER */
295 } lis2mdl_int_source_reg_t;
296 
297 #define LIS2MDL_INT_THS_L_REG           0x65U
298 #define LIS2MDL_INT_THS_H_REG           0x66U
299 #define LIS2MDL_STATUS_REG              0x67U
300 typedef struct
301 {
302 #if DRV_BYTE_ORDER == DRV_LITTLE_ENDIAN
303   uint8_t xda                    : 1;
304   uint8_t yda                    : 1;
305   uint8_t zda                    : 1;
306   uint8_t zyxda                  : 1;
307   uint8_t _xor                   : 1;
308   uint8_t yor                    : 1;
309   uint8_t zor                    : 1;
310   uint8_t zyxor                  : 1;
311 #elif DRV_BYTE_ORDER == DRV_BIG_ENDIAN
312   uint8_t zyxor                  : 1;
313   uint8_t zor                    : 1;
314   uint8_t yor                    : 1;
315   uint8_t _xor                   : 1;
316   uint8_t zyxda                  : 1;
317   uint8_t zda                    : 1;
318   uint8_t yda                    : 1;
319   uint8_t xda                    : 1;
320 #endif /* DRV_BYTE_ORDER */
321 } lis2mdl_status_reg_t;
322 
323 #define LIS2MDL_OUTX_L_REG              0x68U
324 #define LIS2MDL_OUTX_H_REG              0x69U
325 #define LIS2MDL_OUTY_L_REG              0x6AU
326 #define LIS2MDL_OUTY_H_REG              0x6BU
327 #define LIS2MDL_OUTZ_L_REG              0x6CU
328 #define LIS2MDL_OUTZ_H_REG              0x6DU
329 #define LIS2MDL_TEMP_OUT_L_REG          0x6EU
330 #define LIS2MDL_TEMP_OUT_H_REG          0x6FU
331 
332 /**
333   * @defgroup LIS2MDL_Register_Union
334   * @brief    This union group all the registers having a bit-field
335   *           description.
336   *           This union is useful but it's not needed by the driver.
337   *
338   *           REMOVING this union you are compliant with:
339   *           MISRA-C 2012 [Rule 19.2] -> " Union are not allowed "
340   *
341   * @{
342   *
343   */
344 typedef union
345 {
346   lis2mdl_cfg_reg_a_t            cfg_reg_a;
347   lis2mdl_cfg_reg_b_t            cfg_reg_b;
348   lis2mdl_cfg_reg_c_t            cfg_reg_c;
349   lis2mdl_int_crtl_reg_t         int_crtl_reg;
350   lis2mdl_int_source_reg_t       int_source_reg;
351   lis2mdl_status_reg_t           status_reg;
352   bitwise_t                      bitwise;
353   uint8_t                        byte;
354 } lis2mdl_reg_t;
355 
356 /**
357   * @}
358   *
359   */
360 
361 #ifndef __weak
362 #define __weak __attribute__((weak))
363 #endif /* __weak */
364 
365 /*
366  * These are the basic platform dependent I/O routines to read
367  * and write device registers connected on a standard bus.
368  * The driver keeps offering a default implementation based on function
369  * pointers to read/write routines for backward compatibility.
370  * The __weak directive allows the final application to overwrite
371  * them with a custom implementation.
372  */
373 
374 int32_t lis2mdl_read_reg(stmdev_ctx_t *ctx, uint8_t reg,
375                          uint8_t *data,
376                          uint16_t len);
377 int32_t lis2mdl_write_reg(stmdev_ctx_t *ctx, uint8_t reg,
378                           uint8_t *data,
379                           uint16_t len);
380 
381 float_t lis2mdl_from_lsb_to_mgauss(int16_t lsb);
382 
383 float_t lis2mdl_from_lsb_to_celsius(int16_t lsb);
384 
385 int32_t lis2mdl_mag_user_offset_set(stmdev_ctx_t *ctx, int16_t *val);
386 int32_t lis2mdl_mag_user_offset_get(stmdev_ctx_t *ctx, int16_t *val);
387 
388 typedef enum
389 {
390   LIS2MDL_CONTINUOUS_MODE  = 0,
391   LIS2MDL_SINGLE_TRIGGER   = 1,
392   LIS2MDL_POWER_DOWN       = 2,
393 } lis2mdl_md_t;
394 int32_t lis2mdl_operating_mode_set(stmdev_ctx_t *ctx,
395                                    lis2mdl_md_t val);
396 int32_t lis2mdl_operating_mode_get(stmdev_ctx_t *ctx,
397                                    lis2mdl_md_t *val);
398 
399 typedef enum
400 {
401   LIS2MDL_ODR_10Hz   = 0,
402   LIS2MDL_ODR_20Hz   = 1,
403   LIS2MDL_ODR_50Hz   = 2,
404   LIS2MDL_ODR_100Hz  = 3,
405 } lis2mdl_odr_t;
406 int32_t lis2mdl_data_rate_set(stmdev_ctx_t *ctx, lis2mdl_odr_t val);
407 int32_t lis2mdl_data_rate_get(stmdev_ctx_t *ctx, lis2mdl_odr_t *val);
408 
409 typedef enum
410 {
411   LIS2MDL_HIGH_RESOLUTION  = 0,
412   LIS2MDL_LOW_POWER        = 1,
413 } lis2mdl_lp_t;
414 int32_t lis2mdl_power_mode_set(stmdev_ctx_t *ctx, lis2mdl_lp_t val);
415 int32_t lis2mdl_power_mode_get(stmdev_ctx_t *ctx, lis2mdl_lp_t *val);
416 
417 int32_t lis2mdl_offset_temp_comp_set(stmdev_ctx_t *ctx, uint8_t val);
418 int32_t lis2mdl_offset_temp_comp_get(stmdev_ctx_t *ctx, uint8_t *val);
419 
420 typedef enum
421 {
422   LIS2MDL_ODR_DIV_2  = 0,
423   LIS2MDL_ODR_DIV_4  = 1,
424 } lis2mdl_lpf_t;
425 int32_t lis2mdl_low_pass_bandwidth_set(stmdev_ctx_t *ctx,
426                                        lis2mdl_lpf_t val);
427 int32_t lis2mdl_low_pass_bandwidth_get(stmdev_ctx_t *ctx,
428                                        lis2mdl_lpf_t *val);
429 
430 typedef enum
431 {
432   LIS2MDL_SET_SENS_ODR_DIV_63        = 0,
433   LIS2MDL_SENS_OFF_CANC_EVERY_ODR    = 1,
434   LIS2MDL_SET_SENS_ONLY_AT_POWER_ON  = 2,
435 } lis2mdl_set_rst_t;
436 int32_t lis2mdl_set_rst_mode_set(stmdev_ctx_t *ctx,
437                                  lis2mdl_set_rst_t val);
438 int32_t lis2mdl_set_rst_mode_get(stmdev_ctx_t *ctx,
439                                  lis2mdl_set_rst_t *val);
440 
441 int32_t lis2mdl_set_rst_sensor_single_set(stmdev_ctx_t *ctx,
442                                           uint8_t val);
443 int32_t lis2mdl_set_rst_sensor_single_get(stmdev_ctx_t *ctx,
444                                           uint8_t *val);
445 
446 int32_t lis2mdl_block_data_update_set(stmdev_ctx_t *ctx, uint8_t val);
447 int32_t lis2mdl_block_data_update_get(stmdev_ctx_t *ctx,
448                                       uint8_t *val);
449 
450 int32_t lis2mdl_mag_data_ready_get(stmdev_ctx_t *ctx, uint8_t *val);
451 
452 int32_t lis2mdl_mag_data_ovr_get(stmdev_ctx_t *ctx, uint8_t *val);
453 
454 int32_t lis2mdl_magnetic_raw_get(stmdev_ctx_t *ctx, int16_t *val);
455 
456 int32_t lis2mdl_temperature_raw_get(stmdev_ctx_t *ctx,  int16_t *val);
457 
458 int32_t lis2mdl_device_id_get(stmdev_ctx_t *ctx, uint8_t *buff);
459 
460 int32_t lis2mdl_reset_set(stmdev_ctx_t *ctx, uint8_t val);
461 int32_t lis2mdl_reset_get(stmdev_ctx_t *ctx, uint8_t *val);
462 
463 int32_t lis2mdl_boot_set(stmdev_ctx_t *ctx, uint8_t val);
464 int32_t lis2mdl_boot_get(stmdev_ctx_t *ctx, uint8_t *val);
465 
466 int32_t lis2mdl_self_test_set(stmdev_ctx_t *ctx, uint8_t val);
467 int32_t lis2mdl_self_test_get(stmdev_ctx_t *ctx, uint8_t *val);
468 
469 typedef enum
470 {
471   LIS2MDL_LSB_AT_LOW_ADD  = 0,
472   LIS2MDL_MSB_AT_LOW_ADD  = 1,
473 } lis2mdl_ble_t;
474 int32_t lis2mdl_data_format_set(stmdev_ctx_t *ctx, lis2mdl_ble_t val);
475 int32_t lis2mdl_data_format_get(stmdev_ctx_t *ctx,
476                                 lis2mdl_ble_t *val);
477 
478 int32_t lis2mdl_status_get(stmdev_ctx_t *ctx,
479                            lis2mdl_status_reg_t *val);
480 
481 typedef enum
482 {
483   LIS2MDL_CHECK_BEFORE  = 0,
484   LIS2MDL_CHECK_AFTER   = 1,
485 } lis2mdl_int_on_dataoff_t;
486 int32_t lis2mdl_offset_int_conf_set(stmdev_ctx_t *ctx,
487                                     lis2mdl_int_on_dataoff_t val);
488 int32_t lis2mdl_offset_int_conf_get(stmdev_ctx_t *ctx,
489                                     lis2mdl_int_on_dataoff_t *val);
490 
491 int32_t lis2mdl_drdy_on_pin_set(stmdev_ctx_t *ctx, uint8_t val);
492 int32_t lis2mdl_drdy_on_pin_get(stmdev_ctx_t *ctx, uint8_t *val);
493 
494 int32_t lis2mdl_int_on_pin_set(stmdev_ctx_t *ctx, uint8_t val);
495 int32_t lis2mdl_int_on_pin_get(stmdev_ctx_t *ctx, uint8_t *val);
496 
497 int32_t lis2mdl_int_gen_conf_set(stmdev_ctx_t *ctx,
498                                  lis2mdl_int_crtl_reg_t *val);
499 int32_t lis2mdl_int_gen_conf_get(stmdev_ctx_t *ctx,
500                                  lis2mdl_int_crtl_reg_t *val);
501 
502 int32_t lis2mdl_int_gen_source_get(stmdev_ctx_t *ctx,
503                                    lis2mdl_int_source_reg_t *val);
504 
505 int32_t lis2mdl_int_gen_treshold_set(stmdev_ctx_t *ctx, uint16_t val);
506 int32_t lis2mdl_int_gen_treshold_get(stmdev_ctx_t *ctx,
507                                      uint16_t *val);
508 
509 typedef enum
510 {
511   LIS2MDL_SPI_4_WIRE   = 1,
512   LIS2MDL_SPI_3_WIRE   = 0,
513 } lis2mdl_sim_t;
514 int32_t lis2mdl_spi_mode_set(stmdev_ctx_t *ctx, lis2mdl_sim_t val);
515 int32_t lis2mdl_spi_mode_get(stmdev_ctx_t *ctx, lis2mdl_sim_t *val);
516 
517 typedef enum
518 {
519   LIS2MDL_I2C_ENABLE   = 0,
520   LIS2MDL_I2C_DISABLE  = 1,
521 } lis2mdl_i2c_dis_t;
522 int32_t lis2mdl_i2c_interface_set(stmdev_ctx_t *ctx,
523                                   lis2mdl_i2c_dis_t val);
524 int32_t lis2mdl_i2c_interface_get(stmdev_ctx_t *ctx,
525                                   lis2mdl_i2c_dis_t *val);
526 
527 /**
528   *@}
529   *
530   */
531 
532 #ifdef __cplusplus
533 }
534 #endif
535 
536 #endif /* LIS2MDL_REGS_H */
537 
538 /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/
539