Merge branch 'for-upstream' of git://git.kernel.org/pub/scm/linux/kernel/git/bluetooth/bluetooth-next
Johan Hedberg says: ==================== pull request: bluetooth-next 2015-03-19 This wont the last 4.1 bluetooth-next pull request, but we've piled up enough patches in less than a week that I wanted to save you from a single huge "last-minute" pull somewhere closer to the merge window. The main changes are: - Simultaneous LE & BR/EDR discovery support for HW that can do it - Complete LE OOB pairing support - More fine-grained mgmt-command access control (normal user can now do harmless read-only operations). - Added RF power amplifier support in cc2520 ieee802154 driver - Some cleanups/fixes in ieee802154 code Please let me know if there are any issues pulling. Thanks. ==================== Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
@@ -325,7 +325,7 @@ at86rf230_read_subreg(struct at86rf230_local *lp,
|
||||
int rc;
|
||||
|
||||
rc = __at86rf230_read(lp, addr, data);
|
||||
if (rc > 0)
|
||||
if (!rc)
|
||||
*data = (*data & mask) >> shift;
|
||||
|
||||
return rc;
|
||||
|
@@ -714,11 +714,45 @@ static irqreturn_t cc2520_sfd_isr(int irq, void *data)
|
||||
return IRQ_HANDLED;
|
||||
}
|
||||
|
||||
static int cc2520_get_platform_data(struct spi_device *spi,
|
||||
struct cc2520_platform_data *pdata)
|
||||
{
|
||||
struct device_node *np = spi->dev.of_node;
|
||||
struct cc2520_private *priv = spi_get_drvdata(spi);
|
||||
|
||||
if (!np) {
|
||||
struct cc2520_platform_data *spi_pdata = spi->dev.platform_data;
|
||||
if (!spi_pdata)
|
||||
return -ENOENT;
|
||||
*pdata = *spi_pdata;
|
||||
return 0;
|
||||
}
|
||||
|
||||
pdata->fifo = of_get_named_gpio(np, "fifo-gpio", 0);
|
||||
priv->fifo_pin = pdata->fifo;
|
||||
|
||||
pdata->fifop = of_get_named_gpio(np, "fifop-gpio", 0);
|
||||
|
||||
pdata->sfd = of_get_named_gpio(np, "sfd-gpio", 0);
|
||||
pdata->cca = of_get_named_gpio(np, "cca-gpio", 0);
|
||||
pdata->vreg = of_get_named_gpio(np, "vreg-gpio", 0);
|
||||
pdata->reset = of_get_named_gpio(np, "reset-gpio", 0);
|
||||
|
||||
pdata->amplified = of_property_read_bool(np, "amplified");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int cc2520_hw_init(struct cc2520_private *priv)
|
||||
{
|
||||
u8 status = 0, state = 0xff;
|
||||
int ret;
|
||||
int timeout = 100;
|
||||
struct cc2520_platform_data pdata;
|
||||
|
||||
ret = cc2520_get_platform_data(priv->spi, &pdata);
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
|
||||
ret = cc2520_read_register(priv, CC2520_FSMSTAT1, &state);
|
||||
if (ret)
|
||||
@@ -741,11 +775,47 @@ static int cc2520_hw_init(struct cc2520_private *priv)
|
||||
|
||||
dev_vdbg(&priv->spi->dev, "oscillator brought up\n");
|
||||
|
||||
/* Registers default value: section 28.1 in Datasheet */
|
||||
ret = cc2520_write_register(priv, CC2520_TXPOWER, 0xF7);
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
/* If the CC2520 is connected to a CC2591 amplifier, we must both
|
||||
* configure GPIOs on the CC2520 to correctly configure the CC2591
|
||||
* and change a couple settings of the CC2520 to work with the
|
||||
* amplifier. See section 8 page 17 of TI application note AN065.
|
||||
* http://www.ti.com/lit/an/swra229a/swra229a.pdf
|
||||
*/
|
||||
if (pdata.amplified) {
|
||||
ret = cc2520_write_register(priv, CC2520_TXPOWER, 0xF9);
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
|
||||
ret = cc2520_write_register(priv, CC2520_AGCCTRL1, 0x16);
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
|
||||
ret = cc2520_write_register(priv, CC2520_GPIOCTRL0, 0x46);
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
|
||||
ret = cc2520_write_register(priv, CC2520_GPIOCTRL5, 0x47);
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
|
||||
ret = cc2520_write_register(priv, CC2520_GPIOPOLARITY, 0x1e);
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
|
||||
ret = cc2520_write_register(priv, CC2520_TXCTRL, 0xc1);
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
} else {
|
||||
ret = cc2520_write_register(priv, CC2520_TXPOWER, 0xF7);
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
|
||||
ret = cc2520_write_register(priv, CC2520_AGCCTRL1, 0x11);
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
}
|
||||
|
||||
/* Registers default value: section 28.1 in Datasheet */
|
||||
ret = cc2520_write_register(priv, CC2520_CCACTRL0, 0x1A);
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
@@ -770,10 +840,6 @@ static int cc2520_hw_init(struct cc2520_private *priv)
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
|
||||
ret = cc2520_write_register(priv, CC2520_AGCCTRL1, 0x11);
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
|
||||
ret = cc2520_write_register(priv, CC2520_ADCTEST0, 0x10);
|
||||
if (ret)
|
||||
goto err_ret;
|
||||
@@ -808,40 +874,10 @@ err_ret:
|
||||
return ret;
|
||||
}
|
||||
|
||||
static struct cc2520_platform_data *
|
||||
cc2520_get_platform_data(struct spi_device *spi)
|
||||
{
|
||||
struct cc2520_platform_data *pdata;
|
||||
struct device_node *np = spi->dev.of_node;
|
||||
struct cc2520_private *priv = spi_get_drvdata(spi);
|
||||
|
||||
if (!np)
|
||||
return spi->dev.platform_data;
|
||||
|
||||
pdata = devm_kzalloc(&spi->dev, sizeof(*pdata), GFP_KERNEL);
|
||||
if (!pdata)
|
||||
goto done;
|
||||
|
||||
pdata->fifo = of_get_named_gpio(np, "fifo-gpio", 0);
|
||||
priv->fifo_pin = pdata->fifo;
|
||||
|
||||
pdata->fifop = of_get_named_gpio(np, "fifop-gpio", 0);
|
||||
|
||||
pdata->sfd = of_get_named_gpio(np, "sfd-gpio", 0);
|
||||
pdata->cca = of_get_named_gpio(np, "cca-gpio", 0);
|
||||
pdata->vreg = of_get_named_gpio(np, "vreg-gpio", 0);
|
||||
pdata->reset = of_get_named_gpio(np, "reset-gpio", 0);
|
||||
|
||||
spi->dev.platform_data = pdata;
|
||||
|
||||
done:
|
||||
return pdata;
|
||||
}
|
||||
|
||||
static int cc2520_probe(struct spi_device *spi)
|
||||
{
|
||||
struct cc2520_private *priv;
|
||||
struct cc2520_platform_data *pdata;
|
||||
struct cc2520_platform_data pdata;
|
||||
int ret;
|
||||
|
||||
priv = devm_kzalloc(&spi->dev, sizeof(*priv), GFP_KERNEL);
|
||||
@@ -850,8 +886,8 @@ static int cc2520_probe(struct spi_device *spi)
|
||||
|
||||
spi_set_drvdata(spi, priv);
|
||||
|
||||
pdata = cc2520_get_platform_data(spi);
|
||||
if (!pdata) {
|
||||
ret = cc2520_get_platform_data(spi, &pdata);
|
||||
if (ret < 0) {
|
||||
dev_err(&spi->dev, "no platform data\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
@@ -869,76 +905,76 @@ static int cc2520_probe(struct spi_device *spi)
|
||||
init_completion(&priv->tx_complete);
|
||||
|
||||
/* Request all the gpio's */
|
||||
if (!gpio_is_valid(pdata->fifo)) {
|
||||
if (!gpio_is_valid(pdata.fifo)) {
|
||||
dev_err(&spi->dev, "fifo gpio is not valid\n");
|
||||
ret = -EINVAL;
|
||||
goto err_hw_init;
|
||||
}
|
||||
|
||||
ret = devm_gpio_request_one(&spi->dev, pdata->fifo,
|
||||
ret = devm_gpio_request_one(&spi->dev, pdata.fifo,
|
||||
GPIOF_IN, "fifo");
|
||||
if (ret)
|
||||
goto err_hw_init;
|
||||
|
||||
if (!gpio_is_valid(pdata->cca)) {
|
||||
if (!gpio_is_valid(pdata.cca)) {
|
||||
dev_err(&spi->dev, "cca gpio is not valid\n");
|
||||
ret = -EINVAL;
|
||||
goto err_hw_init;
|
||||
}
|
||||
|
||||
ret = devm_gpio_request_one(&spi->dev, pdata->cca,
|
||||
ret = devm_gpio_request_one(&spi->dev, pdata.cca,
|
||||
GPIOF_IN, "cca");
|
||||
if (ret)
|
||||
goto err_hw_init;
|
||||
|
||||
if (!gpio_is_valid(pdata->fifop)) {
|
||||
if (!gpio_is_valid(pdata.fifop)) {
|
||||
dev_err(&spi->dev, "fifop gpio is not valid\n");
|
||||
ret = -EINVAL;
|
||||
goto err_hw_init;
|
||||
}
|
||||
|
||||
ret = devm_gpio_request_one(&spi->dev, pdata->fifop,
|
||||
ret = devm_gpio_request_one(&spi->dev, pdata.fifop,
|
||||
GPIOF_IN, "fifop");
|
||||
if (ret)
|
||||
goto err_hw_init;
|
||||
|
||||
if (!gpio_is_valid(pdata->sfd)) {
|
||||
if (!gpio_is_valid(pdata.sfd)) {
|
||||
dev_err(&spi->dev, "sfd gpio is not valid\n");
|
||||
ret = -EINVAL;
|
||||
goto err_hw_init;
|
||||
}
|
||||
|
||||
ret = devm_gpio_request_one(&spi->dev, pdata->sfd,
|
||||
ret = devm_gpio_request_one(&spi->dev, pdata.sfd,
|
||||
GPIOF_IN, "sfd");
|
||||
if (ret)
|
||||
goto err_hw_init;
|
||||
|
||||
if (!gpio_is_valid(pdata->reset)) {
|
||||
if (!gpio_is_valid(pdata.reset)) {
|
||||
dev_err(&spi->dev, "reset gpio is not valid\n");
|
||||
ret = -EINVAL;
|
||||
goto err_hw_init;
|
||||
}
|
||||
|
||||
ret = devm_gpio_request_one(&spi->dev, pdata->reset,
|
||||
ret = devm_gpio_request_one(&spi->dev, pdata.reset,
|
||||
GPIOF_OUT_INIT_LOW, "reset");
|
||||
if (ret)
|
||||
goto err_hw_init;
|
||||
|
||||
if (!gpio_is_valid(pdata->vreg)) {
|
||||
if (!gpio_is_valid(pdata.vreg)) {
|
||||
dev_err(&spi->dev, "vreg gpio is not valid\n");
|
||||
ret = -EINVAL;
|
||||
goto err_hw_init;
|
||||
}
|
||||
|
||||
ret = devm_gpio_request_one(&spi->dev, pdata->vreg,
|
||||
ret = devm_gpio_request_one(&spi->dev, pdata.vreg,
|
||||
GPIOF_OUT_INIT_LOW, "vreg");
|
||||
if (ret)
|
||||
goto err_hw_init;
|
||||
|
||||
gpio_set_value(pdata->vreg, HIGH);
|
||||
gpio_set_value(pdata.vreg, HIGH);
|
||||
usleep_range(100, 150);
|
||||
|
||||
gpio_set_value(pdata->reset, HIGH);
|
||||
gpio_set_value(pdata.reset, HIGH);
|
||||
usleep_range(200, 250);
|
||||
|
||||
ret = cc2520_hw_init(priv);
|
||||
@@ -947,7 +983,7 @@ static int cc2520_probe(struct spi_device *spi)
|
||||
|
||||
/* Set up fifop interrupt */
|
||||
ret = devm_request_irq(&spi->dev,
|
||||
gpio_to_irq(pdata->fifop),
|
||||
gpio_to_irq(pdata.fifop),
|
||||
cc2520_fifop_isr,
|
||||
IRQF_TRIGGER_RISING,
|
||||
dev_name(&spi->dev),
|
||||
@@ -959,7 +995,7 @@ static int cc2520_probe(struct spi_device *spi)
|
||||
|
||||
/* Set up sfd interrupt */
|
||||
ret = devm_request_irq(&spi->dev,
|
||||
gpio_to_irq(pdata->sfd),
|
||||
gpio_to_irq(pdata.sfd),
|
||||
cc2520_sfd_isr,
|
||||
IRQF_TRIGGER_FALLING,
|
||||
dev_name(&spi->dev),
|
||||
|
Reference in New Issue
Block a user