Char/Misc driver fixes for 6.4-rc5

Here are a bunch of tiny char/misc/other driver fixes for 6.4-rc5 that
 resolve a number of reported issues.  Included in here are:
   - iio driver fixes
   - fpga driver fixes
   - test_firmware bugfixes
   - fastrpc driver tiny bugfixes
   - MAINTAINERS file updates for some subsystems
 
 All of these have been in linux-next this past week with no reported
 issues.
 
 Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
 -----BEGIN PGP SIGNATURE-----
 
 iG0EABECAC0WIQT0tgzFv3jCIUoxPcsxR9QN2y37KQUCZHxDNg8cZ3JlZ0Brcm9h
 aC5jb20ACgkQMUfUDdst+yl1ywCg0uz+E/GYKx5cP9chPFmbbaFwxH4AnRpn/kIH
 xz6nbAqSf7CBbtxmED11
 =4J1c
 -----END PGP SIGNATURE-----

Merge tag 'char-misc-6.4-rc5' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/char-misc

Pull char/misc driver fixes from Greg KH:
 "Here are a bunch of tiny char/misc/other driver fixes for 6.4-rc5 that
  resolve a number of reported issues. Included in here are:

   - iio driver fixes

   - fpga driver fixes

   - test_firmware bugfixes

   - fastrpc driver tiny bugfixes

   - MAINTAINERS file updates for some subsystems

  All of these have been in linux-next this past week with no reported
  issues"

* tag 'char-misc-6.4-rc5' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/char-misc: (34 commits)
  test_firmware: fix the memory leak of the allocated firmware buffer
  test_firmware: fix a memory leak with reqs buffer
  test_firmware: prevent race conditions by a correct implementation of locking
  firmware_loader: Fix a NULL vs IS_ERR() check
  MAINTAINERS: Vaibhav Gupta is the new ipack maintainer
  dt-bindings: fpga: replace Ivan Bornyakov maintainership
  MAINTAINERS: update Microchip MPF FPGA reviewers
  misc: fastrpc: reject new invocations during device removal
  misc: fastrpc: return -EPIPE to invocations on device removal
  misc: fastrpc: Reassign memory ownership only for remote heap
  misc: fastrpc: Pass proper scm arguments for secure map request
  iio: imu: inv_icm42600: fix timestamp reset
  iio: adc: ad_sigma_delta: Fix IRQ issue by setting IRQ_DISABLE_UNLAZY flag
  dt-bindings: iio: adc: renesas,rcar-gyroadc: Fix adi,ad7476 compatible value
  iio: dac: mcp4725: Fix i2c_master_send() return value handling
  iio: accel: kx022a fix irq getting
  iio: bu27034: Ensure reset is written
  iio: dac: build ad5758 driver when AD5758 is selected
  iio: addac: ad74413: fix resistance input processing
  iio: light: vcnl4035: fixed chip ID check
  ...
This commit is contained in:
Linus Torvalds 2023-06-04 08:32:30 -04:00
commit 209835e8ec
27 changed files with 297 additions and 117 deletions

View file

@ -7,7 +7,7 @@ $schema: http://devicetree.org/meta-schemas/core.yaml#
title: Lattice Slave SPI sysCONFIG FPGA manager title: Lattice Slave SPI sysCONFIG FPGA manager
maintainers: maintainers:
- Ivan Bornyakov <i.bornyakov@metrotek.ru> - Vladimir Georgiev <v.georgiev@metrotek.ru>
description: | description: |
Lattice sysCONFIG port, which is used for FPGA configuration, among others, Lattice sysCONFIG port, which is used for FPGA configuration, among others,

View file

@ -7,7 +7,7 @@ $schema: http://devicetree.org/meta-schemas/core.yaml#
title: Microchip Polarfire FPGA manager. title: Microchip Polarfire FPGA manager.
maintainers: maintainers:
- Ivan Bornyakov <i.bornyakov@metrotek.ru> - Vladimir Georgiev <v.georgiev@metrotek.ru>
description: description:
Device Tree Bindings for Microchip Polarfire FPGA Manager using slave SPI to Device Tree Bindings for Microchip Polarfire FPGA Manager using slave SPI to

View file

@ -39,6 +39,12 @@ properties:
power-domains: power-domains:
maxItems: 1 maxItems: 1
vref-supply:
description: |
External ADC reference voltage supply on VREFH pad. If VERID[MVI] is
set, there are additional, internal reference voltages selectable.
VREFH1 is always from VREFH pad.
"#io-channel-cells": "#io-channel-cells":
const: 1 const: 1
@ -72,6 +78,7 @@ examples:
assigned-clocks = <&clk IMX_SC_R_ADC_0>; assigned-clocks = <&clk IMX_SC_R_ADC_0>;
assigned-clock-rates = <24000000>; assigned-clock-rates = <24000000>;
power-domains = <&pd IMX_SC_R_ADC_0>; power-domains = <&pd IMX_SC_R_ADC_0>;
vref-supply = <&reg_1v8>;
#io-channel-cells = <1>; #io-channel-cells = <1>;
}; };
}; };

View file

@ -90,7 +90,7 @@ patternProperties:
of the MAX chips to the GyroADC, while MISO line of each Maxim of the MAX chips to the GyroADC, while MISO line of each Maxim
ADC connects to a shared input pin of the GyroADC. ADC connects to a shared input pin of the GyroADC.
enum: enum:
- adi,7476 - adi,ad7476
- fujitsu,mb88101a - fujitsu,mb88101a
- maxim,max1162 - maxim,max1162
- maxim,max11100 - maxim,max11100

View file

@ -10115,7 +10115,7 @@ S: Maintained
F: Documentation/process/kernel-docs.rst F: Documentation/process/kernel-docs.rst
INDUSTRY PACK SUBSYSTEM (IPACK) INDUSTRY PACK SUBSYSTEM (IPACK)
M: Samuel Iglesias Gonsalvez <siglesias@igalia.com> M: Vaibhav Gupta <vaibhavgupta40@gmail.com>
M: Jens Taprogge <jens.taprogge@taprogge.org> M: Jens Taprogge <jens.taprogge@taprogge.org>
M: Greg Kroah-Hartman <gregkh@linuxfoundation.org> M: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
L: industrypack-devel@lists.sourceforge.net L: industrypack-devel@lists.sourceforge.net
@ -13837,7 +13837,7 @@ F: drivers/tty/serial/8250/8250_pci1xxxx.c
MICROCHIP POLARFIRE FPGA DRIVERS MICROCHIP POLARFIRE FPGA DRIVERS
M: Conor Dooley <conor.dooley@microchip.com> M: Conor Dooley <conor.dooley@microchip.com>
R: Ivan Bornyakov <i.bornyakov@metrotek.ru> R: Vladimir Georgiev <v.georgiev@metrotek.ru>
L: linux-fpga@vger.kernel.org L: linux-fpga@vger.kernel.org
S: Supported S: Supported
F: Documentation/devicetree/bindings/fpga/microchip,mpf-spi-fpga-mgr.yaml F: Documentation/devicetree/bindings/fpga/microchip,mpf-spi-fpga-mgr.yaml

View file

