1 /*
2  * Copyright 2020 Google LLC
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  *
6  * Emulator for the Bosch BMI160 accelerometer / gyro. This supports basic
7  * init and reading of canned samples. It supports both I2C and SPI buses.
8  */
9 
10 #define DT_DRV_COMPAT bosch_bmi160
11 
12 #define LOG_LEVEL CONFIG_SPI_LOG_LEVEL
13 #include <zephyr/logging/log.h>
14 LOG_MODULE_REGISTER(bosch_bmi160);
15 
16 #include <zephyr/sys/byteorder.h>
17 #include <bmi160.h>
18 #include <zephyr/device.h>
19 #include <zephyr/drivers/emul.h>
20 #include <zephyr/drivers/emul_sensor.h>
21 #include <zephyr/drivers/i2c.h>
22 #include <zephyr/drivers/i2c_emul.h>
23 #include <zephyr/drivers/spi.h>
24 #include <zephyr/drivers/spi_emul.h>
25 #include <zephyr/sys/util.h>
26 
27 /** Run-time data used by the emulator */
28 struct bmi160_emul_data {
29 	uint8_t pmu_status;
30 	/** Current register to read (address) */
31 	uint32_t cur_reg;
32 };
33 
34 /** Static configuration for the emulator */
35 struct bmi160_emul_cfg {
36 	/** Chip registers */
37 	uint8_t *reg;
38 	union {
39 		/** Unit address (chip select ordinal) of emulator */
40 		uint16_t chipsel;
41 		/** I2C address of emulator */
42 		uint16_t addr;
43 	};
44 };
45 
46 /* Names for the PMU components */
47 static const char *const pmu_name[] = {"acc", "gyr", "mag", "INV"};
48 
emul_bmi160_get_reg_value(const struct emul * target,int reg_number,uint8_t * out,size_t count)49 int emul_bmi160_get_reg_value(const struct emul *target, int reg_number, uint8_t *out, size_t count)
50 {
51 	const struct bmi160_emul_cfg *cfg = target->cfg;
52 
53 	if (reg_number < 0 || reg_number + count > BMI160_REG_COUNT) {
54 		return -EINVAL;
55 	}
56 
57 	memcpy(out, cfg->reg + reg_number, count);
58 	return 0;
59 }
60 
reg_write(const struct emul * target,int regn,int val)61 static void reg_write(const struct emul *target, int regn, int val)
62 {
63 	struct bmi160_emul_data *data = target->data;
64 	const struct bmi160_emul_cfg *cfg = target->cfg;
65 
66 	LOG_DBG("write %x = %x", regn, val);
67 	cfg->reg[regn] = val;
68 	switch (regn) {
69 	case BMI160_REG_ACC_CONF:
70 		LOG_DBG("   * acc conf");
71 		break;
72 	case BMI160_REG_ACC_RANGE:
73 		LOG_DBG("   * acc range");
74 		break;
75 	case BMI160_REG_GYR_CONF:
76 		LOG_DBG("   * gyr conf");
77 		break;
78 	case BMI160_REG_GYR_RANGE:
79 		LOG_DBG("   * gyr range");
80 		break;
81 	case BMI160_REG_CMD:
82 		switch (val) {
83 		case BMI160_CMD_SOFT_RESET:
84 			LOG_DBG("   * soft reset");
85 			break;
86 		default:
87 			if ((val & BMI160_CMD_PMU_BIT) == BMI160_CMD_PMU_BIT) {
88 				int which = (val & BMI160_CMD_PMU_MASK) >> BMI160_CMD_PMU_SHIFT;
89 				int shift;
90 				int pmu_val = val & BMI160_CMD_PMU_VAL_MASK;
91 
92 				switch (which) {
93 				case 0:
94 					shift = BMI160_PMU_STATUS_ACC_POS;
95 					break;
96 				case 1:
97 					shift = BMI160_PMU_STATUS_GYR_POS;
98 					break;
99 				case 2:
100 				default:
101 					shift = BMI160_PMU_STATUS_MAG_POS;
102 					break;
103 				}
104 				data->pmu_status &= 3 << shift;
105 				data->pmu_status |= pmu_val << shift;
106 				LOG_DBG("   * pmu %s = %x, new status %x", pmu_name[which], pmu_val,
107 					data->pmu_status);
108 			} else {
109 				LOG_DBG("Unknown command %x", val);
110 			}
111 			break;
112 		}
113 		break;
114 	default:
115 		LOG_DBG("Unknown write %x", regn);
116 	}
117 }
118 
reg_read(const struct emul * target,int regn)119 static int reg_read(const struct emul *target, int regn)
120 {
121 	struct bmi160_emul_data *data = target->data;
122 	const struct bmi160_emul_cfg *cfg = target->cfg;
123 	int val;
124 
125 	LOG_DBG("read %x =", regn);
126 	val = cfg->reg[regn];
127 	switch (regn) {
128 	case BMI160_REG_CHIPID:
129 		LOG_DBG("   * get chipid");
130 		break;
131 	case BMI160_REG_PMU_STATUS:
132 		LOG_DBG("   * get pmu");
133 		val = data->pmu_status;
134 		break;
135 	case BMI160_REG_STATUS:
136 		LOG_DBG("   * status");
137 		val |= BMI160_DATA_READY_BIT_MASK;
138 		break;
139 	case BMI160_REG_ACC_CONF:
140 		LOG_DBG("   * acc conf");
141 		break;
142 	case BMI160_REG_GYR_CONF:
143 		LOG_DBG("   * gyr conf");
144 		break;
145 	case BMI160_SPI_START:
146 		LOG_DBG("   * Bus start");
147 		break;
148 	case BMI160_REG_ACC_RANGE:
149 		LOG_DBG("   * acc range");
150 		break;
151 	case BMI160_REG_GYR_RANGE:
152 		LOG_DBG("   * gyr range");
153 		break;
154 	default:
155 		LOG_DBG("Unknown read %x", regn);
156 	}
157 	LOG_DBG("       = %x", val);
158 
159 	return val;
160 }
161 
162 #if BMI160_BUS_SPI
bmi160_emul_io_spi(const struct emul * target,const struct spi_config * config,const struct spi_buf_set * tx_bufs,const struct spi_buf_set * rx_bufs)163 static int bmi160_emul_io_spi(const struct emul *target, const struct spi_config *config,
164 			      const struct spi_buf_set *tx_bufs, const struct spi_buf_set *rx_bufs)
165 {
166 	struct bmi160_emul_data *data;
167 	const struct spi_buf *tx, *txd, *rxd;
168 	unsigned int regn, val;
169 	int count;
170 
171 	ARG_UNUSED(config);
172 
173 	data = target->data;
174 
175 	__ASSERT_NO_MSG(tx_bufs || rx_bufs);
176 	__ASSERT_NO_MSG(!tx_bufs || !rx_bufs || tx_bufs->count == rx_bufs->count);
177 	count = tx_bufs ? tx_bufs->count : rx_bufs->count;
178 
179 	if (count != 2) {
180 		LOG_DBG("Unknown tx_bufs->count %d", count);
181 		return -EIO;
182 	}
183 	tx = tx_bufs ? tx_bufs->buffers : NULL;
184 	txd = tx_bufs ? &tx_bufs->buffers[1] : NULL;
185 	rxd = rx_bufs ? &rx_bufs->buffers[1] : NULL;
186 
187 	if (tx == NULL) {
188 		LOG_DBG("tx cannot be NULL");
189 		return -EIO;
190 	}
191 
192 	if (tx->len != 1) {
193 		LOG_DBG("Unknown tx->len %d", tx->len);
194 		return -EIO;
195 	}
196 
197 	regn = *(uint8_t *)tx->buf;
198 	if ((regn & BMI160_REG_READ) && rxd == NULL) {
199 		LOG_ERR("Cannot read without rxd");
200 		return -EPERM;
201 	}
202 
203 	if (txd->len == 1) {
204 		if (regn & BMI160_REG_READ) {
205 			regn &= BMI160_REG_MASK;
206 			val = reg_read(target, regn);
207 			*(uint8_t *)rxd->buf = val;
208 		} else {
209 			val = *(uint8_t *)txd->buf;
210 			reg_write(target, regn, val);
211 		}
212 	} else {
213 		if (regn & BMI160_REG_READ) {
214 			regn &= BMI160_REG_MASK;
215 			for (int i = 0; i < txd->len; ++i) {
216 				((uint8_t *)rxd->buf)[i] = reg_read(target, regn + i);
217 			}
218 		} else {
219 			LOG_ERR("Unknown sample write");
220 			return -EIO;
221 		}
222 	}
223 
224 	return 0;
225 }
226 #endif
227 
228 #if BMI160_BUS_I2C
bmi160_emul_transfer_i2c(const struct emul * target,struct i2c_msg * msgs,int num_msgs,int addr)229 static int bmi160_emul_transfer_i2c(const struct emul *target, struct i2c_msg *msgs, int num_msgs,
230 				    int addr)
231 {
232 	struct bmi160_emul_data *data;
233 
234 	data = target->data;
235 
236 	__ASSERT_NO_MSG(msgs && num_msgs);
237 
238 	i2c_dump_msgs_rw(target->dev, msgs, num_msgs, addr, false);
239 	switch (num_msgs) {
240 	case 2:
241 		if (msgs->flags & I2C_MSG_READ) {
242 			LOG_ERR("Unexpected read");
243 			return -EIO;
244 		}
245 		if (msgs->len != 1) {
246 			LOG_ERR("Unexpected msg0 length %d", msgs->len);
247 			return -EIO;
248 		}
249 		data->cur_reg = msgs->buf[0];
250 
251 		/* Now process the 'read' part of the message */
252 		msgs++;
253 		if (msgs->flags & I2C_MSG_READ) {
254 			for (int i = 0; i < msgs->len; ++i) {
255 				msgs->buf[i] = reg_read(target, data->cur_reg + i);
256 			}
257 		} else {
258 			if (msgs->len != 1) {
259 				LOG_ERR("Unexpected msg1 length %d", msgs->len);
260 			}
261 			reg_write(target, data->cur_reg, msgs->buf[0]);
262 		}
263 		break;
264 	default:
265 		LOG_ERR("Invalid number of messages: %d", num_msgs);
266 		return -EIO;
267 	}
268 
269 	return 0;
270 }
271 #endif
272 
273 /* Device instantiation */
274 
275 #if BMI160_BUS_SPI
276 static struct spi_emul_api bmi160_emul_api_spi = {
277 	.io = bmi160_emul_io_spi,
278 };
279 #endif
280 
281 #if BMI160_BUS_I2C
282 static struct i2c_emul_api bmi160_emul_api_i2c = {
283 	.transfer = bmi160_emul_transfer_i2c,
284 };
285 #endif
286 
bmi160_emul_backend_set_channel(const struct emul * target,struct sensor_chan_spec ch,const q31_t * value,int8_t shift)287 static int bmi160_emul_backend_set_channel(const struct emul *target, struct sensor_chan_spec ch,
288 					   const q31_t *value, int8_t shift)
289 {
290 	const struct bmi160_emul_cfg *cfg = target->cfg;
291 	int64_t intermediate = *value;
292 	q31_t scale;
293 	int8_t scale_shift = 0;
294 	int reg_lsb;
295 
296 	switch (ch.chan_type) {
297 	case SENSOR_CHAN_ACCEL_X:
298 	case SENSOR_CHAN_ACCEL_Y:
299 	case SENSOR_CHAN_ACCEL_Z:
300 		reg_lsb = BMI160_REG_DATA_ACC_X + (ch.chan_type - SENSOR_CHAN_ACCEL_X) * 2;
301 		scale = 0x4e7404ea;
302 
303 		switch (FIELD_GET(GENMASK(3, 0), cfg->reg[BMI160_REG_ACC_RANGE])) {
304 		case BMI160_ACC_RANGE_4G:
305 			scale_shift = 6;
306 			break;
307 		case BMI160_ACC_RANGE_8G:
308 			scale_shift = 7;
309 			break;
310 		case BMI160_ACC_RANGE_16G:
311 			scale_shift = 8;
312 			break;
313 		default:
314 			scale_shift = 5;
315 			break;
316 		}
317 		break;
318 	case SENSOR_CHAN_GYRO_X:
319 	case SENSOR_CHAN_GYRO_Y:
320 	case SENSOR_CHAN_GYRO_Z:
321 		reg_lsb = BMI160_REG_DATA_GYR_X + (ch.chan_type - SENSOR_CHAN_GYRO_X) * 2;
322 		scale = 0x45d02bea;
323 
324 		switch (FIELD_GET(GENMASK(2, 0), cfg->reg[BMI160_REG_GYR_RANGE])) {
325 		case BMI160_GYR_RANGE_2000DPS:
326 			scale_shift = 6;
327 			break;
328 		case BMI160_GYR_RANGE_1000DPS:
329 			scale_shift = 5;
330 			break;
331 		case BMI160_GYR_RANGE_500DPS:
332 			scale_shift = 4;
333 			break;
334 		case BMI160_GYR_RANGE_250DPS:
335 			scale_shift = 3;
336 			break;
337 		case BMI160_GYR_RANGE_125DPS:
338 			scale_shift = 2;
339 			break;
340 		default:
341 			return -EINVAL;
342 		}
343 		break;
344 	case SENSOR_CHAN_DIE_TEMP:
345 		reg_lsb = BMI160_REG_TEMPERATURE0;
346 		scale = 0x8000;
347 		scale_shift = 7;
348 		break;
349 	default:
350 		return -EINVAL;
351 	}
352 
353 	if (shift < scale_shift) {
354 		/* Original value doesn't have enough int bits, fix it */
355 		intermediate >>= scale_shift - shift;
356 	} else if (shift > 0 && shift > scale_shift) {
357 		/* Original value might be out-of-bounds, fix it (we're going to lose precision) */
358 		intermediate <<= shift - scale_shift;
359 	}
360 
361 	if (ch.chan_type == SENSOR_CHAN_DIE_TEMP) {
362 		/* Need to subtract 23C */
363 		intermediate -= INT64_C(23) << (31 - scale_shift);
364 	}
365 
366 	intermediate =
367 		CLAMP(DIV_ROUND_CLOSEST(intermediate * INT16_MAX, scale), INT16_MIN, INT16_MAX);
368 
369 	cfg->reg[reg_lsb] = FIELD_GET(GENMASK64(7, 0), intermediate);
370 	cfg->reg[reg_lsb + 1] = FIELD_GET(GENMASK64(15, 8), intermediate);
371 	return 0;
372 }
373 
bmi160_emul_backend_get_sample_range(const struct emul * target,struct sensor_chan_spec ch,q31_t * lower,q31_t * upper,q31_t * epsilon,int8_t * shift)374 static int bmi160_emul_backend_get_sample_range(const struct emul *target,
375 						struct sensor_chan_spec ch, q31_t *lower,
376 						q31_t *upper, q31_t *epsilon, int8_t *shift)
377 {
378 	const struct bmi160_emul_cfg *cfg = target->cfg;
379 
380 	switch (ch.chan_type) {
381 	case SENSOR_CHAN_ACCEL_X:
382 	case SENSOR_CHAN_ACCEL_Y:
383 	case SENSOR_CHAN_ACCEL_Z:
384 	case SENSOR_CHAN_ACCEL_XYZ: {
385 		uint8_t acc_range = cfg->reg[BMI160_REG_ACC_RANGE];
386 
387 		switch (acc_range) {
388 		case BMI160_ACC_RANGE_2G:
389 			*shift = 5;
390 			break;
391 		case BMI160_ACC_RANGE_4G:
392 			*shift = 6;
393 			break;
394 		case BMI160_ACC_RANGE_8G:
395 			*shift = 7;
396 			break;
397 		case BMI160_ACC_RANGE_16G:
398 			*shift = 8;
399 			break;
400 		default:
401 			return -EINVAL;
402 		}
403 		int64_t intermediate = ((int64_t)(2 * 9.80665 * INT32_MAX)) >> 5;
404 
405 		*upper = intermediate;
406 		*lower = -(*upper);
407 		*epsilon = intermediate * 2 / (1 << (16 - *shift));
408 		return 0;
409 	}
410 	case SENSOR_CHAN_GYRO_X:
411 	case SENSOR_CHAN_GYRO_Y:
412 	case SENSOR_CHAN_GYRO_Z:
413 	case SENSOR_CHAN_GYRO_XYZ: {
414 		uint8_t gyro_range = cfg->reg[BMI160_REG_GYR_RANGE];
415 
416 		switch (gyro_range) {
417 		case BMI160_GYR_RANGE_125DPS:
418 			*shift = 2;
419 			break;
420 		case BMI160_GYR_RANGE_250DPS:
421 			*shift = 3;
422 			break;
423 		case BMI160_GYR_RANGE_500DPS:
424 			*shift = 4;
425 			break;
426 		case BMI160_GYR_RANGE_1000DPS:
427 			*shift = 5;
428 			break;
429 		case BMI160_GYR_RANGE_2000DPS:
430 			*shift = 6;
431 			break;
432 		default:
433 			return -EINVAL;
434 		}
435 
436 		int64_t intermediate = (int64_t)(125 * 3.141592654 * INT32_MAX / 180) >> 2;
437 
438 		*upper = intermediate;
439 		*lower = -(*upper);
440 		*epsilon = intermediate * 2 / (1 << (16 - *shift));
441 		return 0;
442 	}
443 	default:
444 		return -EINVAL;
445 	}
446 }
447 
bmi160_emul_backend_set_offset(const struct emul * target,struct sensor_chan_spec ch,const q31_t * values,int8_t shift)448 static int bmi160_emul_backend_set_offset(const struct emul *target, struct sensor_chan_spec ch,
449 					  const q31_t *values, int8_t shift)
450 {
451 	if (ch.chan_type != SENSOR_CHAN_ACCEL_XYZ && ch.chan_type != SENSOR_CHAN_GYRO_XYZ) {
452 		return -EINVAL;
453 	}
454 
455 	const struct bmi160_emul_cfg *cfg = target->cfg;
456 	q31_t scale;
457 	int8_t scale_shift = 0;
458 
459 	if (values[0] == 0 && values[1] == 0 && values[2] == 0) {
460 		if (ch.chan_type == SENSOR_CHAN_ACCEL_XYZ) {
461 			cfg->reg[BMI160_REG_OFFSET_EN] &= ~BIT(BMI160_ACC_OFS_EN_POS);
462 		} else {
463 			cfg->reg[BMI160_REG_OFFSET_EN] &= ~BIT(BMI160_GYR_OFS_EN_POS);
464 		}
465 	} else {
466 		if (ch.chan_type == SENSOR_CHAN_ACCEL_XYZ) {
467 			cfg->reg[BMI160_REG_OFFSET_EN] |= BIT(BMI160_ACC_OFS_EN_POS);
468 		} else {
469 			cfg->reg[BMI160_REG_OFFSET_EN] |= BIT(BMI160_GYR_OFS_EN_POS);
470 		}
471 	}
472 
473 	if (ch.chan_type == SENSOR_CHAN_ACCEL_XYZ) {
474 		/*
475 		 * bits = (values[i]mps2 / 9.80665g/mps2) / 0.0039g
476 		 *      = values[i] / 0.038245935mps2/bit
477 		 * 0.038245935 in Q31 format is 0x4e53e28 with shift 0
478 		 */
479 		scale = 0x4e53e28;
480 	} else {
481 		/*
482 		 * bits = (values[i]rad/s * 180 / pi) / 0.061deg/s
483 		 *      = values[i] / 0.001064651rad/s
484 		 */
485 		scale = 0x22e2f0;
486 	}
487 
488 	for (int i = 0; i < 3; ++i) {
489 		int64_t intermediate = values[i];
490 
491 		if (shift > scale_shift) {
492 			/* Input uses a bigger scale, we need to increase its value to match */
493 			intermediate <<= (shift - scale_shift);
494 		} else if (shift < scale_shift) {
495 			/* Scale uses a bigger shift, we need to decrease its value to match */
496 			scale >>= (scale_shift - shift);
497 		}
498 
499 		int64_t reg_value = intermediate / scale;
500 
501 		__ASSERT_NO_MSG(ch.chan_type != SENSOR_CHAN_ACCEL_XYZ ||
502 				(reg_value >= INT8_MIN && reg_value <= INT8_MAX));
503 		__ASSERT_NO_MSG(ch.chan_type != SENSOR_CHAN_GYRO_XYZ ||
504 				(reg_value >= -0x1ff - 1 && reg_value <= 0x1ff));
505 		if (ch.chan_type == SENSOR_CHAN_ACCEL_XYZ) {
506 			cfg->reg[BMI160_REG_OFFSET_ACC_X + i] = reg_value & 0xff;
507 		} else {
508 			cfg->reg[BMI160_REG_OFFSET_GYR_X + i] = reg_value & 0xff;
509 			cfg->reg[BMI160_REG_OFFSET_EN] =
510 				(cfg->reg[BMI160_REG_OFFSET_EN] & ~GENMASK(i * 2 + 1, i * 2)) |
511 				(reg_value & GENMASK(9, 8));
512 		}
513 	}
514 
515 	return 0;
516 }
517 
bmi160_emul_backend_set_attribute(const struct emul * target,struct sensor_chan_spec ch,enum sensor_attribute attribute,const void * value)518 static int bmi160_emul_backend_set_attribute(const struct emul *target, struct sensor_chan_spec ch,
519 					     enum sensor_attribute attribute, const void *value)
520 {
521 	if (attribute == SENSOR_ATTR_OFFSET &&
522 	    (ch.chan_type == SENSOR_CHAN_ACCEL_XYZ || ch.chan_type == SENSOR_CHAN_GYRO_XYZ)) {
523 		const struct sensor_three_axis_attribute *attribute_value = value;
524 
525 		return bmi160_emul_backend_set_offset(target, ch, attribute_value->values,
526 						      attribute_value->shift);
527 	}
528 	return -EINVAL;
529 }
530 
bmi160_emul_backend_get_attribute_metadata(const struct emul * target,struct sensor_chan_spec ch,enum sensor_attribute attribute,q31_t * min,q31_t * max,q31_t * increment,int8_t * shift)531 static int bmi160_emul_backend_get_attribute_metadata(const struct emul *target,
532 						      struct sensor_chan_spec ch,
533 						      enum sensor_attribute attribute, q31_t *min,
534 						      q31_t *max, q31_t *increment, int8_t *shift)
535 {
536 	ARG_UNUSED(target);
537 	switch (ch.chan_type) {
538 	case SENSOR_CHAN_ACCEL_X:
539 	case SENSOR_CHAN_ACCEL_Y:
540 	case SENSOR_CHAN_ACCEL_Z:
541 	case SENSOR_CHAN_ACCEL_XYZ:
542 		if (attribute == SENSOR_ATTR_OFFSET) {
543 			/* Offset uses 3.9mg per bit in an 8 bit register:
544 			 *   0.0039g * 9.8065m/s2: yields the increment in SI units
545 			 *   * INT8_MIN (or MAX) : yields the minimum (or maximum) values
546 			 *   * INT32_MAX >> 3    : converts to q31 format within range [-8, 8]
547 			 */
548 			*min = (q31_t)((int64_t)(0.0039 * 9.8065 * INT8_MIN * INT32_MAX) >> 3);
549 			*max = (q31_t)((int64_t)(0.0039 * 9.8065 * INT8_MAX * INT32_MAX) >> 3);
550 			*increment = (q31_t)((int64_t)(0.0039 * 9.8065 * INT32_MAX) >> 3);
551 			*shift = 3;
552 			return 0;
553 		}
554 		return -EINVAL;
555 	case SENSOR_CHAN_GYRO_X:
556 	case SENSOR_CHAN_GYRO_Y:
557 	case SENSOR_CHAN_GYRO_Z:
558 	case SENSOR_CHAN_GYRO_XYZ:
559 		if (attribute == SENSOR_ATTR_OFFSET) {
560 			/* Offset uses 0.061deg/s per bit in an 10 bit register:
561 			 *   0.061deg/s * pi / 180: yields the increment in SI units
562 			 *   * INT10_MIN (or MAX) : yields the minimum (or maximum) values
563 			 *   * INT32_MAX          : converts to q31 format within range [-1, 1]
564 			 */
565 			*min = (q31_t)(0.061 * 3.141593 / 180.0 * -512 * INT32_MAX);
566 			*max = (q31_t)(0.061 * 3.141593 / 180.0 * 511 * INT32_MAX);
567 			*increment = (q31_t)(0.061 * 3.141593 / 180.0 * INT32_MAX);
568 			*shift = 0;
569 			return 0;
570 		}
571 		return -EINVAL;
572 	default:
573 		return -EINVAL;
574 	}
575 }
576 
577 static const struct emul_sensor_driver_api backend_api = {
578 	.set_channel = bmi160_emul_backend_set_channel,
579 	.get_sample_range = bmi160_emul_backend_get_sample_range,
580 	.set_attribute = bmi160_emul_backend_set_attribute,
581 	.get_attribute_metadata = bmi160_emul_backend_get_attribute_metadata,
582 };
583 
emul_bosch_bmi160_init(const struct emul * target,const struct device * parent)584 static int emul_bosch_bmi160_init(const struct emul *target, const struct device *parent)
585 {
586 	const struct bmi160_emul_cfg *cfg = target->cfg;
587 	struct bmi160_emul_data *data = target->data;
588 	uint8_t *reg = cfg->reg;
589 
590 	ARG_UNUSED(parent);
591 
592 	data->pmu_status = 0;
593 
594 	reg[BMI160_REG_CHIPID] = BMI160_CHIP_ID;
595 
596 	return 0;
597 }
598 
599 #define BMI160_EMUL_DATA(n)                                                                        \
600 	static uint8_t bmi160_emul_reg_##n[BMI160_REG_COUNT];                                      \
601 	static struct bmi160_emul_data bmi160_emul_data_##n;
602 
603 #define BMI160_EMUL_DEFINE(n, bus_api)                                                             \
604 	EMUL_DT_INST_DEFINE(n, emul_bosch_bmi160_init, &bmi160_emul_data_##n,                      \
605 			    &bmi160_emul_cfg_##n, &bus_api, &backend_api)
606 
607 /* Instantiation macros used when a device is on a SPI bus */
608 #define BMI160_EMUL_SPI(n)                                                                         \
609 	BMI160_EMUL_DATA(n)                                                                        \
610 	static const struct bmi160_emul_cfg bmi160_emul_cfg_##n = {                                \
611 		.reg = bmi160_emul_reg_##n, .chipsel = DT_INST_REG_ADDR(n)};                       \
612 	BMI160_EMUL_DEFINE(n, bmi160_emul_api_spi)
613 
614 #define BMI160_EMUL_I2C(n)                                                                         \
615 	BMI160_EMUL_DATA(n)                                                                        \
616 	static const struct bmi160_emul_cfg bmi160_emul_cfg_##n = {.reg = bmi160_emul_reg_##n,     \
617 								   .addr = DT_INST_REG_ADDR(n)};   \
618 	BMI160_EMUL_DEFINE(n, bmi160_emul_api_i2c)
619 
620 /*
621  * Main instantiation macro. Use of COND_CODE_1() selects the right
622  * bus-specific macro at preprocessor time.
623  */
624 #define BMI160_EMUL(n)                                                                             \
625 	COND_CODE_1(DT_INST_ON_BUS(n, spi), (BMI160_EMUL_SPI(n)), (BMI160_EMUL_I2C(n)))
626 
627 DT_INST_FOREACH_STATUS_OKAY(BMI160_EMUL)
628