1217494e5SDenis CIOCCA /* 2217494e5SDenis CIOCCA * STMicroelectronics pressures driver 3217494e5SDenis CIOCCA * 4217494e5SDenis CIOCCA * Copyright 2013 STMicroelectronics Inc. 5217494e5SDenis CIOCCA * 6217494e5SDenis CIOCCA * Denis Ciocca <denis.ciocca@st.com> 7217494e5SDenis CIOCCA * 8217494e5SDenis CIOCCA * Licensed under the GPL-2. 9217494e5SDenis CIOCCA */ 10217494e5SDenis CIOCCA 11217494e5SDenis CIOCCA #include <linux/kernel.h> 12217494e5SDenis CIOCCA #include <linux/module.h> 13217494e5SDenis CIOCCA #include <linux/slab.h> 149d317724SShrirang Bagul #include <linux/acpi.h> 15217494e5SDenis CIOCCA #include <linux/i2c.h> 16217494e5SDenis CIOCCA #include <linux/iio/iio.h> 17217494e5SDenis CIOCCA 18217494e5SDenis CIOCCA #include <linux/iio/common/st_sensors.h> 19217494e5SDenis CIOCCA #include <linux/iio/common/st_sensors_i2c.h> 20217494e5SDenis CIOCCA #include "st_pressure.h" 21217494e5SDenis CIOCCA 222d7768a8SLinus Walleij #ifdef CONFIG_OF 232d7768a8SLinus Walleij static const struct of_device_id st_press_of_match[] = { 242d7768a8SLinus Walleij { 252d7768a8SLinus Walleij .compatible = "st,lps001wp-press", 262d7768a8SLinus Walleij .data = LPS001WP_PRESS_DEV_NAME, 272d7768a8SLinus Walleij }, 282d7768a8SLinus Walleij { 292d7768a8SLinus Walleij .compatible = "st,lps25h-press", 302d7768a8SLinus Walleij .data = LPS25H_PRESS_DEV_NAME, 312d7768a8SLinus Walleij }, 322d7768a8SLinus Walleij { 332d7768a8SLinus Walleij .compatible = "st,lps331ap-press", 342d7768a8SLinus Walleij .data = LPS331AP_PRESS_DEV_NAME, 352d7768a8SLinus Walleij }, 36e039e2f5SGregor Boirie { 37e039e2f5SGregor Boirie .compatible = "st,lps22hb-press", 38e039e2f5SGregor Boirie .data = LPS22HB_PRESS_DEV_NAME, 39e039e2f5SGregor Boirie }, 402d7768a8SLinus Walleij {}, 412d7768a8SLinus Walleij }; 422d7768a8SLinus Walleij MODULE_DEVICE_TABLE(of, st_press_of_match); 432d7768a8SLinus Walleij #else 442d7768a8SLinus Walleij #define st_press_of_match NULL 452d7768a8SLinus Walleij #endif 462d7768a8SLinus Walleij 479d317724SShrirang Bagul #ifdef CONFIG_ACPI 489d317724SShrirang Bagul static const struct acpi_device_id st_press_acpi_match[] = { 499d317724SShrirang Bagul {"SNO9210", LPS22HB}, 509d317724SShrirang Bagul { }, 519d317724SShrirang Bagul }; 529d317724SShrirang Bagul MODULE_DEVICE_TABLE(acpi, st_press_acpi_match); 539d317724SShrirang Bagul #else 549d317724SShrirang Bagul #define st_press_acpi_match NULL 559d317724SShrirang Bagul #endif 569d317724SShrirang Bagul 579d317724SShrirang Bagul static const struct i2c_device_id st_press_id_table[] = { 589d317724SShrirang Bagul { LPS001WP_PRESS_DEV_NAME, LPS001WP }, 599d317724SShrirang Bagul { LPS25H_PRESS_DEV_NAME, LPS25H }, 609d317724SShrirang Bagul { LPS331AP_PRESS_DEV_NAME, LPS331AP }, 619d317724SShrirang Bagul { LPS22HB_PRESS_DEV_NAME, LPS22HB }, 629d317724SShrirang Bagul {}, 639d317724SShrirang Bagul }; 649d317724SShrirang Bagul MODULE_DEVICE_TABLE(i2c, st_press_id_table); 659d317724SShrirang Bagul 66217494e5SDenis CIOCCA static int st_press_i2c_probe(struct i2c_client *client, 67217494e5SDenis CIOCCA const struct i2c_device_id *id) 68217494e5SDenis CIOCCA { 69217494e5SDenis CIOCCA struct iio_dev *indio_dev; 70a1dcf429SDenis CIOCCA struct st_sensor_data *press_data; 719d317724SShrirang Bagul int ret; 72217494e5SDenis CIOCCA 73a1dcf429SDenis CIOCCA indio_dev = devm_iio_device_alloc(&client->dev, sizeof(*press_data)); 74d0fe8c8bSSachin Kamat if (!indio_dev) 75d0fe8c8bSSachin Kamat return -ENOMEM; 76217494e5SDenis CIOCCA 77a1dcf429SDenis CIOCCA press_data = iio_priv(indio_dev); 789d317724SShrirang Bagul 799d317724SShrirang Bagul if (client->dev.of_node) { 80*250bbbdbSLorenzo Bianconi st_sensors_of_name_probe(&client->dev, st_press_of_match, 81*250bbbdbSLorenzo Bianconi client->name, sizeof(client->name)); 829d317724SShrirang Bagul } else if (ACPI_HANDLE(&client->dev)) { 839d317724SShrirang Bagul ret = st_sensors_match_acpi_device(&client->dev); 849d317724SShrirang Bagul if ((ret < 0) || (ret >= ST_PRESS_MAX)) 859d317724SShrirang Bagul return -ENODEV; 869d317724SShrirang Bagul 879d317724SShrirang Bagul strncpy(client->name, st_press_id_table[ret].name, 889d317724SShrirang Bagul sizeof(client->name)); 899d317724SShrirang Bagul client->name[sizeof(client->name) - 1] = '\0'; 909d317724SShrirang Bagul } else if (!id) 919d317724SShrirang Bagul return -ENODEV; 92217494e5SDenis CIOCCA 93a1dcf429SDenis CIOCCA st_sensors_i2c_configure(indio_dev, client, press_data); 94217494e5SDenis CIOCCA 959d317724SShrirang Bagul ret = st_press_common_probe(indio_dev); 969d317724SShrirang Bagul if (ret < 0) 979d317724SShrirang Bagul return ret; 98217494e5SDenis CIOCCA 99217494e5SDenis CIOCCA return 0; 100217494e5SDenis CIOCCA } 101217494e5SDenis CIOCCA 102217494e5SDenis CIOCCA static int st_press_i2c_remove(struct i2c_client *client) 103217494e5SDenis CIOCCA { 104217494e5SDenis CIOCCA st_press_common_remove(i2c_get_clientdata(client)); 105217494e5SDenis CIOCCA 106217494e5SDenis CIOCCA return 0; 107217494e5SDenis CIOCCA } 108217494e5SDenis CIOCCA 109217494e5SDenis CIOCCA static struct i2c_driver st_press_driver = { 110217494e5SDenis CIOCCA .driver = { 111217494e5SDenis CIOCCA .name = "st-press-i2c", 1122d7768a8SLinus Walleij .of_match_table = of_match_ptr(st_press_of_match), 1139d317724SShrirang Bagul .acpi_match_table = ACPI_PTR(st_press_acpi_match), 114217494e5SDenis CIOCCA }, 115217494e5SDenis CIOCCA .probe = st_press_i2c_probe, 116217494e5SDenis CIOCCA .remove = st_press_i2c_remove, 117217494e5SDenis CIOCCA .id_table = st_press_id_table, 118217494e5SDenis CIOCCA }; 119217494e5SDenis CIOCCA module_i2c_driver(st_press_driver); 120217494e5SDenis CIOCCA 121217494e5SDenis CIOCCA MODULE_AUTHOR("Denis Ciocca <denis.ciocca@st.com>"); 122217494e5SDenis CIOCCA MODULE_DESCRIPTION("STMicroelectronics pressures i2c driver"); 123217494e5SDenis CIOCCA MODULE_LICENSE("GPL v2"); 124