@ -812,7 +812,7 @@ static void fw_log_firmware_info(const struct firmware *fw, const char *name, st
char *outbuf; char *outbuf;
alg = crypto_alloc_shash("sha256", 0, 0); alg = crypto_alloc_shash("sha256", 0, 0);
if (!alg) if (IS_ERR(alg))
return; return;
sha256buf = kmalloc(SHA256_DIGEST_SIZE, GFP_KERNEL); sha256buf = kmalloc(SHA256_DIGEST_SIZE, GFP_KERNEL);

View file

@ -1048,7 +1048,7 @@ int kx022a_probe_internal(struct device *dev)
data->ien_reg = KX022A_REG_INC4; data->ien_reg = KX022A_REG_INC4;
} else { } else {
irq = fwnode_irq_get_byname(fwnode, "INT2"); irq = fwnode_irq_get_byname(fwnode, "INT2");
if (irq <= 0) if (irq < 0)
return dev_err_probe(dev, irq, "No suitable IRQ\n"); return dev_err_probe(dev, irq, "No suitable IRQ\n");
data->inc_reg = KX022A_REG_INC5; data->inc_reg = KX022A_REG_INC5;

View file

@ -1291,12 +1291,12 @@ static int apply_acpi_orientation(struct iio_dev *indio_dev)
adev = ACPI_COMPANION(indio_dev->dev.parent); adev = ACPI_COMPANION(indio_dev->dev.parent);
if (!adev) if (!adev)
return 0; return -ENXIO;
/* Read _ONT data, which should be a package of 6 integers. */ /* Read _ONT data, which should be a package of 6 integers. */
status = acpi_evaluate_object(adev->handle, "_ONT", NULL, &buffer); status = acpi_evaluate_object(adev->handle, "_ONT", NULL, &buffer);
if (status == AE_NOT_FOUND) { if (status == AE_NOT_FOUND) {
return 0; return -ENXIO;
} else if (ACPI_FAILURE(status)) { } else if (ACPI_FAILURE(status)) {
dev_warn(&indio_dev->dev, "failed to execute _ONT: %d\n", dev_warn(&indio_dev->dev, "failed to execute _ONT: %d\n",
status); status);

View file

@ -1817,6 +1817,11 @@ static const struct clk_ops ad4130_int_clk_ops = {
.unprepare = ad4130_int_clk_unprepare, .unprepare = ad4130_int_clk_unprepare,
}; };
static void ad4130_clk_del_provider(void *of_node)
{
of_clk_del_provider(of_node);
}
static int ad4130_setup_int_clk(struct ad4130_state *st) static int ad4130_setup_int_clk(struct ad4130_state *st)
{ {
struct device *dev = &st->spi->dev; struct device *dev = &st->spi->dev;
@ -1824,6 +1829,7 @@ static int ad4130_setup_int_clk(struct ad4130_state *st)
struct clk_init_data init; struct clk_init_data init;
const char *clk_name; const char *clk_name;
struct clk *clk; struct clk *clk;
int ret;
if (st->int_pin_sel == AD4130_INT_PIN_CLK || if (st->int_pin_sel == AD4130_INT_PIN_CLK ||
st->mclk_sel != AD4130_MCLK_76_8KHZ) st->mclk_sel != AD4130_MCLK_76_8KHZ)
@ -1843,7 +1849,11 @@ static int ad4130_setup_int_clk(struct ad4130_state *st)
if (IS_ERR(clk)) if (IS_ERR(clk))
return PTR_ERR(clk); return PTR_ERR(clk);
return of_clk_add_provider(of_node, of_clk_src_simple_get, clk); ret = of_clk_add_provider(of_node, of_clk_src_simple_get, clk);
if (ret)
return ret;
return devm_add_action_or_reset(dev, ad4130_clk_del_provider, of_node);
} }
static int ad4130_setup(struct iio_dev *indio_dev) static int ad4130_setup(struct iio_dev *indio_dev)

View file

@ -897,10 +897,6 @@ static const struct iio_info ad7195_info = {
__AD719x_CHANNEL(_si, _channel1, -1, _address, NULL, IIO_VOLTAGE, \ __AD719x_CHANNEL(_si, _channel1, -1, _address, NULL, IIO_VOLTAGE, \
BIT(IIO_CHAN_INFO_SCALE), ad7192_calibsys_ext_info) BIT(IIO_CHAN_INFO_SCALE), ad7192_calibsys_ext_info)
#define AD719x_SHORTED_CHANNEL(_si, _channel1, _address) \
__AD719x_CHANNEL(_si, _channel1, -1, _address, "shorted", IIO_VOLTAGE, \
BIT(IIO_CHAN_INFO_SCALE), ad7192_calibsys_ext_info)
#define AD719x_TEMP_CHANNEL(_si, _address) \ #define AD719x_TEMP_CHANNEL(_si, _address) \
__AD719x_CHANNEL(_si, 0, -1, _address, NULL, IIO_TEMP, 0, NULL) __AD719x_CHANNEL(_si, 0, -1, _address, NULL, IIO_TEMP, 0, NULL)
@ -908,7 +904,7 @@ static const struct iio_chan_spec ad7192_channels[] = {
AD719x_DIFF_CHANNEL(0, 1, 2, AD7192_CH_AIN1P_AIN2M), AD719x_DIFF_CHANNEL(0, 1, 2, AD7192_CH_AIN1P_AIN2M),
AD719x_DIFF_CHANNEL(1, 3, 4, AD7192_CH_AIN3P_AIN4M), AD719x_DIFF_CHANNEL(1, 3, 4, AD7192_CH_AIN3P_AIN4M),
AD719x_TEMP_CHANNEL(2, AD7192_CH_TEMP), AD719x_TEMP_CHANNEL(2, AD7192_CH_TEMP),
AD719x_SHORTED_CHANNEL(3, 2, AD7192_CH_AIN2P_AIN2M), AD719x_DIFF_CHANNEL(3, 2, 2, AD7192_CH_AIN2P_AIN2M),
AD719x_CHANNEL(4, 1, AD7192_CH_AIN1), AD719x_CHANNEL(4, 1, AD7192_CH_AIN1),
AD719x_CHANNEL(5, 2, AD7192_CH_AIN2), AD719x_CHANNEL(5, 2, AD7192_CH_AIN2),
AD719x_CHANNEL(6, 3, AD7192_CH_AIN3), AD719x_CHANNEL(6, 3, AD7192_CH_AIN3),
@ -922,7 +918,7 @@ static const struct iio_chan_spec ad7193_channels[] = {
AD719x_DIFF_CHANNEL(2, 5, 6, AD7193_CH_AIN5P_AIN6M), AD719x_DIFF_CHANNEL(2, 5, 6, AD7193_CH_AIN5P_AIN6M),
AD719x_DIFF_CHANNEL(3, 7, 8, AD7193_CH_AIN7P_AIN8M), AD719x_DIFF_CHANNEL(3, 7, 8, AD7193_CH_AIN7P_AIN8M),
AD719x_TEMP_CHANNEL(4, AD7193_CH_TEMP), AD719x_TEMP_CHANNEL(4, AD7193_CH_TEMP),
AD719x_SHORTED_CHANNEL(5, 2, AD7193_CH_AIN2P_AIN2M), AD719x_DIFF_CHANNEL(5, 2, 2, AD7193_CH_AIN2P_AIN2M),
AD719x_CHANNEL(6, 1, AD7193_CH_AIN1), AD719x_CHANNEL(6, 1, AD7193_CH_AIN1),
AD719x_CHANNEL(7, 2, AD7193_CH_AIN2), AD719x_CHANNEL(7, 2, AD7193_CH_AIN2),
AD719x_CHANNEL(8, 3, AD7193_CH_AIN3), AD719x_CHANNEL(8, 3, AD7193_CH_AIN3),

View file

@ -584,6 +584,10 @@ static int devm_ad_sd_probe_trigger(struct device *dev, struct iio_dev *indio_de
init_completion(&sigma_delta->completion); init_completion(&sigma_delta->completion);
sigma_delta->irq_dis = true; sigma_delta->irq_dis = true;
/* the IRQ core clears IRQ_DISABLE_UNLAZY flag when freeing an IRQ */
irq_set_status_flags(sigma_delta->spi->irq, IRQ_DISABLE_UNLAZY);
ret = devm_request_irq(dev, sigma_delta->spi->irq, ret = devm_request_irq(dev, sigma_delta->spi->irq,
ad_sd_data_rdy_trig_poll, ad_sd_data_rdy_trig_poll,
sigma_delta->info->irq_flags | IRQF_NO_AUTOEN, sigma_delta->info->irq_flags | IRQF_NO_AUTOEN,

View file

@ -236,8 +236,7 @@ static int imx93_adc_read_raw(struct iio_dev *indio_dev,
{ {
struct imx93_adc *adc = iio_priv(indio_dev); struct imx93_adc *adc = iio_priv(indio_dev);
struct device *dev = adc->dev; struct device *dev = adc->dev;
long ret; int ret;
u32 vref_uv;
switch (mask) { switch (mask) {
case IIO_CHAN_INFO_RAW: case IIO_CHAN_INFO_RAW:
@ -253,10 +252,10 @@ static int imx93_adc_read_raw(struct iio_dev *indio_dev,
return IIO_VAL_INT; return IIO_VAL_INT;
case IIO_CHAN_INFO_SCALE: case IIO_CHAN_INFO_SCALE:
ret = vref_uv = regulator_get_voltage(adc->vref); ret = regulator_get_voltage(adc->vref);
if (ret < 0) if (ret < 0)
return ret; return ret;
*val = vref_uv / 1000; *val = ret / 1000;
*val2 = 12; *val2 = 12;
return IIO_VAL_FRACTIONAL_LOG2; return IIO_VAL_FRACTIONAL_LOG2;

View file

@ -19,6 +19,7 @@
#include <dt-bindings/iio/adc/mediatek,mt6370_adc.h> #include <dt-bindings/iio/adc/mediatek,mt6370_adc.h>
#define MT6370_REG_DEV_INFO 0x100
#define MT6370_REG_CHG_CTRL3 0x113 #define MT6370_REG_CHG_CTRL3 0x113
#define MT6370_REG_CHG_CTRL7 0x117 #define MT6370_REG_CHG_CTRL7 0x117
#define MT6370_REG_CHG_ADC 0x121 #define MT6370_REG_CHG_ADC 0x121
@ -27,6 +28,7 @@
#define MT6370_ADC_START_MASK BIT(0) #define MT6370_ADC_START_MASK BIT(0)
#define MT6370_ADC_IN_SEL_MASK GENMASK(7, 4) #define MT6370_ADC_IN_SEL_MASK GENMASK(7, 4)
#define MT6370_AICR_ICHG_MASK GENMASK(7, 2) #define MT6370_AICR_ICHG_MASK GENMASK(7, 2)
#define MT6370_VENID_MASK GENMASK(7, 4)
#define MT6370_AICR_100_mA 0x0 #define MT6370_AICR_100_mA 0x0
#define MT6370_AICR_150_mA 0x1 #define MT6370_AICR_150_mA 0x1
@ -47,6 +49,10 @@
#define ADC_CONV_TIME_MS 35 #define ADC_CONV_TIME_MS 35
#define ADC_CONV_POLLING_TIME_US 1000 #define ADC_CONV_POLLING_TIME_US 1000
#define MT6370_VID_RT5081 0x8
#define MT6370_VID_RT5081A 0xA
#define MT6370_VID_MT6370 0xE
struct mt6370_adc_data { struct mt6370_adc_data {
struct device *dev; struct device *dev;
struct regmap *regmap; struct regmap *regmap;
@ -55,6 +61,7 @@ struct mt6370_adc_data {
* from being read at the same time. * from being read at the same time.
*/ */
struct mutex adc_lock; struct mutex adc_lock;
unsigned int vid;
}; };
static int mt6370_adc_read_channel(struct mt6370_adc_data *priv, int chan, static int mt6370_adc_read_channel(struct mt6370_adc_data *priv, int chan,
@ -98,6 +105,30 @@ static int mt6370_adc_read_channel(struct mt6370_adc_data *priv, int chan,
return ret; return ret;
} }
static int mt6370_adc_get_ibus_scale(struct mt6370_adc_data *priv)
{
switch (priv->vid) {
case MT6370_VID_RT5081:
case MT6370_VID_RT5081A:
case MT6370_VID_MT6370:
return 3350;
default:
return 3875;
}
}
static int mt6370_adc_get_ibat_scale(struct mt6370_adc_data *priv)
{
switch (priv->vid) {
case MT6370_VID_RT5081:
case MT6370_VID_RT5081A:
case MT6370_VID_MT6370:
return 2680;
default:
return 3870;
}
}
static int mt6370_adc_read_scale(struct mt6370_adc_data *priv, static int mt6370_adc_read_scale(struct mt6370_adc_data *priv,
int chan, int *val1, int *val2) int chan, int *val1, int *val2)
{ {
@ -123,7 +154,7 @@ static int mt6370_adc_read_scale(struct mt6370_adc_data *priv,
case MT6370_AICR_250_mA: case MT6370_AICR_250_mA:
case MT6370_AICR_300_mA: case MT6370_AICR_300_mA:
case MT6370_AICR_350_mA: case MT6370_AICR_350_mA:
*val1 = 3350; *val1 = mt6370_adc_get_ibus_scale(priv);
break; break;
default: default:
*val1 = 5000; *val1 = 5000;
@ -150,7 +181,7 @@ static int mt6370_adc_read_scale(struct mt6370_adc_data *priv,
case MT6370_ICHG_600_mA: case MT6370_ICHG_600_mA:
case MT6370_ICHG_700_mA: case MT6370_ICHG_700_mA:
case MT6370_ICHG_800_mA: case MT6370_ICHG_800_mA:
*val1 = 2680; *val1 = mt6370_adc_get_ibat_scale(priv);
break; break;
default: default:
*val1 = 5000; *val1 = 5000;
@ -251,6 +282,20 @@ static const struct iio_chan_spec mt6370_adc_channels[] = {
MT6370_ADC_CHAN(TEMP_JC, IIO_TEMP, 12, BIT(IIO_CHAN_INFO_OFFSET)), MT6370_ADC_CHAN(TEMP_JC, IIO_TEMP, 12, BIT(IIO_CHAN_INFO_OFFSET)),
}; };
static int mt6370_get_vendor_info(struct mt6370_adc_data *priv)
{
unsigned int dev_info;
int ret;
ret = regmap_read(priv->regmap, MT6370_REG_DEV_INFO, &dev_info);
if (ret)
return ret;
priv->vid = FIELD_GET(MT6370_VENID_MASK, dev_info);
return 0;
}
static int mt6370_adc_probe(struct platform_device *pdev) static int mt6370_adc_probe(struct platform_device *pdev)
{ {
struct device *dev = &pdev->dev; struct device *dev = &pdev->dev;
@ -272,6 +317,10 @@ static int mt6370_adc_probe(struct platform_device *pdev)
priv->regmap = regmap; priv->regmap = regmap;
mutex_init(&priv->adc_lock); mutex_init(&priv->adc_lock);
ret = mt6370_get_vendor_info(priv);
if (ret)
return dev_err_probe(dev, ret, "Failed to get vid\n");
ret = regmap_write(priv->regmap, MT6370_REG_CHG_ADC, 0); ret = regmap_write(priv->regmap, MT6370_REG_CHG_ADC, 0);
if (ret) if (ret)
return dev_err_probe(dev, ret, "Failed to reset ADC\n"); return dev_err_probe(dev, ret, "Failed to reset ADC\n");

View file

@ -757,13 +757,13 @@ static int mxs_lradc_adc_probe(struct platform_device *pdev)
ret = mxs_lradc_adc_trigger_init(iio); ret = mxs_lradc_adc_trigger_init(iio);
if (ret) if (ret)
goto err_trig; return ret;
ret = iio_triggered_buffer_setup(iio, &iio_pollfunc_store_time, ret = iio_triggered_buffer_setup(iio, &iio_pollfunc_store_time,
&mxs_lradc_adc_trigger_handler, &mxs_lradc_adc_trigger_handler,
&mxs_lradc_adc_buffer_ops); &mxs_lradc_adc_buffer_ops);
if (ret) if (ret)
return ret; goto err_trig;
adc->vref_mv = mxs_lradc_adc_vref_mv[lradc->soc]; adc->vref_mv = mxs_lradc_adc_vref_mv[lradc->soc];
@ -801,9 +801,9 @@ static int mxs_lradc_adc_probe(struct platform_device *pdev)
err_dev: err_dev:
mxs_lradc_adc_hw_stop(adc); mxs_lradc_adc_hw_stop(adc);
mxs_lradc_adc_trigger_remove(iio);
err_trig:
iio_triggered_buffer_cleanup(iio); iio_triggered_buffer_cleanup(iio);
err_trig:
mxs_lradc_adc_trigger_remove(iio);
return ret; return ret;
} }
@ -814,8 +814,8 @@ static int mxs_lradc_adc_remove(struct platform_device *pdev)
iio_device_unregister(iio); iio_device_unregister(iio);
mxs_lradc_adc_hw_stop(adc); mxs_lradc_adc_hw_stop(adc);
mxs_lradc_adc_trigger_remove(iio);
iio_triggered_buffer_cleanup(iio); iio_triggered_buffer_cleanup(iio);
mxs_lradc_adc_trigger_remove(iio);
return 0; return 0;
} }

View file

@ -547,7 +547,7 @@ static int palmas_gpadc_read_raw(struct iio_dev *indio_dev,
int adc_chan = chan->channel; int adc_chan = chan->channel;
int ret = 0; int ret = 0;
if (adc_chan > PALMAS_ADC_CH_MAX) if (adc_chan >= PALMAS_ADC_CH_MAX)
return -EINVAL; return -EINVAL;
mutex_lock(&adc->lock); mutex_lock(&adc->lock);
@ -595,7 +595,7 @@ static int palmas_gpadc_read_event_config(struct iio_dev *indio_dev,
int adc_chan = chan->channel; int adc_chan = chan->channel;
int ret = 0; int ret = 0;
if (adc_chan > PALMAS_ADC_CH_MAX || type != IIO_EV_TYPE_THRESH) if (adc_chan >= PALMAS_ADC_CH_MAX || type != IIO_EV_TYPE_THRESH)
return -EINVAL; return -EINVAL;
mutex_lock(&adc->lock); mutex_lock(&adc->lock);
@ -684,7 +684,7 @@ static int palmas_gpadc_write_event_config(struct iio_dev *indio_dev,
int adc_chan = chan->channel; int adc_chan = chan->channel;
int ret; int ret;
if (adc_chan > PALMAS_ADC_CH_MAX || type != IIO_EV_TYPE_THRESH) if (adc_chan >= PALMAS_ADC_CH_MAX || type != IIO_EV_TYPE_THRESH)
return -EINVAL; return -EINVAL;
mutex_lock(&adc->lock); mutex_lock(&adc->lock);
@ -710,7 +710,7 @@ static int palmas_gpadc_read_event_value(struct iio_dev *indio_dev,
int adc_chan = chan->channel; int adc_chan = chan->channel;
int ret; int ret;
if (adc_chan > PALMAS_ADC_CH_MAX || type != IIO_EV_TYPE_THRESH) if (adc_chan >= PALMAS_ADC_CH_MAX || type != IIO_EV_TYPE_THRESH)
return -EINVAL; return -EINVAL;
mutex_lock(&adc->lock); mutex_lock(&adc->lock);
@ -744,7 +744,7 @@ static int palmas_gpadc_write_event_value(struct iio_dev *indio_dev,
int old; int old;
int ret; int ret;
if (adc_chan > PALMAS_ADC_CH_MAX || type != IIO_EV_TYPE_THRESH) if (adc_chan >= PALMAS_ADC_CH_MAX || type != IIO_EV_TYPE_THRESH)
return -EINVAL; return -EINVAL;
mutex_lock(&adc->lock); mutex_lock(&adc->lock);

View file

@ -2006,9 +2006,7 @@ static int stm32_adc_get_legacy_chan_count(struct iio_dev *indio_dev, struct stm
* to get the *real* number of channels. * to get the *real* number of channels.
*/ */
ret = device_property_count_u32(dev, "st,adc-diff-channels"); ret = device_property_count_u32(dev, "st,adc-diff-channels");
if (ret < 0) if (ret > 0) {
return ret;
ret /= (int)(sizeof(struct stm32_adc_diff_channel) / sizeof(u32)); ret /= (int)(sizeof(struct stm32_adc_diff_channel) / sizeof(u32));
if (ret > adc_info->max_channels) { if (ret > adc_info->max_channels) {
dev_err(&indio_dev->dev, "Bad st,adc-diff-channels?\n"); dev_err(&indio_dev->dev, "Bad st,adc-diff-channels?\n");
@ -2017,6 +2015,7 @@ static int stm32_adc_get_legacy_chan_count(struct iio_dev *indio_dev, struct stm
adc->num_diff = ret; adc->num_diff = ret;
num_channels += ret; num_channels += ret;
} }
}
/* Optional sample time is provided either for each, or all channels */ /* Optional sample time is provided either for each, or all channels */
adc->nsmps = device_property_count_u32(dev, "st,min-sample-time-nsecs"); adc->nsmps = device_property_count_u32(dev, "st,min-sample-time-nsecs");
@ -2037,6 +2036,7 @@ static int stm32_adc_legacy_chan_init(struct iio_dev *indio_dev,
struct stm32_adc_diff_channel diff[STM32_ADC_CH_MAX]; struct stm32_adc_diff_channel diff[STM32_ADC_CH_MAX];
struct device *dev = &indio_dev->dev; struct device *dev = &indio_dev->dev;
u32 num_diff = adc->num_diff; u32 num_diff = adc->num_diff;
int num_se = nchans - num_diff;
int size = num_diff * sizeof(*diff) / sizeof(u32); int size = num_diff * sizeof(*diff) / sizeof(u32);
int scan_index = 0, ret, i, c; int scan_index = 0, ret, i, c;
u32 smp = 0, smps[STM32_ADC_CH_MAX], chans[STM32_ADC_CH_MAX]; u32 smp = 0, smps[STM32_ADC_CH_MAX], chans[STM32_ADC_CH_MAX];
@ -2063,13 +2063,14 @@ static int stm32_adc_legacy_chan_init(struct iio_dev *indio_dev,
scan_index++; scan_index++;
} }
} }
if (num_se > 0) {
ret = device_property_read_u32_array(dev, "st,adc-channels", chans, ret = device_property_read_u32_array(dev, "st,adc-channels", chans, num_se);
nchans); if (ret) {
if (ret) dev_err(&indio_dev->dev, "Failed to get st,adc-channels %d\n", ret);
return ret; return ret;
}
for (c = 0; c < nchans; c++) { for (c = 0; c < num_se; c++) {
if (chans[c] >= adc_info->max_channels) { if (chans[c] >= adc_info->max_channels) {
dev_err(&indio_dev->dev, "Invalid channel %d\n", dev_err(&indio_dev->dev, "Invalid channel %d\n",
chans[c]); chans[c]);
@ -2079,7 +2080,8 @@ static int stm32_adc_legacy_chan_init(struct iio_dev *indio_dev,
/* Channel can't be configured both as single-ended & diff */ /* Channel can't be configured both as single-ended & diff */
for (i = 0; i < num_diff; i++) { for (i = 0; i < num_diff; i++) {
if (chans[c] == diff[i].vinp) { if (chans[c] == diff[i].vinp) {
dev_err(&indio_dev->dev, "channel %d misconfigured\n", chans[c]); dev_err(&indio_dev->dev, "channel %d misconfigured\n",
chans[c]);
return -EINVAL; return -EINVAL;
} }
} }
@ -2087,6 +2089,7 @@ static int stm32_adc_legacy_chan_init(struct iio_dev *indio_dev,
chans[c], 0, scan_index, false); chans[c], 0, scan_index, false);
scan_index++; scan_index++;
} }
}
if (adc->nsmps > 0) { if (adc->nsmps > 0) {
ret = device_property_read_u32_array(dev, "st,min-sample-time-nsecs", ret = device_property_read_u32_array(dev, "st,min-sample-time-nsecs",
@ -2306,7 +2309,7 @@ static int stm32_adc_chan_fw_init(struct iio_dev *indio_dev, bool timestamping)
if (legacy) if (legacy)
ret = stm32_adc_legacy_chan_init(indio_dev, adc, channels, ret = stm32_adc_legacy_chan_init(indio_dev, adc, channels,
num_channels); timestamping ? num_channels - 1 : num_channels);
else else
ret = stm32_adc_generic_chan_init(indio_dev, adc, channels); ret = stm32_adc_generic_chan_init(indio_dev, adc, channels);
if (ret < 0) if (ret < 0)

View file

@ -1007,7 +1007,7 @@ static int ad74413r_read_raw(struct iio_dev *indio_dev,
ret = ad74413r_get_single_adc_result(indio_dev, chan->channel, ret = ad74413r_get_single_adc_result(indio_dev, chan->channel,
val); val);
if (ret) if (ret < 0)
return ret; return ret;
ad74413r_adc_to_resistance_result(*val, val); ad74413r_adc_to_resistance_result(*val, val);

View file

@ -17,7 +17,7 @@ obj-$(CONFIG_AD5592R_BASE) += ad5592r-base.o
obj-$(CONFIG_AD5592R) += ad5592r.o obj-$(CONFIG_AD5592R) += ad5592r.o
obj-$(CONFIG_AD5593R) += ad5593r.o obj-$(CONFIG_AD5593R) += ad5593r.o
obj-$(CONFIG_AD5755) += ad5755.o obj-$(CONFIG_AD5755) += ad5755.o
obj-$(CONFIG_AD5755) += ad5758.o obj-$(CONFIG_AD5758) += ad5758.o
obj-$(CONFIG_AD5761) += ad5761.o obj-$(CONFIG_AD5761) += ad5761.o
obj-$(CONFIG_AD5764) += ad5764.o obj-$(CONFIG_AD5764) += ad5764.o
obj-$(CONFIG_AD5766) += ad5766.o obj-$(CONFIG_AD5766) += ad5766.o

View file

@ -47,12 +47,18 @@ static int mcp4725_suspend(struct device *dev)
struct mcp4725_data *data = iio_priv(i2c_get_clientdata( struct mcp4725_data *data = iio_priv(i2c_get_clientdata(
to_i2c_client(dev))); to_i2c_client(dev)));
u8 outbuf[2]; u8 outbuf[2];
int ret;
outbuf[0] = (data->powerdown_mode + 1) << 4; outbuf[0] = (data->powerdown_mode + 1) << 4;
outbuf[1] = 0; outbuf[1] = 0;
data->powerdown = true; data->powerdown = true;
return i2c_master_send(data->client, outbuf, 2); ret = i2c_master_send(data->client, outbuf, 2);
if (ret < 0)
return ret;
else if (ret != 2)
return -EIO;
return 0;
} }
static int mcp4725_resume(struct device *dev) static int mcp4725_resume(struct device *dev)
@ -60,13 +66,19 @@ static int mcp4725_resume(struct device *dev)
struct mcp4725_data *data = iio_priv(i2c_get_clientdata( struct mcp4725_data *data = iio_priv(i2c_get_clientdata(
to_i2c_client(dev))); to_i2c_client(dev)));
u8 outbuf[2]; u8 outbuf[2];
int ret;
/* restore previous DAC value */ /* restore previous DAC value */
outbuf[0] = (data->dac_value >> 8) & 0xf; outbuf[0] = (data->dac_value >> 8) & 0xf;
outbuf[1] = data->dac_value & 0xff; outbuf[1] = data->dac_value & 0xff;
data->powerdown = false; data->powerdown = false;
return i2c_master_send(data->client, outbuf, 2); ret = i2c_master_send(data->client, outbuf, 2);
if (ret < 0)
return ret;
else if (ret != 2)
return -EIO;
return 0;
} }
static DEFINE_SIMPLE_DEV_PM_OPS(mcp4725_pm_ops, mcp4725_suspend, static DEFINE_SIMPLE_DEV_PM_OPS(mcp4725_pm_ops, mcp4725_suspend,
mcp4725_resume); mcp4725_resume);

View file

@ -275,9 +275,14 @@ static int inv_icm42600_buffer_preenable(struct iio_dev *indio_dev)
{ {
struct inv_icm42600_state *st = iio_device_get_drvdata(indio_dev); struct inv_icm42600_state *st = iio_device_get_drvdata(indio_dev);
struct device *dev = regmap_get_device(st->map); struct device *dev = regmap_get_device(st->map);
struct inv_icm42600_timestamp *ts = iio_priv(indio_dev);
pm_runtime_get_sync(dev); pm_runtime_get_sync(dev);
mutex_lock(&st->lock);
inv_icm42600_timestamp_reset(ts);
mutex_unlock(&st->lock);
return 0; return 0;
} }
@ -375,7 +380,6 @@ static int inv_icm42600_buffer_postdisable(struct iio_dev *indio_dev)
struct device *dev = regmap_get_device(st->map); struct device *dev = regmap_get_device(st->map);
unsigned int sensor; unsigned int sensor;
unsigned int *watermark; unsigned int *watermark;
struct inv_icm42600_timestamp *ts;
struct inv_icm42600_sensor_conf conf = INV_ICM42600_SENSOR_CONF_INIT; struct inv_icm42600_sensor_conf conf = INV_ICM42600_SENSOR_CONF_INIT;
unsigned int sleep_temp = 0; unsigned int sleep_temp = 0;
unsigned int sleep_sensor = 0; unsigned int sleep_sensor = 0;
@ -385,11 +389,9 @@ static int inv_icm42600_buffer_postdisable(struct iio_dev *indio_dev)
if (indio_dev == st->indio_gyro) { if (indio_dev == st->indio_gyro) {
sensor = INV_ICM42600_SENSOR_GYRO; sensor = INV_ICM42600_SENSOR_GYRO;
watermark = &st->fifo.watermark.gyro; watermark = &st->fifo.watermark.gyro;
ts = iio_priv(st->indio_gyro);
} else if (indio_dev == st->indio_accel) { } else if (indio_dev == st->indio_accel) {
sensor = INV_ICM42600_SENSOR_ACCEL; sensor = INV_ICM42600_SENSOR_ACCEL;
watermark = &st->fifo.watermark.accel; watermark = &st->fifo.watermark.accel;
ts = iio_priv(st->indio_accel);
} else { } else {
return -EINVAL; return -EINVAL;
} }
@ -417,8 +419,6 @@ static int inv_icm42600_buffer_postdisable(struct iio_dev *indio_dev)
if (!st->fifo.on) if (!st->fifo.on)
ret = inv_icm42600_set_temp_conf(st, false, &sleep_temp); ret = inv_icm42600_set_temp_conf(st, false, &sleep_temp);
inv_icm42600_timestamp_reset(ts);
out_unlock: out_unlock:
mutex_unlock(&st->lock); mutex_unlock(&st->lock);

View file

@ -337,6 +337,17 @@ static int iio_gts_build_avail_scale_table(struct iio_gts *gts)
return ret; return ret;
} }
static void iio_gts_us_to_int_micro(int *time_us, int *int_micro_times,
int num_times)
{
int i;
for (i = 0; i < num_times; i++) {
int_micro_times[i * 2] = time_us[i] / 1000000;
int_micro_times[i * 2 + 1] = time_us[i] % 1000000;
}
}
/** /**
* iio_gts_build_avail_time_table - build table of available integration times * iio_gts_build_avail_time_table - build table of available integration times
* @gts: Gain time scale descriptor * @gts: Gain time scale descriptor
@ -351,7 +362,7 @@ static int iio_gts_build_avail_scale_table(struct iio_gts *gts)
*/ */
static int iio_gts_build_avail_time_table(struct iio_gts *gts) static int iio_gts_build_avail_time_table(struct iio_gts *gts)
{ {
int *times, i, j, idx = 0; int *times, i, j, idx = 0, *int_micro_times;
if (!gts->num_itime) if (!gts->num_itime)
return 0; return 0;
@ -378,13 +389,24 @@ static int iio_gts_build_avail_time_table(struct iio_gts *gts)
} }
} }
} }
gts->avail_time_tables = times;
/* create a list of times formatted as list of IIO_VAL_INT_PLUS_MICRO */
int_micro_times = kcalloc(idx, sizeof(int) * 2, GFP_KERNEL);
if (int_micro_times) {
/* /*
* This is just to survive a unlikely corner-case where times in the * This is just to survive a unlikely corner-case where times in
* given time table were not unique. Else we could just trust the * the given time table were not unique. Else we could just
* gts->num_itime. * trust the gts->num_itime.
*/ */
gts->num_avail_time_tables = idx; gts->num_avail_time_tables = idx;
iio_gts_us_to_int_micro(times, int_micro_times, idx);
}
gts->avail_time_tables = int_micro_times;
kfree(times);
if (!int_micro_times)
return -ENOMEM;
return 0; return 0;
} }
@ -683,8 +705,8 @@ int iio_gts_avail_times(struct iio_gts *gts, const int **vals, int *type,
return -EINVAL; return -EINVAL;
*vals = gts->avail_time_tables; *vals = gts->avail_time_tables;
*type = IIO_VAL_INT; *type = IIO_VAL_INT_PLUS_MICRO;
*length = gts->num_avail_time_tables; *length = gts->num_avail_time_tables * 2;
return IIO_AVAIL_LIST; return IIO_AVAIL_LIST;
} }

View file

@ -231,6 +231,9 @@ struct bu27034_result {
static const struct regmap_range bu27034_volatile_ranges[] = { static const struct regmap_range bu27034_volatile_ranges[] = {
{ {
.range_min = BU27034_REG_SYSTEM_CONTROL,
.range_max = BU27034_REG_SYSTEM_CONTROL,
}, {
.range_min = BU27034_REG_MODE_CONTROL4, .range_min = BU27034_REG_MODE_CONTROL4,
.range_max = BU27034_REG_MODE_CONTROL4, .range_max = BU27034_REG_MODE_CONTROL4,
}, { }, {
@ -1167,11 +1170,12 @@ static int bu27034_read_raw(struct iio_dev *idev,
switch (mask) { switch (mask) {
case IIO_CHAN_INFO_INT_TIME: case IIO_CHAN_INFO_INT_TIME:
*val = bu27034_get_int_time(data); *val = 0;
if (*val < 0) *val2 = bu27034_get_int_time(data);
return *val; if (*val2 < 0)
return *val2;
return IIO_VAL_INT; return IIO_VAL_INT_PLUS_MICRO;
case IIO_CHAN_INFO_SCALE: case IIO_CHAN_INFO_SCALE:
return bu27034_get_scale(data, chan->channel, val, val2); return bu27034_get_scale(data, chan->channel, val, val2);
@ -1229,7 +1233,10 @@ static int bu27034_write_raw(struct iio_dev *idev,
ret = bu27034_set_scale(data, chan->channel, val, val2); ret = bu27034_set_scale(data, chan->channel, val, val2);
break; break;
case IIO_CHAN_INFO_INT_TIME: case IIO_CHAN_INFO_INT_TIME:
ret = bu27034_try_set_int_time(data, val); if (!val)
ret = bu27034_try_set_int_time(data, val2);
else
ret = -EINVAL;
break; break;
default: default:
ret = -EINVAL; ret = -EINVAL;
@ -1268,12 +1275,19 @@ static int bu27034_chip_init(struct bu27034_data *data)
int ret, sel; int ret, sel;
/* Reset */ /* Reset */
ret = regmap_update_bits(data->regmap, BU27034_REG_SYSTEM_CONTROL, ret = regmap_write_bits(data->regmap, BU27034_REG_SYSTEM_CONTROL,
BU27034_MASK_SW_RESET, BU27034_MASK_SW_RESET); BU27034_MASK_SW_RESET, BU27034_MASK_SW_RESET);
if (ret) if (ret)
return dev_err_probe(data->dev, ret, "Sensor reset failed\n"); return dev_err_probe(data->dev, ret, "Sensor reset failed\n");
msleep(1); msleep(1);
ret = regmap_reinit_cache(data->regmap, &bu27034_regmap);
if (ret) {
dev_err(data->dev, "Failed to reinit reg cache\n");
return ret;
}
/* /*
* Read integration time here to ensure it is in regmap cache. We do * Read integration time here to ensure it is in regmap cache. We do
* this to speed-up the int-time acquisition in the start of the buffer * this to speed-up the int-time acquisition in the start of the buffer

View file

@ -8,6 +8,7 @@
* TODO: Proximity * TODO: Proximity
*/ */
#include <linux/bitops.h> #include <linux/bitops.h>
#include <linux/bitfield.h>
#include <linux/i2c.h> #include <linux/i2c.h>
#include <linux/module.h> #include <linux/module.h>
#include <linux/pm_runtime.h> #include <linux/pm_runtime.h>
@ -42,6 +43,7 @@
#define VCNL4035_ALS_PERS_MASK GENMASK(3, 2) #define VCNL4035_ALS_PERS_MASK GENMASK(3, 2)
#define VCNL4035_INT_ALS_IF_H_MASK BIT(12) #define VCNL4035_INT_ALS_IF_H_MASK BIT(12)
#define VCNL4035_INT_ALS_IF_L_MASK BIT(13) #define VCNL4035_INT_ALS_IF_L_MASK BIT(13)
#define VCNL4035_DEV_ID_MASK GENMASK(7, 0)
/* Default values */ /* Default values */
#define VCNL4035_MODE_ALS_ENABLE BIT(0) #define VCNL4035_MODE_ALS_ENABLE BIT(0)
@ -413,6 +415,7 @@ static int vcnl4035_init(struct vcnl4035_data *data)
return ret; return ret;
} }
id = FIELD_GET(VCNL4035_DEV_ID_MASK, id);
if (id != VCNL4035_DEV_ID_VAL) { if (id != VCNL4035_DEV_ID_VAL) {
dev_err(&data->client->dev, "Wrong id, got %x, expected %x\n", dev_err(&data->client->dev, "Wrong id, got %x, expected %x\n",
id, VCNL4035_DEV_ID_VAL); id, VCNL4035_DEV_ID_VAL);

View file

@ -296,12 +296,13 @@ static int tmag5273_read_raw(struct iio_dev *indio_dev,
return ret; return ret;
ret = tmag5273_get_measure(data, &t, &x, &y, &z, &angle, &magnitude); ret = tmag5273_get_measure(data, &t, &x, &y, &z, &angle, &magnitude);
if (ret)
return ret;
pm_runtime_mark_last_busy(data->dev); pm_runtime_mark_last_busy(data->dev);
pm_runtime_put_autosuspend(data->dev); pm_runtime_put_autosuspend(data->dev);
if (ret)
return ret;
switch (chan->address) { switch (chan->address) {
case TEMPERATURE: case TEMPERATURE:
*val = t; *val = t;

View file

@ -316,12 +316,14 @@ static void fastrpc_free_map(struct kref *ref)
if (map->table) { if (map->table) {
if (map->attr & FASTRPC_ATTR_SECUREMAP) { if (map->attr & FASTRPC_ATTR_SECUREMAP) {
struct qcom_scm_vmperm perm; struct qcom_scm_vmperm perm;
int vmid = map->fl->cctx->vmperms[0].vmid;
u64 src_perms = BIT(QCOM_SCM_VMID_HLOS) | BIT(vmid);
int err = 0; int err = 0;
perm.vmid = QCOM_SCM_VMID_HLOS; perm.vmid = QCOM_SCM_VMID_HLOS;
perm.perm = QCOM_SCM_PERM_RWX; perm.perm = QCOM_SCM_PERM_RWX;
err = qcom_scm_assign_mem(map->phys, map->size, err = qcom_scm_assign_mem(map->phys, map->size,
&map->fl->cctx->perms, &perm, 1); &src_perms, &perm, 1);
if (err) { if (err) {
dev_err(map->fl->sctx->dev, "Failed to assign memory phys 0x%llx size 0x%llx err %d", dev_err(map->fl->sctx->dev, "Failed to assign memory phys 0x%llx size 0x%llx err %d",
map->phys, map->size, err); map->phys, map->size, err);
@ -787,8 +789,12 @@ static int fastrpc_map_create(struct fastrpc_user *fl, int fd,
goto map_err; goto map_err;
} }
if (attr & FASTRPC_ATTR_SECUREMAP) {
map->phys = sg_phys(map->table->sgl);
} else {
map->phys = sg_dma_address(map->table->sgl); map->phys = sg_dma_address(map->table->sgl);
map->phys += ((u64)fl->sctx->sid << 32); map->phys += ((u64)fl->sctx->sid << 32);
}
map->size = len; map->size = len;
map->va = sg_virt(map->table->sgl); map->va = sg_virt(map->table->sgl);
map->len = len; map->len = len;
@ -798,9 +804,15 @@ static int fastrpc_map_create(struct fastrpc_user *fl, int fd,
* If subsystem VMIDs are defined in DTSI, then do * If subsystem VMIDs are defined in DTSI, then do
* hyp_assign from HLOS to those VM(s) * hyp_assign from HLOS to those VM(s)
*/ */
u64 src_perms = BIT(QCOM_SCM_VMID_HLOS);
struct qcom_scm_vmperm dst_perms[2] = {0};
dst_perms[0].vmid = QCOM_SCM_VMID_HLOS;
dst_perms[0].perm = QCOM_SCM_PERM_RW;
dst_perms[1].vmid = fl->cctx->vmperms[0].vmid;
dst_perms[1].perm = QCOM_SCM_PERM_RWX;
map->attr = attr; map->attr = attr;
err = qcom_scm_assign_mem(map->phys, (u64)map->size, &fl->cctx->perms, err = qcom_scm_assign_mem(map->phys, (u64)map->size, &src_perms, dst_perms, 2);
fl->cctx->vmperms, fl->cctx->vmcount);
if (err) { if (err) {
dev_err(sess->dev, "Failed to assign memory with phys 0x%llx size 0x%llx err %d", dev_err(sess->dev, "Failed to assign memory with phys 0x%llx size 0x%llx err %d",
map->phys, map->size, err); map->phys, map->size, err);
@ -1892,7 +1904,7 @@ static int fastrpc_req_mmap(struct fastrpc_user *fl, char __user *argp)
req.vaddrout = rsp_msg.vaddr; req.vaddrout = rsp_msg.vaddr;
/* Add memory to static PD pool, protection thru hypervisor */ /* Add memory to static PD pool, protection thru hypervisor */
if (req.flags != ADSP_MMAP_REMOTE_HEAP_ADDR && fl->cctx->vmcount) { if (req.flags == ADSP_MMAP_REMOTE_HEAP_ADDR && fl->cctx->vmcount) {
struct qcom_scm_vmperm perm; struct qcom_scm_vmperm perm;
perm.vmid = QCOM_SCM_VMID_HLOS; perm.vmid = QCOM_SCM_VMID_HLOS;
@ -2337,8 +2349,10 @@ static void fastrpc_notify_users(struct fastrpc_user *user)
struct fastrpc_invoke_ctx *ctx; struct fastrpc_invoke_ctx *ctx;
spin_lock(&user->lock); spin_lock(&user->lock);
list_for_each_entry(ctx, &user->pending, node) list_for_each_entry(ctx, &user->pending, node) {
ctx->retval = -EPIPE;
complete(&ctx->work); complete(&ctx->work);
}
spin_unlock(&user->lock); spin_unlock(&user->lock);
} }
@ -2349,7 +2363,9 @@ static void fastrpc_rpmsg_remove(struct rpmsg_device *rpdev)
struct fastrpc_user *user; struct fastrpc_user *user;
unsigned long flags; unsigned long flags;
/* No invocations past this point */
spin_lock_irqsave(&cctx->lock, flags); spin_lock_irqsave(&cctx->lock, flags);
cctx->rpdev = NULL;
list_for_each_entry(user, &cctx->users, user) list_for_each_entry(user, &cctx->users, user)
fastrpc_notify_users(user); fastrpc_notify_users(user);
spin_unlock_irqrestore(&cctx->lock, flags); spin_unlock_irqrestore(&cctx->lock, flags);
@ -2368,7 +2384,6 @@ static void fastrpc_rpmsg_remove(struct rpmsg_device *rpdev)
of_platform_depopulate(&rpdev->dev); of_platform_depopulate(&rpdev->dev);
cctx->rpdev = NULL;
fastrpc_channel_ctx_put(cctx); fastrpc_channel_ctx_put(cctx);
} }

View file

@ -135,7 +135,7 @@ static inline int iio_gts_find_int_time_by_sel(struct iio_gts *gts, int sel)
/** /**
* iio_gts_find_sel_by_int_time - find selector matching integration time * iio_gts_find_sel_by_int_time - find selector matching integration time
* @gts: Gain time scale descriptor * @gts: Gain time scale descriptor
* @gain: HW-gain for which matching selector is searched for * @time: Integration time for which matching selector is searched for
* *
* Return: a selector matching given integration time or -EINVAL if * Return: a selector matching given integration time or -EINVAL if
* selector was not found. * selector was not found.

View file

@ -45,6 +45,7 @@ struct test_batched_req {
bool sent; bool sent;
const struct firmware *fw; const struct firmware *fw;
const char *name; const char *name;
const char *fw_buf;
struct completion completion; struct completion completion;
struct task_struct *task; struct task_struct *task;
struct device *dev; struct device *dev;
@ -175,8 +176,14 @@ static void __test_release_all_firmware(void)
for (i = 0; i < test_fw_config->num_requests; i++) { for (i = 0; i < test_fw_config->num_requests; i++) {
req = &test_fw_config->reqs[i]; req = &test_fw_config->reqs[i];
if (req->fw) if (req->fw) {
if (req->fw_buf) {
kfree_const(req->fw_buf);
req->fw_buf = NULL;
}
release_firmware(req->fw); release_firmware(req->fw);
req->fw = NULL;
}
} }
vfree(test_fw_config->reqs); vfree(test_fw_config->reqs);
@ -353,16 +360,26 @@ static ssize_t config_test_show_str(char *dst,
return len; return len;
} }
static inline int __test_dev_config_update_bool(const char *buf, size_t size,
bool *cfg)
{
int ret;
if (kstrtobool(buf, cfg) < 0)
ret = -EINVAL;
else
ret = size;
return ret;
}
static int test_dev_config_update_bool(const char *buf, size_t size, static int test_dev_config_update_bool(const char *buf, size_t size,
bool *cfg) bool *cfg)
{ {
int ret; int ret;
mutex_lock(&test_fw_mutex); mutex_lock(&test_fw_mutex);
if (kstrtobool(buf, cfg) < 0) ret = __test_dev_config_update_bool(buf, size, cfg);
ret = -EINVAL;
else
ret = size;
mutex_unlock(&test_fw_mutex); mutex_unlock(&test_fw_mutex);
return ret; return ret;
@ -373,7 +390,8 @@ static ssize_t test_dev_config_show_bool(char *buf, bool val)
return snprintf(buf, PAGE_SIZE, "%d\n", val); return snprintf(buf, PAGE_SIZE, "%d\n", val);
} }
static int test_dev_config_update_size_t(const char *buf, static int __test_dev_config_update_size_t(
const char *buf,
size_t size, size_t size,
size_t *cfg) size_t *cfg)
{ {
@ -384,9 +402,7 @@ static int test_dev_config_update_size_t(const char *buf,
if (ret) if (ret)
return ret; return ret;
mutex_lock(&test_fw_mutex);
*(size_t *)cfg = new; *(size_t *)cfg = new;
mutex_unlock(&test_fw_mutex);
/* Always return full write size even if we didn't consume all */ /* Always return full write size even if we didn't consume all */
return size; return size;
@ -402,7 +418,7 @@ static ssize_t test_dev_config_show_int(char *buf, int val)
return snprintf(buf, PAGE_SIZE, "%d\n", val); return snprintf(buf, PAGE_SIZE, "%d\n", val);
} }
static int test_dev_config_update_u8(const char *buf, size_t size, u8 *cfg) static int __test_dev_config_update_u8(const char *buf, size_t size, u8 *cfg)
{ {
u8 val; u8 val;
int ret; int ret;
@ -411,14 +427,23 @@ static int test_dev_config_update_u8(const char *buf, size_t size, u8 *cfg)
if (ret) if (ret)
return ret; return ret;
mutex_lock(&test_fw_mutex);
*(u8 *)cfg = val; *(u8 *)cfg = val;
mutex_unlock(&test_fw_mutex);
/* Always return full write size even if we didn't consume all */ /* Always return full write size even if we didn't consume all */
return size; return size;
} }
static int test_dev_config_update_u8(const char *buf, size_t size, u8 *cfg)
{
int ret;
mutex_lock(&test_fw_mutex);
ret = __test_dev_config_update_u8(buf, size, cfg);
mutex_unlock(&test_fw_mutex);
return ret;
}
static ssize_t test_dev_config_show_u8(char *buf, u8 val) static ssize_t test_dev_config_show_u8(char *buf, u8 val)
{ {
return snprintf(buf, PAGE_SIZE, "%u\n", val); return snprintf(buf, PAGE_SIZE, "%u\n", val);
@ -471,10 +496,10 @@ static ssize_t config_num_requests_store(struct device *dev,
mutex_unlock(&test_fw_mutex); mutex_unlock(&test_fw_mutex);
goto out; goto out;
} }
mutex_unlock(&test_fw_mutex);
rc = test_dev_config_update_u8(buf, count, rc = __test_dev_config_update_u8(buf, count,
&test_fw_config->num_requests); &test_fw_config->num_requests);
mutex_unlock(&test_fw_mutex);
out: out:
return rc; return rc;
@ -518,10 +543,10 @@ static ssize_t config_buf_size_store(struct device *dev,
mutex_unlock(&test_fw_mutex); mutex_unlock(&test_fw_mutex);
goto out; goto out;
} }
mutex_unlock(&test_fw_mutex);
rc = test_dev_config_update_size_t(buf, count, rc = __test_dev_config_update_size_t(buf, count,
&test_fw_config->buf_size); &test_fw_config->buf_size);
mutex_unlock(&test_fw_mutex);
out: out:
return rc; return rc;
@ -548,10 +573,10 @@ static ssize_t config_file_offset_store(struct device *dev,
mutex_unlock(&test_fw_mutex); mutex_unlock(&test_fw_mutex);
goto out; goto out;
} }
mutex_unlock(&test_fw_mutex);
rc = test_dev_config_update_size_t(buf, count, rc = __test_dev_config_update_size_t(buf, count,
&test_fw_config->file_offset); &test_fw_config->file_offset);
mutex_unlock(&test_fw_mutex);
out: out:
return rc; return rc;
@ -652,6 +677,8 @@ static ssize_t trigger_request_store(struct device *dev,
mutex_lock(&test_fw_mutex); mutex_lock(&test_fw_mutex);
release_firmware(test_firmware); release_firmware(test_firmware);
if (test_fw_config->reqs)
__test_release_all_firmware();
test_firmware = NULL; test_firmware = NULL;
rc = request_firmware(&test_firmware, name, dev); rc = request_firmware(&test_firmware, name, dev);
if (rc) { if (rc) {
@ -752,6 +779,8 @@ static ssize_t trigger_async_request_store(struct device *dev,
mutex_lock(&test_fw_mutex); mutex_lock(&test_fw_mutex);
release_firmware(test_firmware); release_firmware(test_firmware);
test_firmware = NULL; test_firmware = NULL;
if (test_fw_config->reqs)
__test_release_all_firmware();
rc = request_firmware_nowait(THIS_MODULE, 1, name, dev, GFP_KERNEL, rc = request_firmware_nowait(THIS_MODULE, 1, name, dev, GFP_KERNEL,
NULL, trigger_async_request_cb); NULL, trigger_async_request_cb);
if (rc) { if (rc) {
@ -794,6 +823,8 @@ static ssize_t trigger_custom_fallback_store(struct device *dev,
mutex_lock(&test_fw_mutex); mutex_lock(&test_fw_mutex);
release_firmware(test_firmware); release_firmware(test_firmware);
if (test_fw_config->reqs)
__test_release_all_firmware();
test_firmware = NULL; test_firmware = NULL;
rc = request_firmware_nowait(THIS_MODULE, FW_ACTION_NOUEVENT, name, rc = request_firmware_nowait(THIS_MODULE, FW_ACTION_NOUEVENT, name,
dev, GFP_KERNEL, NULL, dev, GFP_KERNEL, NULL,
@ -856,6 +887,8 @@ static int test_fw_run_batch_request(void *data)
test_fw_config->buf_size); test_fw_config->buf_size);
if (!req->fw) if (!req->fw)
kfree(test_buf); kfree(test_buf);
else
req->fw_buf = test_buf;
} else { } else {
req->rc = test_fw_config->req_firmware(&req->fw, req->rc = test_fw_config->req_firmware(&req->fw,
req->name, req->name,
@ -895,6 +928,11 @@ static ssize_t trigger_batched_requests_store(struct device *dev,
mutex_lock(&test_fw_mutex); mutex_lock(&test_fw_mutex);
if (test_fw_config->reqs) {
rc = -EBUSY;
goto out_bail;
}
test_fw_config->reqs = test_fw_config->reqs =
vzalloc(array3_size(sizeof(struct test_batched_req), vzalloc(array3_size(sizeof(struct test_batched_req),
test_fw_config->num_requests, 2)); test_fw_config->num_requests, 2));
@ -911,6 +949,7 @@ static ssize_t trigger_batched_requests_store(struct device *dev,
req->fw = NULL; req->fw = NULL;
req->idx = i; req->idx = i;
req->name = test_fw_config->name; req->name = test_fw_config->name;
req->fw_buf = NULL;
req->dev = dev; req->dev = dev;
init_completion(&req->completion); init_completion(&req->completion);
req->task = kthread_run(test_fw_run_batch_request, req, req->task = kthread_run(test_fw_run_batch_request, req,
@ -993,6 +1032,11 @@ ssize_t trigger_batched_requests_async_store(struct device *dev,
mutex_lock(&test_fw_mutex); mutex_lock(&test_fw_mutex);
if (test_fw_config->reqs) {
rc = -EBUSY;
goto out_bail;
}
test_fw_config->reqs = test_fw_config->reqs =
vzalloc(array3_size(sizeof(struct test_batched_req), vzalloc(array3_size(sizeof(struct test_batched_req),
test_fw_config->num_requests, 2)); test_fw_config->num_requests, 2));
@ -1010,6 +1054,7 @@ ssize_t trigger_batched_requests_async_store(struct device *dev,
for (i = 0; i < test_fw_config->num_requests; i++) { for (i = 0; i < test_fw_config->num_requests; i++) {
req = &test_fw_config->reqs[i]; req = &test_fw_config->reqs[i];
req->name = test_fw_config->name; req->name = test_fw_config->name;
req->fw_buf = NULL;
req->fw = NULL; req->fw = NULL;
req->idx = i; req->idx = i;
init_completion(&req->completion); init_completion(&req->completion);