147d323ceSPetre Rodan // SPDX-License-Identifier: GPL-2.0-or-later 247d323ceSPetre Rodan /* 347d323ceSPetre Rodan * Honeywell ABP2 series pressure sensor driver 447d323ceSPetre Rodan * 547d323ceSPetre Rodan * Copyright (c) 2025 Petre Rodan <petre.rodan@subdimension.ro> 647d323ceSPetre Rodan * 747d323ceSPetre Rodan * Datasheet: https://prod-edam.honeywell.com/content/dam/honeywell-edam/sps/siot/en-us/products/sensors/pressure-sensors/board-mount-pressure-sensors/basic-abp2-series/documents/sps-siot-abp2-series-datasheet-32350268-en.pdf 847d323ceSPetre Rodan */ 947d323ceSPetre Rodan 1047d323ceSPetre Rodan #include <linux/array_size.h> 1147d323ceSPetre Rodan #include <linux/bits.h> 1247d323ceSPetre Rodan #include <linux/completion.h> 1347d323ceSPetre Rodan #include <linux/delay.h> 1447d323ceSPetre Rodan #include <linux/dev_printk.h> 1547d323ceSPetre Rodan #include <linux/device.h> 1647d323ceSPetre Rodan #include <linux/errno.h> 1747d323ceSPetre Rodan #include <linux/export.h> 1847d323ceSPetre Rodan #include <linux/gpio/consumer.h> 1947d323ceSPetre Rodan #include <linux/interrupt.h> 2047d323ceSPetre Rodan #include <linux/jiffies.h> 2147d323ceSPetre Rodan #include <linux/math64.h> 2247d323ceSPetre Rodan #include <linux/module.h> 2347d323ceSPetre Rodan #include <linux/property.h> 2447d323ceSPetre Rodan #include <linux/regulator/consumer.h> 2547d323ceSPetre Rodan #include <linux/string.h> 2647d323ceSPetre Rodan #include <linux/time.h> 2747d323ceSPetre Rodan #include <linux/types.h> 2847d323ceSPetre Rodan #include <linux/unaligned.h> 2947d323ceSPetre Rodan #include <linux/units.h> 3047d323ceSPetre Rodan 3147d323ceSPetre Rodan #include <linux/iio/buffer.h> 3247d323ceSPetre Rodan #include <linux/iio/iio.h> 3347d323ceSPetre Rodan #include <linux/iio/trigger_consumer.h> 3447d323ceSPetre Rodan #include <linux/iio/triggered_buffer.h> 3547d323ceSPetre Rodan 3647d323ceSPetre Rodan #include "abp2030pa.h" 3747d323ceSPetre Rodan 3847d323ceSPetre Rodan /* Status byte flags */ 3947d323ceSPetre Rodan #define ABP2_ST_POWER BIT(6) /* 1 if device is powered */ 4047d323ceSPetre Rodan #define ABP2_ST_BUSY BIT(5) /* 1 if device is busy */ 4147d323ceSPetre Rodan 4247d323ceSPetre Rodan #define ABP2_CMD_NOP 0xf0 4347d323ceSPetre Rodan #define ABP2_CMD_SYNC 0xaa 4447d323ceSPetre Rodan #define ABP2_PKT_SYNC_LEN 3 4547d323ceSPetre Rodan #define ABP2_PKT_NOP_LEN ABP2_MEASUREMENT_RD_SIZE 4647d323ceSPetre Rodan 4747d323ceSPetre Rodan struct abp2_func_spec { 4847d323ceSPetre Rodan u32 output_min; 4947d323ceSPetre Rodan u32 output_max; 5047d323ceSPetre Rodan }; 5147d323ceSPetre Rodan 5247d323ceSPetre Rodan /* transfer function A: 10% to 90% of 2^24 */ 5347d323ceSPetre Rodan static const struct abp2_func_spec abp2_func_spec[] = { 5447d323ceSPetre Rodan [ABP2_FUNCTION_A] = { .output_min = 1677722, .output_max = 15099494 }, 5547d323ceSPetre Rodan }; 5647d323ceSPetre Rodan 5747d323ceSPetre Rodan enum abp2_variants { 5847d323ceSPetre Rodan ABP2001BA, ABP21_6BA, ABP22_5BA, ABP2004BA, ABP2006BA, ABP2008BA, 5947d323ceSPetre Rodan ABP2010BA, ABP2012BA, ABP2001BD, ABP21_6BD, ABP22_5BD, ABP2004BD, 6047d323ceSPetre Rodan ABP2001BG, ABP21_6BG, ABP22_5BG, ABP2004BG, ABP2006BG, ABP2008BG, 6147d323ceSPetre Rodan ABP2010BG, ABP2012BG, ABP2001GG, ABP21_2GG, ABP2100KA, ABP2160KA, 6247d323ceSPetre Rodan ABP2250KA, ABP2001KD, ABP21_6KD, ABP22_5KD, ABP2004KD, ABP2006KD, 6347d323ceSPetre Rodan ABP2010KD, ABP2016KD, ABP2025KD, ABP2040KD, ABP2060KD, ABP2100KD, 6447d323ceSPetre Rodan ABP2160KD, ABP2250KD, ABP2400KD, ABP2001KG, ABP21_6KG, ABP22_5KG, 6547d323ceSPetre Rodan ABP2004KG, ABP2006KG, ABP2010KG, ABP2016KG, ABP2025KG, ABP2040KG, 6647d323ceSPetre Rodan ABP2060KG, ABP2100KG, ABP2160KG, ABP2250KG, ABP2400KG, ABP2600KG, 6747d323ceSPetre Rodan ABP2800KG, ABP2250LD, ABP2600LD, ABP2600LG, ABP22_5MD, ABP2006MD, 6847d323ceSPetre Rodan ABP2010MD, ABP2016MD, ABP2025MD, ABP2040MD, ABP2060MD, ABP2100MD, 6947d323ceSPetre Rodan ABP2160MD, ABP2250MD, ABP2400MD, ABP2600MD, ABP2006MG, ABP2010MG, 7047d323ceSPetre Rodan ABP2016MG, ABP2025MG, ABP2040MG, ABP2060MG, ABP2100MG, ABP2160MG, 7147d323ceSPetre Rodan ABP2250MG, ABP2400MG, ABP2600MG, ABP2001ND, ABP2002ND, ABP2004ND, 7247d323ceSPetre Rodan ABP2005ND, ABP2010ND, ABP2020ND, ABP2030ND, ABP2002NG, ABP2004NG, 7347d323ceSPetre Rodan ABP2005NG, ABP2010NG, ABP2020NG, ABP2030NG, ABP2015PA, ABP2030PA, 7447d323ceSPetre Rodan ABP2060PA, ABP2100PA, ABP2150PA, ABP2175PA, ABP2001PD, ABP2005PD, 7547d323ceSPetre Rodan ABP2015PD, ABP2030PD, ABP2060PD, ABP2001PG, ABP2005PG, ABP2015PG, 7647d323ceSPetre Rodan ABP2030PG, ABP2060PG, ABP2100PG, ABP2150PG, ABP2175PG, 7747d323ceSPetre Rodan }; 7847d323ceSPetre Rodan 7947d323ceSPetre Rodan static const char * const abp2_triplet_variants[] = { 8047d323ceSPetre Rodan [ABP2001BA] = "001BA", [ABP21_6BA] = "1.6BA", [ABP22_5BA] = "2.5BA", 8147d323ceSPetre Rodan [ABP2004BA] = "004BA", [ABP2006BA] = "006BA", [ABP2008BA] = "008BA", 8247d323ceSPetre Rodan [ABP2010BA] = "010BA", [ABP2012BA] = "012BA", [ABP2001BD] = "001BD", 8347d323ceSPetre Rodan [ABP21_6BD] = "1.6BD", [ABP22_5BD] = "2.5BD", [ABP2004BD] = "004BD", 8447d323ceSPetre Rodan [ABP2001BG] = "001BG", [ABP21_6BG] = "1.6BG", [ABP22_5BG] = "2.5BG", 8547d323ceSPetre Rodan [ABP2004BG] = "004BG", [ABP2006BG] = "006BG", [ABP2008BG] = "008BG", 8647d323ceSPetre Rodan [ABP2010BG] = "010BG", [ABP2012BG] = "012BG", [ABP2001GG] = "001GG", 8747d323ceSPetre Rodan [ABP21_2GG] = "1.2GG", [ABP2100KA] = "100KA", [ABP2160KA] = "160KA", 8847d323ceSPetre Rodan [ABP2250KA] = "250KA", [ABP2001KD] = "001KD", [ABP21_6KD] = "1.6KD", 8947d323ceSPetre Rodan [ABP22_5KD] = "2.5KD", [ABP2004KD] = "004KD", [ABP2006KD] = "006KD", 9047d323ceSPetre Rodan [ABP2010KD] = "010KD", [ABP2016KD] = "016KD", [ABP2025KD] = "025KD", 9147d323ceSPetre Rodan [ABP2040KD] = "040KD", [ABP2060KD] = "060KD", [ABP2100KD] = "100KD", 9247d323ceSPetre Rodan [ABP2160KD] = "160KD", [ABP2250KD] = "250KD", [ABP2400KD] = "400KD", 9347d323ceSPetre Rodan [ABP2001KG] = "001KG", [ABP21_6KG] = "1.6KG", [ABP22_5KG] = "2.5KG", 9447d323ceSPetre Rodan [ABP2004KG] = "004KG", [ABP2006KG] = "006KG", [ABP2010KG] = "010KG", 9547d323ceSPetre Rodan [ABP2016KG] = "016KG", [ABP2025KG] = "025KG", [ABP2040KG] = "040KG", 9647d323ceSPetre Rodan [ABP2060KG] = "060KG", [ABP2100KG] = "100KG", [ABP2160KG] = "160KG", 9747d323ceSPetre Rodan [ABP2250KG] = "250KG", [ABP2400KG] = "400KG", [ABP2600KG] = "600KG", 9847d323ceSPetre Rodan [ABP2800KG] = "800KG", [ABP2250LD] = "250LD", [ABP2600LD] = "600LD", 9947d323ceSPetre Rodan [ABP2600LG] = "600LG", [ABP22_5MD] = "2.5MD", [ABP2006MD] = "006MD", 10047d323ceSPetre Rodan [ABP2010MD] = "010MD", [ABP2016MD] = "016MD", [ABP2025MD] = "025MD", 10147d323ceSPetre Rodan [ABP2040MD] = "040MD", [ABP2060MD] = "060MD", [ABP2100MD] = "100MD", 10247d323ceSPetre Rodan [ABP2160MD] = "160MD", [ABP2250MD] = "250MD", [ABP2400MD] = "400MD", 10347d323ceSPetre Rodan [ABP2600MD] = "600MD", [ABP2006MG] = "006MG", [ABP2010MG] = "010MG", 10447d323ceSPetre Rodan [ABP2016MG] = "016MG", [ABP2025MG] = "025MG", [ABP2040MG] = "040MG", 10547d323ceSPetre Rodan [ABP2060MG] = "060MG", [ABP2100MG] = "100MG", [ABP2160MG] = "160MG", 10647d323ceSPetre Rodan [ABP2250MG] = "250MG", [ABP2400MG] = "400MG", [ABP2600MG] = "600MG", 10747d323ceSPetre Rodan [ABP2001ND] = "001ND", [ABP2002ND] = "002ND", [ABP2004ND] = "004ND", 10847d323ceSPetre Rodan [ABP2005ND] = "005ND", [ABP2010ND] = "010ND", [ABP2020ND] = "020ND", 10947d323ceSPetre Rodan [ABP2030ND] = "030ND", [ABP2002NG] = "002NG", [ABP2004NG] = "004NG", 11047d323ceSPetre Rodan [ABP2005NG] = "005NG", [ABP2010NG] = "010NG", [ABP2020NG] = "020NG", 11147d323ceSPetre Rodan [ABP2030NG] = "030NG", [ABP2015PA] = "015PA", [ABP2030PA] = "030PA", 11247d323ceSPetre Rodan [ABP2060PA] = "060PA", [ABP2100PA] = "100PA", [ABP2150PA] = "150PA", 11347d323ceSPetre Rodan [ABP2175PA] = "175PA", [ABP2001PD] = "001PD", [ABP2005PD] = "005PD", 11447d323ceSPetre Rodan [ABP2015PD] = "015PD", [ABP2030PD] = "030PD", [ABP2060PD] = "060PD", 11547d323ceSPetre Rodan [ABP2001PG] = "001PG", [ABP2005PG] = "005PG", [ABP2015PG] = "015PG", 11647d323ceSPetre Rodan [ABP2030PG] = "030PG", [ABP2060PG] = "060PG", [ABP2100PG] = "100PG", 11747d323ceSPetre Rodan [ABP2150PG] = "150PG", [ABP2175PG] = "175PG", 11847d323ceSPetre Rodan }; 11947d323ceSPetre Rodan 12047d323ceSPetre Rodan /** 12147d323ceSPetre Rodan * struct abp2_range_config - list of pressure ranges based on nomenclature 12247d323ceSPetre Rodan * @pmin: lowest pressure that can be measured 12347d323ceSPetre Rodan * @pmax: highest pressure that can be measured 12447d323ceSPetre Rodan */ 12547d323ceSPetre Rodan struct abp2_range_config { 12647d323ceSPetre Rodan s32 pmin; 12747d323ceSPetre Rodan s32 pmax; 12847d323ceSPetre Rodan }; 12947d323ceSPetre Rodan 13047d323ceSPetre Rodan /* All min max limits have been converted to pascals */ 13147d323ceSPetre Rodan static const struct abp2_range_config abp2_range_config[] = { 13247d323ceSPetre Rodan [ABP2001BA] = { .pmin = 0, .pmax = 100000 }, 13347d323ceSPetre Rodan [ABP21_6BA] = { .pmin = 0, .pmax = 160000 }, 13447d323ceSPetre Rodan [ABP22_5BA] = { .pmin = 0, .pmax = 250000 }, 13547d323ceSPetre Rodan [ABP2004BA] = { .pmin = 0, .pmax = 400000 }, 13647d323ceSPetre Rodan [ABP2006BA] = { .pmin = 0, .pmax = 600000 }, 13747d323ceSPetre Rodan [ABP2008BA] = { .pmin = 0, .pmax = 800000 }, 13847d323ceSPetre Rodan [ABP2010BA] = { .pmin = 0, .pmax = 1000000 }, 13947d323ceSPetre Rodan [ABP2012BA] = { .pmin = 0, .pmax = 1200000 }, 14047d323ceSPetre Rodan [ABP2001BD] = { .pmin = -100000, .pmax = 100000 }, 14147d323ceSPetre Rodan [ABP21_6BD] = { .pmin = -160000, .pmax = 160000 }, 14247d323ceSPetre Rodan [ABP22_5BD] = { .pmin = -250000, .pmax = 250000 }, 14347d323ceSPetre Rodan [ABP2004BD] = { .pmin = -400000, .pmax = 400000 }, 14447d323ceSPetre Rodan [ABP2001BG] = { .pmin = 0, .pmax = 100000 }, 14547d323ceSPetre Rodan [ABP21_6BG] = { .pmin = 0, .pmax = 160000 }, 14647d323ceSPetre Rodan [ABP22_5BG] = { .pmin = 0, .pmax = 250000 }, 14747d323ceSPetre Rodan [ABP2004BG] = { .pmin = 0, .pmax = 400000 }, 14847d323ceSPetre Rodan [ABP2006BG] = { .pmin = 0, .pmax = 600000 }, 14947d323ceSPetre Rodan [ABP2008BG] = { .pmin = 0, .pmax = 800000 }, 15047d323ceSPetre Rodan [ABP2010BG] = { .pmin = 0, .pmax = 1000000 }, 15147d323ceSPetre Rodan [ABP2012BG] = { .pmin = 0, .pmax = 1200000 }, 15247d323ceSPetre Rodan [ABP2001GG] = { .pmin = 0, .pmax = 1000000 }, 15347d323ceSPetre Rodan [ABP21_2GG] = { .pmin = 0, .pmax = 1200000 }, 15447d323ceSPetre Rodan [ABP2100KA] = { .pmin = 0, .pmax = 100000 }, 15547d323ceSPetre Rodan [ABP2160KA] = { .pmin = 0, .pmax = 160000 }, 15647d323ceSPetre Rodan [ABP2250KA] = { .pmin = 0, .pmax = 250000 }, 15747d323ceSPetre Rodan [ABP2001KD] = { .pmin = -1000, .pmax = 1000 }, 15847d323ceSPetre Rodan [ABP21_6KD] = { .pmin = -1600, .pmax = 1600 }, 15947d323ceSPetre Rodan [ABP22_5KD] = { .pmin = -2500, .pmax = 2500 }, 16047d323ceSPetre Rodan [ABP2004KD] = { .pmin = -4000, .pmax = 4000 }, 16147d323ceSPetre Rodan [ABP2006KD] = { .pmin = -6000, .pmax = 6000 }, 16247d323ceSPetre Rodan [ABP2010KD] = { .pmin = -10000, .pmax = 10000 }, 16347d323ceSPetre Rodan [ABP2016KD] = { .pmin = -16000, .pmax = 16000 }, 16447d323ceSPetre Rodan [ABP2025KD] = { .pmin = -25000, .pmax = 25000 }, 16547d323ceSPetre Rodan [ABP2040KD] = { .pmin = -40000, .pmax = 40000 }, 16647d323ceSPetre Rodan [ABP2060KD] = { .pmin = -60000, .pmax = 60000 }, 16747d323ceSPetre Rodan [ABP2100KD] = { .pmin = -100000, .pmax = 100000 }, 16847d323ceSPetre Rodan [ABP2160KD] = { .pmin = -160000, .pmax = 160000 }, 16947d323ceSPetre Rodan [ABP2250KD] = { .pmin = -250000, .pmax = 250000 }, 17047d323ceSPetre Rodan [ABP2400KD] = { .pmin = -400000, .pmax = 400000 }, 17147d323ceSPetre Rodan [ABP2001KG] = { .pmin = 0, .pmax = 1000 }, 17247d323ceSPetre Rodan [ABP21_6KG] = { .pmin = 0, .pmax = 1600 }, 17347d323ceSPetre Rodan [ABP22_5KG] = { .pmin = 0, .pmax = 2500 }, 17447d323ceSPetre Rodan [ABP2004KG] = { .pmin = 0, .pmax = 4000 }, 17547d323ceSPetre Rodan [ABP2006KG] = { .pmin = 0, .pmax = 6000 }, 17647d323ceSPetre Rodan [ABP2010KG] = { .pmin = 0, .pmax = 10000 }, 17747d323ceSPetre Rodan [ABP2016KG] = { .pmin = 0, .pmax = 16000 }, 17847d323ceSPetre Rodan [ABP2025KG] = { .pmin = 0, .pmax = 25000 }, 17947d323ceSPetre Rodan [ABP2040KG] = { .pmin = 0, .pmax = 40000 }, 18047d323ceSPetre Rodan [ABP2060KG] = { .pmin = 0, .pmax = 60000 }, 18147d323ceSPetre Rodan [ABP2100KG] = { .pmin = 0, .pmax = 100000 }, 18247d323ceSPetre Rodan [ABP2160KG] = { .pmin = 0, .pmax = 160000 }, 18347d323ceSPetre Rodan [ABP2250KG] = { .pmin = 0, .pmax = 250000 }, 18447d323ceSPetre Rodan [ABP2400KG] = { .pmin = 0, .pmax = 400000 }, 18547d323ceSPetre Rodan [ABP2600KG] = { .pmin = 0, .pmax = 600000 }, 18647d323ceSPetre Rodan [ABP2800KG] = { .pmin = 0, .pmax = 800000 }, 18747d323ceSPetre Rodan [ABP2250LD] = { .pmin = -250, .pmax = 250 }, 18847d323ceSPetre Rodan [ABP2600LD] = { .pmin = -600, .pmax = 600 }, 18947d323ceSPetre Rodan [ABP2600LG] = { .pmin = 0, .pmax = 600 }, 19047d323ceSPetre Rodan [ABP22_5MD] = { .pmin = -250, .pmax = 250 }, 19147d323ceSPetre Rodan [ABP2006MD] = { .pmin = -600, .pmax = 600 }, 19247d323ceSPetre Rodan [ABP2010MD] = { .pmin = -1000, .pmax = 1000 }, 19347d323ceSPetre Rodan [ABP2016MD] = { .pmin = -1600, .pmax = 1600 }, 19447d323ceSPetre Rodan [ABP2025MD] = { .pmin = -2500, .pmax = 2500 }, 19547d323ceSPetre Rodan [ABP2040MD] = { .pmin = -4000, .pmax = 4000 }, 19647d323ceSPetre Rodan [ABP2060MD] = { .pmin = -6000, .pmax = 6000 }, 19747d323ceSPetre Rodan [ABP2100MD] = { .pmin = -10000, .pmax = 10000 }, 19847d323ceSPetre Rodan [ABP2160MD] = { .pmin = -16000, .pmax = 16000 }, 19947d323ceSPetre Rodan [ABP2250MD] = { .pmin = -25000, .pmax = 25000 }, 20047d323ceSPetre Rodan [ABP2400MD] = { .pmin = -40000, .pmax = 40000 }, 20147d323ceSPetre Rodan [ABP2600MD] = { .pmin = -60000, .pmax = 60000 }, 20247d323ceSPetre Rodan [ABP2006MG] = { .pmin = 0, .pmax = 600 }, 20347d323ceSPetre Rodan [ABP2010MG] = { .pmin = 0, .pmax = 1000 }, 20447d323ceSPetre Rodan [ABP2016MG] = { .pmin = 0, .pmax = 1600 }, 20547d323ceSPetre Rodan [ABP2025MG] = { .pmin = 0, .pmax = 2500 }, 20647d323ceSPetre Rodan [ABP2040MG] = { .pmin = 0, .pmax = 4000 }, 20747d323ceSPetre Rodan [ABP2060MG] = { .pmin = 0, .pmax = 6000 }, 20847d323ceSPetre Rodan [ABP2100MG] = { .pmin = 0, .pmax = 10000 }, 20947d323ceSPetre Rodan [ABP2160MG] = { .pmin = 0, .pmax = 16000 }, 21047d323ceSPetre Rodan [ABP2250MG] = { .pmin = 0, .pmax = 25000 }, 21147d323ceSPetre Rodan [ABP2400MG] = { .pmin = 0, .pmax = 40000 }, 21247d323ceSPetre Rodan [ABP2600MG] = { .pmin = 0, .pmax = 60000 }, 21347d323ceSPetre Rodan [ABP2001ND] = { .pmin = -249, .pmax = 249 }, 21447d323ceSPetre Rodan [ABP2002ND] = { .pmin = -498, .pmax = 498 }, 21547d323ceSPetre Rodan [ABP2004ND] = { .pmin = -996, .pmax = 996 }, 21647d323ceSPetre Rodan [ABP2005ND] = { .pmin = -1245, .pmax = 1245 }, 21747d323ceSPetre Rodan [ABP2010ND] = { .pmin = -2491, .pmax = 2491 }, 21847d323ceSPetre Rodan [ABP2020ND] = { .pmin = -4982, .pmax = 4982 }, 21947d323ceSPetre Rodan [ABP2030ND] = { .pmin = -7473, .pmax = 7473 }, 22047d323ceSPetre Rodan [ABP2002NG] = { .pmin = 0, .pmax = 498 }, 22147d323ceSPetre Rodan [ABP2004NG] = { .pmin = 0, .pmax = 996 }, 22247d323ceSPetre Rodan [ABP2005NG] = { .pmin = 0, .pmax = 1245 }, 22347d323ceSPetre Rodan [ABP2010NG] = { .pmin = 0, .pmax = 2491 }, 22447d323ceSPetre Rodan [ABP2020NG] = { .pmin = 0, .pmax = 4982 }, 22547d323ceSPetre Rodan [ABP2030NG] = { .pmin = 0, .pmax = 7473 }, 22647d323ceSPetre Rodan [ABP2015PA] = { .pmin = 0, .pmax = 103421 }, 22747d323ceSPetre Rodan [ABP2030PA] = { .pmin = 0, .pmax = 206843 }, 22847d323ceSPetre Rodan [ABP2060PA] = { .pmin = 0, .pmax = 413685 }, 22947d323ceSPetre Rodan [ABP2100PA] = { .pmin = 0, .pmax = 689476 }, 23047d323ceSPetre Rodan [ABP2150PA] = { .pmin = 0, .pmax = 1034214 }, 23147d323ceSPetre Rodan [ABP2175PA] = { .pmin = 0, .pmax = 1206583 }, 23247d323ceSPetre Rodan [ABP2001PD] = { .pmin = -6895, .pmax = 6895 }, 23347d323ceSPetre Rodan [ABP2005PD] = { .pmin = -34474, .pmax = 34474 }, 23447d323ceSPetre Rodan [ABP2015PD] = { .pmin = -103421, .pmax = 103421 }, 23547d323ceSPetre Rodan [ABP2030PD] = { .pmin = -206843, .pmax = 206843 }, 23647d323ceSPetre Rodan [ABP2060PD] = { .pmin = -413685, .pmax = 413685 }, 23747d323ceSPetre Rodan [ABP2001PG] = { .pmin = 0, .pmax = 6895 }, 23847d323ceSPetre Rodan [ABP2005PG] = { .pmin = 0, .pmax = 34474 }, 23947d323ceSPetre Rodan [ABP2015PG] = { .pmin = 0, .pmax = 103421 }, 24047d323ceSPetre Rodan [ABP2030PG] = { .pmin = 0, .pmax = 206843 }, 24147d323ceSPetre Rodan [ABP2060PG] = { .pmin = 0, .pmax = 413685 }, 24247d323ceSPetre Rodan [ABP2100PG] = { .pmin = 0, .pmax = 689476 }, 24347d323ceSPetre Rodan [ABP2150PG] = { .pmin = 0, .pmax = 1034214 }, 24447d323ceSPetre Rodan [ABP2175PG] = { .pmin = 0, .pmax = 1206583 }, 24547d323ceSPetre Rodan }; 24647d323ceSPetre Rodan 24747d323ceSPetre Rodan static_assert(ARRAY_SIZE(abp2_triplet_variants) == ARRAY_SIZE(abp2_range_config)); 24847d323ceSPetre Rodan 24947d323ceSPetre Rodan static int abp2_get_measurement(struct abp2_data *data) 25047d323ceSPetre Rodan { 25147d323ceSPetre Rodan struct device *dev = data->dev; 25247d323ceSPetre Rodan int ret; 25347d323ceSPetre Rodan 25447d323ceSPetre Rodan reinit_completion(&data->completion); 25547d323ceSPetre Rodan 25647d323ceSPetre Rodan ret = data->ops->write(data, ABP2_CMD_SYNC, ABP2_PKT_SYNC_LEN); 25747d323ceSPetre Rodan if (ret < 0) 25847d323ceSPetre Rodan return ret; 25947d323ceSPetre Rodan 26047d323ceSPetre Rodan if (data->irq > 0) { 26147d323ceSPetre Rodan ret = wait_for_completion_timeout(&data->completion, HZ); 26247d323ceSPetre Rodan if (!ret) { 26347d323ceSPetre Rodan dev_err(dev, "timeout waiting for EOC interrupt\n"); 26447d323ceSPetre Rodan return -ETIMEDOUT; 26547d323ceSPetre Rodan } 26647d323ceSPetre Rodan } else { 26747d323ceSPetre Rodan fsleep(5 * USEC_PER_MSEC); 26847d323ceSPetre Rodan } 26947d323ceSPetre Rodan 27047d323ceSPetre Rodan memset(data->rx_buf, 0, sizeof(data->rx_buf)); 27147d323ceSPetre Rodan ret = data->ops->read(data, ABP2_CMD_NOP, ABP2_PKT_NOP_LEN); 27247d323ceSPetre Rodan if (ret < 0) 27347d323ceSPetre Rodan return ret; 27447d323ceSPetre Rodan 27547d323ceSPetre Rodan /* 27647d323ceSPetre Rodan * Status byte flags 27747d323ceSPetre Rodan * bit7 SANITY_CHK - must always be 0 27847d323ceSPetre Rodan * bit6 ABP2_ST_POWER - 1 if device is powered 27947d323ceSPetre Rodan * bit5 ABP2_ST_BUSY - 1 if device has no new conversion ready 28047d323ceSPetre Rodan * bit4 SANITY_CHK - must always be 0 28147d323ceSPetre Rodan * bit3 SANITY_CHK - must always be 0 28247d323ceSPetre Rodan * bit2 MEMORY_ERR - 1 if integrity test has failed 28347d323ceSPetre Rodan * bit1 SANITY_CHK - must always be 0 28447d323ceSPetre Rodan * bit0 MATH_ERR - 1 during internal math saturation error 28547d323ceSPetre Rodan */ 28647d323ceSPetre Rodan 28747d323ceSPetre Rodan if (data->rx_buf[0] == (ABP2_ST_POWER | ABP2_ST_BUSY)) 28847d323ceSPetre Rodan return -EBUSY; 28947d323ceSPetre Rodan 29047d323ceSPetre Rodan /* 29147d323ceSPetre Rodan * The ABP2 sensor series seem to have a noticeable latch-up sensitivity. 29247d323ceSPetre Rodan * A partial latch-up condition manifests as either 29347d323ceSPetre Rodan * - output of invalid status bytes 29447d323ceSPetre Rodan * - zeroed out conversions (despite a normal status byte) 29547d323ceSPetre Rodan * - the MOSI line being pulled low randomly in sync with the SCLK 29647d323ceSPetre Rodan * signal (visible during the ABP2_CMD_NOP command). 29747d323ceSPetre Rodan * https://e2e.ti.com/support/processors-group/processors/f/processors-forum/1588325/am3358-spi-tx-data-corruption 29847d323ceSPetre Rodan */ 29947d323ceSPetre Rodan 30047d323ceSPetre Rodan if (data->rx_buf[0] != ABP2_ST_POWER) { 30147d323ceSPetre Rodan dev_err(data->dev, 30247d323ceSPetre Rodan "unexpected status byte 0x%02x\n", data->rx_buf[0]); 30347d323ceSPetre Rodan return -EIO; 30447d323ceSPetre Rodan } 30547d323ceSPetre Rodan 30647d323ceSPetre Rodan return 0; 30747d323ceSPetre Rodan } 30847d323ceSPetre Rodan 30947d323ceSPetre Rodan static irqreturn_t abp2_eoc_handler(int irq, void *private) 31047d323ceSPetre Rodan { 31147d323ceSPetre Rodan struct abp2_data *data = private; 31247d323ceSPetre Rodan 31347d323ceSPetre Rodan complete(&data->completion); 31447d323ceSPetre Rodan 31547d323ceSPetre Rodan return IRQ_HANDLED; 31647d323ceSPetre Rodan } 31747d323ceSPetre Rodan 31847d323ceSPetre Rodan static irqreturn_t abp2_trigger_handler(int irq, void *private) 31947d323ceSPetre Rodan { 32047d323ceSPetre Rodan int ret; 32147d323ceSPetre Rodan struct iio_poll_func *pf = private; 32247d323ceSPetre Rodan struct iio_dev *indio_dev = pf->indio_dev; 32347d323ceSPetre Rodan struct abp2_data *data = iio_priv(indio_dev); 32447d323ceSPetre Rodan 32547d323ceSPetre Rodan ret = abp2_get_measurement(data); 32647d323ceSPetre Rodan if (ret < 0) 32747d323ceSPetre Rodan goto out_notify_done; 32847d323ceSPetre Rodan 32947d323ceSPetre Rodan data->scan.chan[0] = get_unaligned_be24(&data->rx_buf[1]); 33047d323ceSPetre Rodan data->scan.chan[1] = get_unaligned_be24(&data->rx_buf[4]); 33147d323ceSPetre Rodan 33247d323ceSPetre Rodan iio_push_to_buffers_with_ts(indio_dev, &data->scan, sizeof(data->scan), 33347d323ceSPetre Rodan iio_get_time_ns(indio_dev)); 33447d323ceSPetre Rodan 33547d323ceSPetre Rodan out_notify_done: 33647d323ceSPetre Rodan iio_trigger_notify_done(indio_dev->trig); 33747d323ceSPetre Rodan 33847d323ceSPetre Rodan return IRQ_HANDLED; 33947d323ceSPetre Rodan } 34047d323ceSPetre Rodan 34147d323ceSPetre Rodan /* 34247d323ceSPetre Rodan * IIO ABI expects 34347d323ceSPetre Rodan * value = (conv + offset) * scale 34447d323ceSPetre Rodan * 34547d323ceSPetre Rodan * temp[C] = conv * a + b 34647d323ceSPetre Rodan * where a = 200/16777215; b = -50 34747d323ceSPetre Rodan * 34847d323ceSPetre Rodan * temp[C] = (conv + (b/a)) * a * (1000) 34947d323ceSPetre Rodan * => 35047d323ceSPetre Rodan * scale = a * 1000 = .0000119209296 * 1000 = .01192092966562 35147d323ceSPetre Rodan * offset = b/a = -50 * 16777215 / 200 = -4194303.75 35247d323ceSPetre Rodan * 35347d323ceSPetre Rodan * pressure = (conv - Omin) * Q + Pmin = 35447d323ceSPetre Rodan * ((conv - Omin) + Pmin/Q) * Q 35547d323ceSPetre Rodan * => 35647d323ceSPetre Rodan * scale = Q = (Pmax - Pmin) / (Omax - Omin) 35747d323ceSPetre Rodan * offset = Pmin/Q - Omin = Pmin * (Omax - Omin) / (Pmax - Pmin) - Omin 35847d323ceSPetre Rodan */ 35947d323ceSPetre Rodan static int abp2_read_raw(struct iio_dev *indio_dev, 36047d323ceSPetre Rodan struct iio_chan_spec const *channel, int *val, 36147d323ceSPetre Rodan int *val2, long mask) 36247d323ceSPetre Rodan { 36347d323ceSPetre Rodan struct abp2_data *data = iio_priv(indio_dev); 36447d323ceSPetre Rodan int ret; 36547d323ceSPetre Rodan 36647d323ceSPetre Rodan switch (mask) { 36747d323ceSPetre Rodan case IIO_CHAN_INFO_RAW: 36847d323ceSPetre Rodan ret = abp2_get_measurement(data); 36947d323ceSPetre Rodan if (ret < 0) 37047d323ceSPetre Rodan return ret; 37147d323ceSPetre Rodan 37247d323ceSPetre Rodan switch (channel->type) { 37347d323ceSPetre Rodan case IIO_PRESSURE: 37447d323ceSPetre Rodan *val = get_unaligned_be24(&data->rx_buf[1]); 37547d323ceSPetre Rodan return IIO_VAL_INT; 37647d323ceSPetre Rodan case IIO_TEMP: 37747d323ceSPetre Rodan *val = get_unaligned_be24(&data->rx_buf[4]); 37847d323ceSPetre Rodan return IIO_VAL_INT; 37947d323ceSPetre Rodan default: 38047d323ceSPetre Rodan return -EINVAL; 38147d323ceSPetre Rodan } 38247d323ceSPetre Rodan return IIO_VAL_INT; 38347d323ceSPetre Rodan 38447d323ceSPetre Rodan case IIO_CHAN_INFO_SCALE: 38547d323ceSPetre Rodan switch (channel->type) { 38647d323ceSPetre Rodan case IIO_TEMP: 38747d323ceSPetre Rodan *val = 0; 38847d323ceSPetre Rodan *val2 = 11920929; 38947d323ceSPetre Rodan return IIO_VAL_INT_PLUS_NANO; 39047d323ceSPetre Rodan case IIO_PRESSURE: 39147d323ceSPetre Rodan *val = data->p_scale; 39247d323ceSPetre Rodan *val2 = data->p_scale_dec; 39347d323ceSPetre Rodan return IIO_VAL_INT_PLUS_NANO; 39447d323ceSPetre Rodan default: 39547d323ceSPetre Rodan return -EINVAL; 39647d323ceSPetre Rodan } 39747d323ceSPetre Rodan 39847d323ceSPetre Rodan case IIO_CHAN_INFO_OFFSET: 39947d323ceSPetre Rodan switch (channel->type) { 40047d323ceSPetre Rodan case IIO_TEMP: 40147d323ceSPetre Rodan *val = -4194304; 40247d323ceSPetre Rodan return IIO_VAL_INT; 40347d323ceSPetre Rodan case IIO_PRESSURE: 40447d323ceSPetre Rodan *val = data->p_offset; 40547d323ceSPetre Rodan return IIO_VAL_INT; 40647d323ceSPetre Rodan default: 40747d323ceSPetre Rodan return -EINVAL; 40847d323ceSPetre Rodan } 40947d323ceSPetre Rodan 41047d323ceSPetre Rodan default: 41147d323ceSPetre Rodan return -EINVAL; 41247d323ceSPetre Rodan } 41347d323ceSPetre Rodan } 41447d323ceSPetre Rodan 41547d323ceSPetre Rodan static const struct iio_info abp2_info = { 41647d323ceSPetre Rodan .read_raw = &abp2_read_raw, 41747d323ceSPetre Rodan }; 41847d323ceSPetre Rodan 41947d323ceSPetre Rodan static const unsigned long abp2_scan_masks[] = {0x3, 0}; 42047d323ceSPetre Rodan 42147d323ceSPetre Rodan static const struct iio_chan_spec abp2_channels[] = { 42247d323ceSPetre Rodan { 42347d323ceSPetre Rodan .type = IIO_PRESSURE, 42447d323ceSPetre Rodan .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | 42547d323ceSPetre Rodan BIT(IIO_CHAN_INFO_SCALE) | 42647d323ceSPetre Rodan BIT(IIO_CHAN_INFO_OFFSET), 42747d323ceSPetre Rodan .scan_index = 0, 42847d323ceSPetre Rodan .scan_type = { 42947d323ceSPetre Rodan .sign = 'u', 43047d323ceSPetre Rodan .realbits = 24, 43147d323ceSPetre Rodan .storagebits = 32, 43247d323ceSPetre Rodan .endianness = IIO_CPU, 43347d323ceSPetre Rodan }, 43447d323ceSPetre Rodan }, 43547d323ceSPetre Rodan { 43647d323ceSPetre Rodan .type = IIO_TEMP, 43747d323ceSPetre Rodan .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | 43847d323ceSPetre Rodan BIT(IIO_CHAN_INFO_SCALE) | 43947d323ceSPetre Rodan BIT(IIO_CHAN_INFO_OFFSET), 44047d323ceSPetre Rodan .scan_index = 1, 44147d323ceSPetre Rodan .scan_type = { 44247d323ceSPetre Rodan .sign = 'u', 44347d323ceSPetre Rodan .realbits = 24, 44447d323ceSPetre Rodan .storagebits = 32, 44547d323ceSPetre Rodan .endianness = IIO_CPU, 44647d323ceSPetre Rodan }, 44747d323ceSPetre Rodan }, 44847d323ceSPetre Rodan IIO_CHAN_SOFT_TIMESTAMP(2), 44947d323ceSPetre Rodan }; 45047d323ceSPetre Rodan 45147d323ceSPetre Rodan int abp2_common_probe(struct device *dev, const struct abp2_ops *ops, int irq) 45247d323ceSPetre Rodan { 45347d323ceSPetre Rodan int ret; 45447d323ceSPetre Rodan struct abp2_data *data; 45547d323ceSPetre Rodan struct iio_dev *indio_dev; 45647d323ceSPetre Rodan const char *triplet; 45747d323ceSPetre Rodan s32 tmp; 45847d323ceSPetre Rodan s64 odelta, pdelta; 45947d323ceSPetre Rodan 46047d323ceSPetre Rodan indio_dev = devm_iio_device_alloc(dev, sizeof(*data)); 46147d323ceSPetre Rodan if (!indio_dev) 46247d323ceSPetre Rodan return -ENOMEM; 46347d323ceSPetre Rodan 46447d323ceSPetre Rodan data = iio_priv(indio_dev); 46547d323ceSPetre Rodan data->dev = dev; 46647d323ceSPetre Rodan data->ops = ops; 46747d323ceSPetre Rodan data->irq = irq; 46847d323ceSPetre Rodan 46947d323ceSPetre Rodan init_completion(&data->completion); 47047d323ceSPetre Rodan 47147d323ceSPetre Rodan indio_dev->name = "abp2030pa"; 47247d323ceSPetre Rodan indio_dev->info = &abp2_info; 47347d323ceSPetre Rodan indio_dev->channels = abp2_channels; 47447d323ceSPetre Rodan indio_dev->num_channels = ARRAY_SIZE(abp2_channels); 47547d323ceSPetre Rodan indio_dev->modes = INDIO_DIRECT_MODE; 47647d323ceSPetre Rodan indio_dev->available_scan_masks = abp2_scan_masks; 47747d323ceSPetre Rodan 47847d323ceSPetre Rodan ret = devm_regulator_get_enable(dev, "vdd"); 47947d323ceSPetre Rodan if (ret) 48047d323ceSPetre Rodan return dev_err_probe(dev, ret, "can't get and enable vdd supply\n"); 48147d323ceSPetre Rodan 48247d323ceSPetre Rodan ret = device_property_read_string(dev, "honeywell,pressure-triplet", 48347d323ceSPetre Rodan &triplet); 48447d323ceSPetre Rodan if (ret) { 48547d323ceSPetre Rodan ret = device_property_read_u32(dev, "honeywell,pmin-pascal", 48647d323ceSPetre Rodan &data->pmin); 48747d323ceSPetre Rodan if (ret) 48847d323ceSPetre Rodan return dev_err_probe(dev, ret, 48947d323ceSPetre Rodan "honeywell,pmin-pascal could not be read\n"); 49047d323ceSPetre Rodan 49147d323ceSPetre Rodan ret = device_property_read_u32(dev, "honeywell,pmax-pascal", 49247d323ceSPetre Rodan &data->pmax); 49347d323ceSPetre Rodan if (ret) 49447d323ceSPetre Rodan return dev_err_probe(dev, ret, 49547d323ceSPetre Rodan "honeywell,pmax-pascal could not be read\n"); 49647d323ceSPetre Rodan } else { 49747d323ceSPetre Rodan ret = device_property_match_property_string(dev, 49847d323ceSPetre Rodan "honeywell,pressure-triplet", 49947d323ceSPetre Rodan abp2_triplet_variants, 50047d323ceSPetre Rodan ARRAY_SIZE(abp2_triplet_variants)); 50147d323ceSPetre Rodan if (ret < 0) 50247d323ceSPetre Rodan return dev_err_probe(dev, -EINVAL, "honeywell,pressure-triplet is invalid\n"); 50347d323ceSPetre Rodan 50447d323ceSPetre Rodan data->pmin = abp2_range_config[ret].pmin; 50547d323ceSPetre Rodan data->pmax = abp2_range_config[ret].pmax; 50647d323ceSPetre Rodan } 50747d323ceSPetre Rodan 50847d323ceSPetre Rodan if (data->pmin >= data->pmax) 50947d323ceSPetre Rodan return dev_err_probe(dev, -EINVAL, "pressure limits are invalid\n"); 51047d323ceSPetre Rodan 51147d323ceSPetre Rodan data->outmin = abp2_func_spec[data->function].output_min; 51247d323ceSPetre Rodan data->outmax = abp2_func_spec[data->function].output_max; 51347d323ceSPetre Rodan 51447d323ceSPetre Rodan odelta = data->outmax - data->outmin; 51547d323ceSPetre Rodan pdelta = data->pmax - data->pmin; 51647d323ceSPetre Rodan 51747d323ceSPetre Rodan data->p_scale = div_s64_rem(div_s64(pdelta * NANO, odelta), NANO, &tmp); 51847d323ceSPetre Rodan data->p_scale_dec = tmp; 51947d323ceSPetre Rodan 52047d323ceSPetre Rodan data->p_offset = div_s64(odelta * data->pmin, pdelta) - data->outmin; 52147d323ceSPetre Rodan 52247d323ceSPetre Rodan if (data->irq > 0) { 52347d323ceSPetre Rodan ret = devm_request_irq(dev, irq, abp2_eoc_handler, IRQF_ONESHOT, 52447d323ceSPetre Rodan dev_name(dev), data); 52547d323ceSPetre Rodan if (ret) 526*b82f3047SPetre Rodan return ret; 52747d323ceSPetre Rodan } 52847d323ceSPetre Rodan 52947d323ceSPetre Rodan ret = devm_iio_triggered_buffer_setup(dev, indio_dev, NULL, 53047d323ceSPetre Rodan abp2_trigger_handler, NULL); 53147d323ceSPetre Rodan if (ret) 53247d323ceSPetre Rodan return dev_err_probe(dev, ret, "iio triggered buffer setup failed\n"); 53347d323ceSPetre Rodan 53447d323ceSPetre Rodan ret = devm_iio_device_register(dev, indio_dev); 53547d323ceSPetre Rodan if (ret) 53647d323ceSPetre Rodan return dev_err_probe(dev, ret, "unable to register iio device\n"); 53747d323ceSPetre Rodan 53847d323ceSPetre Rodan return 0; 53947d323ceSPetre Rodan } 54047d323ceSPetre Rodan EXPORT_SYMBOL_NS_GPL(abp2_common_probe, "IIO_HONEYWELL_ABP2030PA"); 54147d323ceSPetre Rodan 54247d323ceSPetre Rodan MODULE_AUTHOR("Petre Rodan <petre.rodan@subdimension.ro>"); 54347d323ceSPetre Rodan MODULE_DESCRIPTION("Honeywell ABP2 pressure sensor core driver"); 54447d323ceSPetre Rodan MODULE_LICENSE("GPL"); 545