Пример #1
0
static int __init hp_wmi_rfkill_setup(struct platform_device *device)
{
	int err, wireless;

	wireless = hp_wmi_read_int(HPWMI_WIRELESS_QUERY);
	if (wireless < 0)
		return wireless;

	err = hp_wmi_perform_query(HPWMI_WIRELESS_QUERY, HPWMI_WRITE, &wireless,
				   sizeof(wireless), 0);
	if (err)
		return err;

	if (wireless & 0x1) {
		wifi_rfkill = rfkill_alloc("hp-wifi", &device->dev,
					   RFKILL_TYPE_WLAN,
					   &hp_wmi_rfkill_ops,
					   (void *) HPWMI_WIFI);
		if (!wifi_rfkill)
			return -ENOMEM;
		rfkill_init_sw_state(wifi_rfkill,
				     hp_wmi_get_sw_state(HPWMI_WIFI));
		rfkill_set_hw_state(wifi_rfkill,
				    hp_wmi_get_hw_state(HPWMI_WIFI));
		err = rfkill_register(wifi_rfkill);
		if (err)
			goto register_wifi_error;
	}

	if (wireless & 0x2) {
		bluetooth_rfkill = rfkill_alloc("hp-bluetooth", &device->dev,
						RFKILL_TYPE_BLUETOOTH,
						&hp_wmi_rfkill_ops,
						(void *) HPWMI_BLUETOOTH);
		if (!bluetooth_rfkill) {
			err = -ENOMEM;
			goto register_bluetooth_error;
		}
		rfkill_init_sw_state(bluetooth_rfkill,
				     hp_wmi_get_sw_state(HPWMI_BLUETOOTH));
		rfkill_set_hw_state(bluetooth_rfkill,
				    hp_wmi_get_hw_state(HPWMI_BLUETOOTH));
		err = rfkill_register(bluetooth_rfkill);
		if (err)
			goto register_bluetooth_error;
	}

	if (wireless & 0x4) {
		wwan_rfkill = rfkill_alloc("hp-wwan", &device->dev,
					   RFKILL_TYPE_WWAN,
					   &hp_wmi_rfkill_ops,
					   (void *) HPWMI_WWAN);
		if (!wwan_rfkill) {
			err = -ENOMEM;
			goto register_wwan_error;
		}
		rfkill_init_sw_state(wwan_rfkill,
				     hp_wmi_get_sw_state(HPWMI_WWAN));
		rfkill_set_hw_state(wwan_rfkill,
				    hp_wmi_get_hw_state(HPWMI_WWAN));
		err = rfkill_register(wwan_rfkill);
		if (err)
			goto register_wwan_error;
	}

	return 0;

register_wwan_error:
	rfkill_destroy(wwan_rfkill);
	wwan_rfkill = NULL;
	if (bluetooth_rfkill)
		rfkill_unregister(bluetooth_rfkill);
register_bluetooth_error:
	rfkill_destroy(bluetooth_rfkill);
	bluetooth_rfkill = NULL;
	if (wifi_rfkill)
		rfkill_unregister(wifi_rfkill);
register_wifi_error:
	rfkill_destroy(wifi_rfkill);
	wifi_rfkill = NULL;
	return err;
}
static int __devinit toshiba_acpi_add(struct acpi_device *acpi_dev)
{
	struct toshiba_acpi_dev *dev;
	const char *hci_method;
	u32 dummy;
	bool bt_present;
	int ret = 0;
	struct backlight_properties props;

	if (toshiba_acpi)
		return -EBUSY;

	pr_info("Toshiba Laptop ACPI Extras version %s\n",
	       TOSHIBA_ACPI_VERSION);

	hci_method = find_hci_method(acpi_dev->handle);
	if (!hci_method) {
		pr_err("HCI interface not found\n");
		return -ENODEV;
	}

	dev = kzalloc(sizeof(*dev), GFP_KERNEL);
	if (!dev)
		return -ENOMEM;
	dev->acpi_dev = acpi_dev;
	dev->method_hci = hci_method;
	acpi_dev->driver_data = dev;

	if (toshiba_acpi_setup_keyboard(dev))
		pr_info("Unable to activate hotkeys\n");

	mutex_init(&dev->mutex);

	props.type = BACKLIGHT_PLATFORM;
	props.max_brightness = HCI_LCD_BRIGHTNESS_LEVELS - 1;
	dev->backlight_dev = backlight_device_register("toshiba",
						       &acpi_dev->dev,
						       dev,
						       &toshiba_backlight_data,
						       &props);
	if (IS_ERR(dev->backlight_dev)) {
		ret = PTR_ERR(dev->backlight_dev);

		pr_err("Could not register toshiba backlight device\n");
		dev->backlight_dev = NULL;
		goto error;
	}
	dev->backlight_dev->props.brightness = get_lcd(dev->backlight_dev);

	/*                                      */
	if (hci_get_bt_present(dev, &bt_present) == HCI_SUCCESS && bt_present) {
		dev->bt_rfk = rfkill_alloc("Toshiba Bluetooth",
					   &acpi_dev->dev,
					   RFKILL_TYPE_BLUETOOTH,
					   &toshiba_rfk_ops,
					   dev);
		if (!dev->bt_rfk) {
			pr_err("unable to allocate rfkill device\n");
			ret = -ENOMEM;
			goto error;
		}

		ret = rfkill_register(dev->bt_rfk);
		if (ret) {
			pr_err("unable to register rfkill device\n");
			rfkill_destroy(dev->bt_rfk);
			goto error;
		}
	}

	if (toshiba_illumination_available(dev)) {
		dev->led_dev.name = "toshiba::illumination";
		dev->led_dev.max_brightness = 1;
		dev->led_dev.brightness_set = toshiba_illumination_set;
		dev->led_dev.brightness_get = toshiba_illumination_get;
		if (!led_classdev_register(&acpi_dev->dev, &dev->led_dev))
			dev->illumination_supported = 1;
	}

	/*                                                                 */

	ret = get_video_status(dev, &dummy);
	dev->video_supported = !ret;

	ret = get_fan_status(dev, &dummy);
	dev->fan_supported = !ret;

	create_toshiba_proc_entries(dev);

	toshiba_acpi = dev;

	return 0;

error:
	toshiba_acpi_remove(acpi_dev, 0);
	return ret;
}
Пример #3
0
static int spica_bt_probe(struct platform_device *pdev)
{
	struct spica_bt_pdata *pdata = pdev->dev.platform_data;
	struct spica_bt *bt;
	int ret = 0;

	if (!pdata) {
		dev_err(&pdev->dev, "no platform data specified\n");
		return -EINVAL;
	}

	if (!gpio_is_valid(pdata->gpio_host_wake)) {
		dev_err(&pdev->dev, "invalid BT host wake GPIO\n");
		return -EINVAL;
	}

	bt = kzalloc(sizeof(struct spica_bt), GFP_KERNEL);
	if (!bt) {
		dev_err(&pdev->dev, "failed to allocate driver data\n");
		return -ENOMEM;
	}

	bt->pdata = pdata;
	bt->dev = &pdev->dev;
	wake_lock_init(&bt->wake_lock, WAKE_LOCK_SUSPEND, "bt_host_wake");

	WARN_ON(gpio_request(pdata->gpio_host_wake, "BT host wake") < 0);

	ret = gpio_to_irq(pdata->gpio_host_wake);
	if (ret < 0) {
		dev_err(&pdev->dev, "failed to get host wake IRQ number\n");
		goto err_gpio_irq;
	}
	bt->irq = ret;
	bt->blocked = true;

	ret = request_irq(bt->irq, spica_bt_host_wake_irq,
				IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING,
				"BT host wake", bt);
	if (ret < 0) {
		dev_err(&pdev->dev, "failed to request bt host wake IRQ\n");
		goto err_irq;
	}

	disable_irq(bt->irq);

	bt->rfk = rfkill_alloc("bcm4329", &pdev->dev,
			RFKILL_TYPE_BLUETOOTH, &spica_bt_ops, bt);
	if (IS_ERR(bt->rfk)) {
		dev_err(&pdev->dev, "rfkill_alloc failed\n");
		ret = PTR_ERR(bt->rfk);
		goto err_alloc;
	}

	rfkill_init_sw_state(bt->rfk, true);

	ret = rfkill_register(bt->rfk);
	if (ret) {
		dev_err(&pdev->dev, "rfkill_register failed (%d)\n", ret);
		goto err_register;
	}

	return 0;

err_register:
	rfkill_destroy(bt->rfk);
err_alloc:
	free_irq(bt->irq, bt);
err_irq:
	gpio_free(pdata->gpio_host_wake);
err_gpio_irq:
	kfree(bt);
	return ret;
}
Пример #4
0
/* ----- Initialization/removal -------------------------------------------- */
static int __init gtablet_wlan_probe(struct platform_device *pdev)
{
	/* default-on for now */
	const int default_state = 1;
	
	struct rfkill *rfkill;
	struct regulator *regulator[2];
	struct gtablet_pm_wlan_data *wlan_data;
	int ret;

	wlan_data = kzalloc(sizeof(*wlan_data), GFP_KERNEL);
	if (!wlan_data) {
		dev_err(&pdev->dev, "no memory for context\n");
		return -ENOMEM;
	}
	dev_set_drvdata(&pdev->dev, wlan_data);

	regulator[0] = regulator_get(&pdev->dev, "vddio_wlan");
	if (IS_ERR(regulator[0])) {
		dev_err(&pdev->dev, "unable to get regulator 0\n");
		kfree(wlan_data);
		dev_set_drvdata(&pdev->dev, NULL);
		return -ENODEV;
	}

	wlan_data->regulator[0] = regulator[0];

	regulator[1] = regulator_get(&pdev->dev, "vcore_wifi");
	if (IS_ERR(regulator[1])) {
		dev_err(&pdev->dev, "unable to get regulator 1\n");
		regulator_put(regulator[0]);
		kfree(wlan_data);
		dev_set_drvdata(&pdev->dev, NULL);
		return -ENODEV;
	}
	wlan_data->regulator[1] = regulator[1];
	
	wlan_data->wifi_32k_clk = clk_get_sys(NULL, "blink");
	if (IS_ERR(wlan_data->wifi_32k_clk)) {
                pr_err("%s: unable to get blink clock\n", __func__);
                return PTR_ERR(wlan_data->wifi_32k_clk);
        }

	/* Init io pins */
	gpio_request(GTABLET_WLAN_POWER, "wlan_power");
	gpio_direction_output(GTABLET_WLAN_POWER, 0);

	gpio_request(GTABLET_WLAN_POWER, "wlan_reset");
	gpio_direction_output(GTABLET_WLAN_POWER, 0);
	
	rfkill = rfkill_alloc("bcm4329", &pdev->dev, RFKILL_TYPE_WLAN,
							&gtablet_wlan_rfkill_ops, &pdev->dev);


	if (!rfkill) {
		dev_err(&pdev->dev, "Failed to allocate rfkill\n");
		regulator_put(regulator[1]);
		regulator_put(regulator[0]);
		kfree(wlan_data);
		dev_set_drvdata(&pdev->dev, NULL);
		return -ENOMEM;
	}
	wlan_data->rfkill = rfkill;
	
	rfkill_init_sw_state(rfkill, default_state);

	ret = rfkill_register(rfkill);
	if (ret) {
		dev_err(&pdev->dev, "Failed to register rfkill\n");
		regulator_put(regulator[1]);
		regulator_put(regulator[0]);
		rfkill_destroy(rfkill);
		kfree(wlan_data);
		dev_set_drvdata(&pdev->dev, NULL);
		return ret;
	}

	dev_info(&pdev->dev, "WLAN RFKill driver loaded\n");
	
	return sysfs_create_group(&pdev->dev.kobj, &gtablet_wlan_attr_group);
}
static int __init herring_rfkill_probe(struct platform_device *pdev)
{
	int irq;
	int ret;
    
	/* Initialize wake locks */
	wake_lock_init(&rfkill_wake_lock, WAKE_LOCK_SUSPEND, "bt_host_wake");
    
	ret = gpio_request(GPIO_WLAN_BT_EN, "GPB");
	if (ret < 0) {
		pr_err("[BT] Failed to request GPIO_WLAN_BT_EN!\n");
		goto err_req_gpio_wlan_bt_en;
	}
    
	ret = gpio_request(GPIO_BT_nRST, "GPB");
	if (ret < 0) {
		pr_err("[BT] Failed to request GPIO_BT_nRST!\n");
		goto err_req_gpio_bt_nrst;
	}
    
	/* BT Host Wake IRQ */
	irq = IRQ_BT_HOST_WAKE;
    
	ret = request_irq(irq, bt_host_wake_irq_handler,
                      IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING,
                      "bt_host_wake_irq_handler", NULL);
    
	if (ret < 0) {
		pr_err("[BT] Request_irq failed\n");
		goto err_req_irq;
	}
    
	disable_irq(irq);
    
	bt_rfk = rfkill_alloc(bt_name, &pdev->dev, RFKILL_TYPE_BLUETOOTH,
                          &bt_rfkill_ops, NULL);
    
	if (!bt_rfk) {
		pr_err("[BT] bt_rfk : rfkill_alloc is failed\n");
		ret = -ENOMEM;
		goto err_alloc;
	}
    
	rfkill_init_sw_state(bt_rfk, 0);
    
	pr_debug("[BT] rfkill_register(bt_rfk)\n");
    
	ret = rfkill_register(bt_rfk);
	if (ret) {
		pr_debug("********ERROR IN REGISTERING THE RFKILL********\n");
		goto err_register;
	}
    
	rfkill_set_sw_state(bt_rfk, 1);
	bluetooth_set_power(NULL, RFKILL_USER_STATE_SOFT_BLOCKED);
    
	return ret;
    
err_register:
	rfkill_destroy(bt_rfk);
    
err_alloc:
	free_irq(irq, NULL);
    
err_req_irq:
	gpio_free(GPIO_BT_nRST);
    
err_req_gpio_bt_nrst:
	gpio_free(GPIO_WLAN_BT_EN);
    
err_req_gpio_wlan_bt_en:
	return ret;
}
Пример #6
0
static int  bt_ctr_probe(struct platform_device *pdev)
{
	int irq;
	int ret;

	struct bt_gpio_info *bt_info;
	
	/* Initialize wake locks */
	wake_lock_init(&rfkill_wake_lock, WAKE_LOCK_SUSPEND, "bt_host_wake");

	/* request gpio */
	ret = gpio_request(BT_POWER, "GPB");
	if (ret < 0) {
		pr_err("[BT] Failed to request BT_POWER!\n");
		goto err_req_bt_power;
	}

	ret = gpio_request(BT_RESET, "GPB");
	if (ret < 0) {
		pr_err("[BT] Failed to request BT_RESET!\n");
		goto err_req_bt_reset;
	}

	/* BT Host Wake IRQ */
	irq = gpio_to_irq(BT_HOST_WAKE);
	
	ret = request_irq(irq, bt_host_wake_irq_handler,
			IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING,
			"bt_host_wake_irq_handler", NULL);

	if (ret < 0) {
		pr_err("[BT] Request_irq failed\n");
		goto err_req_irq;
	}

	disable_irq(irq);

	/* init rfkill */
	bt_rfk = rfkill_alloc(bt_name, &pdev->dev, RFKILL_TYPE_BLUETOOTH,
			&bt_rfkill_ops, NULL);

	if (!bt_rfk) {
		pr_err("[BT] bt_rfk : rfkill_alloc is failed\n");
		ret = -ENOMEM;
		goto err_alloc;
	}

	rfkill_init_sw_state(bt_rfk, 0);	

	ret = rfkill_register(bt_rfk);
	if (ret) {
		pr_debug("********ERROR IN REGISTERING THE RFKILL********\n");
		goto err_register;
	}

	rfkill_set_sw_state(bt_rfk, 1);
	
	/* init low power state*/
	ret = bt_lpm_init();
	if (ret < 0) {
		pr_debug("[BT]  set low power failed\n");
		goto err_register;
	}

	/* create sysfs attributes */
	bt_info = kzalloc(sizeof(struct bt_gpio_info), GFP_KERNEL);
	if(!bt_info) {
		pr_debug("[BT]  sysfs_create_group failed\n");
		goto err_register;
	}

	bt_info->bt_test_mode =0;     //bt   in normal mode
	bt_info->bt_enable = 0;
	bt_info->bt_wake = 0;
	mutex_init(&bt_info->bt_lock);	
	
	bt_info->dev = &pdev->dev;
	platform_set_drvdata(pdev, bt_info);

	ret = sysfs_create_group(&pdev->dev.kobj, &bcm_attribute_group);
	if (ret < 0) {
		pr_debug("[BT]  sysfs_create_group failed\n");
		goto err_register;
	}

	device_init_wakeup(&pdev->dev, 1);

	/* set init power state*/
	bt_set_power(NULL, RFKILL_USER_STATE_SOFT_BLOCKED);

	return ret;

 err_register:
	rfkill_destroy(bt_rfk);

 err_alloc:
	free_irq(irq, NULL);

 err_req_irq:
	gpio_free(BT_RESET);

 err_req_bt_reset:
	gpio_free(BT_POWER);

 err_req_bt_power:
	return ret;
}
static int bcm4354_bluetooth_probe(struct platform_device *pdev)
{
    int rc = 0;

#ifdef BT_UART_CFG
    int pin = 0;
#endif
    rc = gpio_request(GPIO_BT_EN, "bt_en");
    if (rc)
    {
        pr_err("[BT] %s: gpio_request for GPIO_BT_EN is failed", __func__);
        gpio_free(GPIO_BT_EN);
    }

#ifdef BT_EN_GENERAL_GPIO
    gpio_tlmm_config(GPIO_CFG(GPIO_BT_EN, 0, GPIO_CFG_OUTPUT,
        GPIO_CFG_PULL_DOWN, GPIO_CFG_8MA), GPIO_CFG_ENABLE);
    gpio_set_value(GPIO_BT_EN, 0);
#endif

    /* temporailiy set HOST_WAKE OUT direction until FPGA work finishs */
    /* if setting HOST_WAKE to NO PULL, BT would not be turned on. */
    /* By guideline of BRCM, it is needed to determine pull status */
#ifndef BT_LPM_ENABLE
    gpio_tlmm_config(GPIO_CFG(get_gpio_hwrev(gpio_bt_host_wake), 0, GPIO_CFG_OUTPUT,
        GPIO_CFG_PULL_UP, GPIO_CFG_8MA), GPIO_CFG_ENABLE);
    gpio_set_value(get_gpio_hwrev(gpio_bt_host_wake), 1);
#endif

#ifdef BT_UART_CFG
    for (pin = 0; pin < ARRAY_SIZE(bt_uart_off_table); pin++) {
        rc = gpio_tlmm_config(bt_uart_off_table[pin], GPIO_CFG_ENABLE);
        if (rc < 0)
            pr_err("%s: gpio_tlmm_config(%#x)=%d\n",
                __func__, bt_uart_off_table[pin], rc);
    }
#endif

    bt_rfkill = rfkill_alloc("bcm4354 Bluetooth", &pdev->dev,
                RFKILL_TYPE_BLUETOOTH, &bcm4354_bt_rfkill_ops,
                NULL);

    if (unlikely(!bt_rfkill)) {
        pr_err("[BT] bt_rfkill alloc failed.\n");
        return -ENOMEM;
    }


    rfkill_init_sw_state(bt_rfkill, 0);

    rc = rfkill_register(bt_rfkill);

    if (unlikely(rc)) {
        pr_err("[BT] bt_rfkill register failed.\n");
        rfkill_destroy(bt_rfkill);
        gpio_free(get_gpio_hwrev(BT_WAKE));
        return rc;
    }


    rfkill_set_sw_state(bt_rfkill, true);

    return rc;
}
static int bcm43xx_bluetooth_probe(struct platform_device *pdev)
{
	bool default_state = true;	/* off */
	int ret = 0;

	int_handler_enabled = false;

#ifdef CONFIG_ACPI
	if (ACPI_HANDLE(&pdev->dev)) {
		/*
		 * acpi specific probe
		 */
		pr_debug("%s for ACPI device %s\n", __func__,
							dev_name(&pdev->dev));
		if (bcm_bt_lpm_acpi_probe(pdev) < 0)
			ret = -EINVAL;
	} else
		ret = -ENODEV;
#else
	ret = bcm43xx_bluetooth_pdata_probe(pdev);
#endif

	if (ret < 0) {
		pr_err("%s: Cannot register platform data\n", __func__);
		goto err_data_probe;
	}

	ret = gpio_request(bt_lpm.gpio_enable_bt, pdev->name);
	if (ret < 0) {
		pr_err("%s: Unable to request gpio %d\n", __func__,
							bt_lpm.gpio_enable_bt);
		goto err_gpio_enable_req;
	}

	ret = gpio_direction_output(bt_lpm.gpio_enable_bt, 0);
	if (ret < 0) {
		pr_err("%s: Unable to set int direction for gpio %d\n",
					__func__, bt_lpm.gpio_enable_bt);
		goto err_gpio_enable_dir;
	}

#ifdef LPM_ON
	ret = gpio_request(bt_lpm.gpio_host_wake, pdev->name);
	if (ret < 0) {
		pr_err("%s: Unable to request gpio %d\n",
					__func__, bt_lpm.gpio_host_wake);
		goto err_gpio_host_wake_req;
	}

	ret = gpio_direction_input(bt_lpm.gpio_host_wake);
	if (ret < 0) {
		pr_err("%s: Unable to set direction for gpio %d\n", __func__,
							bt_lpm.gpio_host_wake);
		goto err_gpio_host_wake_dir;
	}

	ret = gpio_request(bt_lpm.gpio_wake, pdev->name);
	if (ret < 0) {
		pr_err("%s: Unable to request gpio %d\n", __func__,
							bt_lpm.gpio_wake);
		goto err_gpio_wake_req;
	}

	ret =  gpio_direction_output(bt_lpm.gpio_wake, 0);
	if (ret < 0) {
		pr_err("%s: Unable to set direction for gpio %d\n", __func__,
							bt_lpm.gpio_wake);
		goto err_gpio_wake_dir;
	}

	pr_debug("%s: gpio_enable=%d, gpio_wake=%d, gpio_host_wake=%d\n",
							__func__,
							bt_lpm.gpio_enable_bt,
							bt_lpm.gpio_wake,
							bt_lpm.gpio_host_wake);
#endif

	bt_rfkill = rfkill_alloc("bcm43xx Bluetooth", &pdev->dev,
				RFKILL_TYPE_BLUETOOTH, &bcm43xx_bt_rfkill_ops,
				NULL);
	if (unlikely(!bt_rfkill)) {
		ret = -ENOMEM;
		goto err_rfkill_alloc;
	}

	bcm43xx_bt_rfkill_set_power(NULL, default_state);
	rfkill_init_sw_state(bt_rfkill, default_state);

	ret = rfkill_register(bt_rfkill);
	if (unlikely(ret))
		goto err_rfkill_register;

#ifdef LPM_ON
	ret = bcm_bt_lpm_init(pdev);
	if (ret)
		goto err_lpm_init;
#endif

	return ret;

err_lpm_init:
	rfkill_unregister(bt_rfkill);
err_rfkill_register:
	rfkill_destroy(bt_rfkill);
err_rfkill_alloc:
#ifdef LPM_ON
err_gpio_wake_dir:
	gpio_free(bt_lpm.gpio_wake);
err_gpio_wake_req:
err_gpio_host_wake_dir:
	gpio_free(bt_lpm.gpio_host_wake);
err_gpio_host_wake_req:
#endif
err_gpio_enable_dir:
	gpio_free(bt_lpm.gpio_enable_bt);
err_gpio_enable_req:
err_data_probe:
	return ret;
}
Пример #9
0
static int rfkill_rk_probe(struct platform_device *pdev)
{
	struct rfkill_rk_data *rfkill;
	struct rfkill_rk_platform_data *pdata = pdev->dev.platform_data;
	int ret = 0;
    struct proc_dir_entry *ent;

    DBG("Enter %s\n", __func__);

	if (!pdata) {
		LOG("%s: No platform data specified\n", __func__);
		return -EINVAL;
	}

    pdata->name = (char*)bt_name;

	rfkill = kzalloc(sizeof(*rfkill), GFP_KERNEL);
	if (!rfkill)
		return -ENOMEM;

	rfkill->pdata = pdata;
    g_rfkill = rfkill;

    bluetooth_dir = proc_mkdir("bluetooth", NULL);
    if (bluetooth_dir == NULL) {
        LOG("Unable to create /proc/bluetooth directory");
        return -ENOMEM;
    }

    sleep_dir = proc_mkdir("sleep", bluetooth_dir);
    if (sleep_dir == NULL) {
        LOG("Unable to create /proc/%s directory", PROC_DIR);
        return -ENOMEM;
    }

	/* read/write proc entries */
    ent = create_proc_entry("lpm", 0, sleep_dir);
    if (ent == NULL) {
        LOG("Unable to create /proc/%s/lpm entry", PROC_DIR);
        ret = -ENOMEM;
        goto fail_alloc;
    }
    ent->read_proc = bluesleep_read_proc_lpm;
    ent->write_proc = bluesleep_write_proc_lpm;

    /* read/write proc entries */
    ent = create_proc_entry("btwrite", 0, sleep_dir);
    if (ent == NULL) {
        LOG("Unable to create /proc/%s/btwrite entry", PROC_DIR);
        ret = -ENOMEM;
        goto fail_alloc;
    }
    ent->read_proc = bluesleep_read_proc_btwrite;
    ent->write_proc = bluesleep_write_proc_btwrite;

    // 申请GPIO以及IRQ
    DBG("init gpio\n");
    // 对于RK29 BCM4329,它的poweron io与wifi共用,在boad文件中已经request
    // 此处不用去申请
#if !WIFI_BT_POWER_TOGGLE
    ret = rfkill_rk_setup_gpio(&pdata->poweron_gpio, IOMUX_FGPIO, pdata->name, "poweron");
    if (ret) goto fail_alloc;
#endif

    ret = rfkill_rk_setup_gpio(&pdata->reset_gpio, IOMUX_FGPIO, pdata->name, "reset");
    if (ret) goto fail_poweron;

    ret = rfkill_rk_setup_gpio(&pdata->wake_gpio, IOMUX_FGPIO, pdata->name, "wake");
    if (ret) goto fail_reset;

    ret = rfkill_rk_setup_wake_irq(rfkill);
    if (ret) goto fail_wake;

    ret = rfkill_rk_setup_gpio(&pdata->rts_gpio, IOMUX_FMUX, rfkill->pdata->name, "rts"); 
    if (ret) goto fail_wake_host_irq;

    // 创建并注册RFKILL设备
    DBG("setup rfkill\n");
	rfkill->rfkill_dev = rfkill_alloc(pdata->name, &pdev->dev, pdata->type,
				&rfkill_rk_ops, rfkill);
	if (!rfkill->rfkill_dev)
		goto fail_rts;

    // cmy: 设置rfkill初始状态为blocked,在注册时不会调用 set_blocked函数
    rfkill_set_states(rfkill->rfkill_dev, BT_BLOCKED, false);
	ret = rfkill_register(rfkill->rfkill_dev);
	if (ret < 0)
		goto fail_rfkill;

    wake_lock_init(&(rfkill->bt_irq_wl), WAKE_LOCK_SUSPEND, "rfkill_rk_irq_wl");
    INIT_DELAYED_WORK(&rfkill->bt_sleep_delay_work, rfkill_rk_delay_sleep_bt);

    // cmy: 设置蓝牙电源的状态为 blocked
    rfkill_rk_set_power(rfkill, BT_BLOCKED);

	platform_set_drvdata(pdev, rfkill);

    LOG("%s device registered.\n", pdata->name);

	return 0;

fail_rfkill:
	rfkill_destroy(rfkill->rfkill_dev);
fail_rts:
    if (gpio_is_valid(pdata->rts_gpio.io))
        gpio_free(pdata->rts_gpio.io);
fail_wake_host_irq:
    if (gpio_is_valid(pdata->wake_host_irq.gpio.io)){
        free_irq(pdata->wake_host_irq.irq, rfkill);
        gpio_free(pdata->wake_host_irq.gpio.io);
    }
fail_wake:
    if (gpio_is_valid(pdata->wake_gpio.io))
        gpio_free(pdata->wake_gpio.io);
fail_reset:
	if (gpio_is_valid(pdata->reset_gpio.io))
		gpio_free(pdata->reset_gpio.io);
fail_poweron:
#if !WIFI_BT_POWER_TOGGLE
    if (gpio_is_valid(pdata->poweron_gpio.io))
        gpio_free(pdata->poweron_gpio.io);
#endif
fail_alloc:
	kfree(rfkill);
    g_rfkill = NULL;

	remove_proc_entry("btwrite", sleep_dir);
	remove_proc_entry("lpm", sleep_dir);

	return ret;
}
static int bcm43455_bluetooth_probe(struct platform_device *pdev)
{
	int rc = 0;
#ifdef BT_LPM_ENABLE
	int ret;
#endif
	pr_err("[BT] bcm43455_bluetooth_probe.\n");

	bt_gpio.bt_en = of_get_gpio(pdev->dev.of_node, 0);

	if (!gpio_is_valid(bt_gpio.bt_en)) {
		pr_err("[BT] bt_gpio.bt_en get gpio failed.\n");
		return -EINVAL;
	}

	rc = gpio_request(bt_gpio.bt_en, "bten_gpio");

	if (unlikely(rc)) {
		pr_err("[BT] bt_gpio.bt_en request failed.\n");
		return rc;
	}

	bt_gpio.bt_wake =of_get_gpio(pdev->dev.of_node, 1);

	if (!gpio_is_valid(bt_gpio.bt_wake)) {
		pr_err("[BT] bt_gpio.bt_wake get gpio failed.\n");
		return -EINVAL;
	}

	rc = gpio_request(bt_gpio.bt_wake, "btwake_gpio");

	if (unlikely(rc)) {
		pr_err("[BT] bt_gpio.bt_wake request failed.\n");
		gpio_free(bt_gpio.bt_en);
		return rc;
	}

	bt_gpio.bt_hostwake =of_get_gpio(pdev->dev.of_node, 2);

	if (!gpio_is_valid(bt_gpio.bt_hostwake)) {
		pr_err("[BT] bt_gpio.bt_hostwake get gpio failed.\n");
		return -EINVAL;
	}

	rc = gpio_request(bt_gpio.bt_hostwake,"bthostwake_gpio");

	if (unlikely(rc)) {
		pr_err("[BT] bt_gpio.bt_hostwake request failed.\n");
		gpio_free(bt_gpio.bt_wake);
		gpio_free(bt_gpio.bt_en);
		return rc;
	}

	gpio_direction_input(bt_gpio.bt_hostwake);
	gpio_direction_output(bt_gpio.bt_wake, 0);
	gpio_direction_output(bt_gpio.bt_en, 0);

	bt_rfkill = rfkill_alloc("bcm43455 Bluetooth", &pdev->dev,
				RFKILL_TYPE_BLUETOOTH, &bcm43455_bt_rfkill_ops,
				NULL);

	if (unlikely(!bt_rfkill)) {
		pr_err("[BT] bt_rfkill alloc failed.\n");
		gpio_free(bt_gpio.bt_hostwake);
		gpio_free(bt_gpio.bt_wake);
		gpio_free(bt_gpio.bt_en);
		return -ENOMEM;
	}

	rfkill_init_sw_state(bt_rfkill, 0);

	rc = rfkill_register(bt_rfkill);

	if (unlikely(rc)) {
		pr_err("[BT] bt_rfkill register failed.\n");
		rfkill_destroy(bt_rfkill);
		gpio_free(bt_gpio.bt_hostwake);
		gpio_free(bt_gpio.bt_wake);
		gpio_free(bt_gpio.bt_en);
		return -1;
	}

	rfkill_set_sw_state(bt_rfkill, true);

#ifdef BT_LPM_ENABLE
	ret = bcm_bt_lpm_init(pdev);
	if (ret) {
		rfkill_unregister(bt_rfkill);
		rfkill_destroy(bt_rfkill);

		gpio_free(bt_gpio.bt_hostwake);
		gpio_free(bt_gpio.bt_wake);
		gpio_free(bt_gpio.bt_en);
	}
#endif
	pr_info("[BT] bcm43455_bluetooth_probe End \n");
	return rc;
}
Пример #11
0
static int __init aries_rfkill_probe(struct platform_device *pdev)
{
	int irq;
	int ret;
        unsigned int GPIO_BTnRST; //To distinguish HW Revision

	/* Initialize wake locks */
	wake_lock_init(&rfkill_wake_lock, WAKE_LOCK_SUSPEND, "bt_host_wake");

        if (HWREV == 0) {
            GPIO_BTnRST = GPIO_BT_nRST_REV00;
        }
        else {
            GPIO_BTnRST = GPIO_BT_nRST;
        }

	ret = gpio_request(GPIO_WLAN_BT_EN, "GPB");
	if (ret < 0) {
		pr_err("[BT] Failed to request GPIO_WLAN_BT_EN!\n");
		goto err_req_gpio_wlan_bt_en;
	}

	ret = gpio_request(GPIO_BTnRST, "GPB");
	if (ret < 0) {
		pr_err("[BT] Failed to request GPIO_BT_nRST!\n");
		goto err_req_gpio_bt_nrst;
	}

	/* BT Host Wake IRQ */
	irq = IRQ_BT_HOST_WAKE;

	ret = request_irq(irq, bt_host_wake_irq_handler,
			IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING,
			"bt_host_wake_irq_handler", NULL);

	if (ret < 0) {
		pr_err("[BT] Request_irq failed\n");
		goto err_req_irq;
	}

	disable_irq(irq);

	bt_rfk = rfkill_alloc(bt_name, &pdev->dev, RFKILL_TYPE_BLUETOOTH,
			&bt_rfkill_ops, NULL);

	if (!bt_rfk) {
		pr_err("[BT] bt_rfk : rfkill_alloc is failed\n");
		ret = -ENOMEM;
		goto err_alloc;
	}

	rfkill_init_sw_state(bt_rfk, 0);

	pr_debug("[BT] rfkill_register(bt_rfk)\n");

	ret = rfkill_register(bt_rfk);
	if (ret) {
		pr_err("********ERROR IN REGISTERING THE bt_rfk********\n");
		goto err_register;
	}

	rfkill_set_sw_state(bt_rfk, 1);
	bluetooth_set_power(NULL, RFKILL_USER_STATE_SOFT_BLOCKED);

#ifdef BT_SLEEP_ENABLE
	wake_lock_init(&bt_wake_lock, WAKE_LOCK_SUSPEND, "bt_wake");

	ret = gpio_request(GPIO_BT_WAKE, "gpio_bt_wake");
	if (ret < 0) {
		pr_err("[BT] Failed to request GPIO_BT_WAKE\n");
		goto err_req_gpio_bt_wake;
	}

	gpio_direction_output(GPIO_BT_WAKE, GPIO_LEVEL_LOW);

	bt_sleep_rfk = rfkill_alloc(bt_name, &pdev->dev, RFKILL_TYPE_BLUETOOTH,
			&btsleep_rfkill_ops, NULL);

	if (!bt_sleep_rfk) {
		pr_err("[BT] bt_sleep_rfk : rfkill_alloc is failed\n");
		ret = -ENOMEM;
		goto err_sleep_alloc;
	}

	rfkill_set_sw_state(bt_sleep_rfk, 1);

	pr_debug("[BT] rfkill_register(bt_sleep_rfk)\n");

	ret = rfkill_register(bt_sleep_rfk);
	if (ret) {
		pr_err("********ERROR IN REGISTERING THE bt_sleep_rfk********\n");
		goto err_sleep_register;
	}
#endif

#ifdef USE_LOCK_DVFS
	bt_lock_dvfs_rfk = rfkill_alloc(bt_name, &pdev->dev, RFKILL_TYPE_BLUETOOTH,
			&bt_lock_dvfs_rfkill_ops, NULL);

	if (!bt_lock_dvfs_rfk) {
		pr_err("[BT] bt_lock_dvfs_rfk : rfkill_alloc is failed\n");
		ret = -ENOMEM;
		goto err_dvfs_lock_alloc;
	}

	pr_debug("[BT] rfkill_register(bt_lock_dvfs_rfk)\n");

	ret = rfkill_register(bt_lock_dvfs_rfk);
	if (ret) {
		pr_err("********ERROR IN REGISTERING THE bt_lock_dvfs_rfk********\n");
		goto err_lock_dvfs_register;
	}

	bt_lock_dvfs_l2_rfk = rfkill_alloc(bt_name, &pdev->dev, RFKILL_TYPE_BLUETOOTH,
			&bt_lock_dvfs_l2_rfkill_ops, NULL);

	if (!bt_lock_dvfs_l2_rfk) {
		pr_err("[BT] bt_lock_dvfs_l2_rfk : rfkill_alloc is failed\n");
		ret = -ENOMEM;
		goto err_dvfs_l2_lock_alloc;
	}

	pr_debug("[BT] rfkill_register(bt_lock_dvfs_l2_rfk)\n");

	ret = rfkill_register(bt_lock_dvfs_l2_rfk);
	if (ret) {
		pr_err("********ERROR IN REGISTERING THE bt_lock_dvfs_l2_rfk********\n");
		goto err_lock_dvfs_l2_register;
	}	
#endif
	return ret;

#ifdef USE_LOCK_DVFS
err_lock_dvfs_l2_register:
	rfkill_destroy(bt_lock_dvfs_l2_rfk);

err_dvfs_l2_lock_alloc:
	rfkill_unregister(bt_lock_dvfs_rfk);
	
err_lock_dvfs_register:
	rfkill_destroy(bt_lock_dvfs_rfk);

err_dvfs_lock_alloc:
	rfkill_unregister(bt_sleep_rfk);
#endif

#ifdef BT_SLEEP_ENABLE
err_sleep_register:
	rfkill_destroy(bt_sleep_rfk);

err_sleep_alloc:
	gpio_free(GPIO_BT_WAKE);
	
err_req_gpio_bt_wake:
	rfkill_unregister(bt_rfk);
#endif

 err_register:
	rfkill_destroy(bt_rfk);

 err_alloc:
	free_irq(irq, NULL);

 err_req_irq:
	gpio_free(GPIO_BTnRST);

 err_req_gpio_bt_nrst:
	gpio_free(GPIO_WLAN_BT_EN);

 err_req_gpio_wlan_bt_en:
	return ret;
}
Пример #12
0
static int rfkill_rk_probe(struct platform_device *pdev)
{
	struct rfkill_rk_data *rfkill;
	struct rfkill_rk_platform_data *pdata = pdev->dev.platform_data;
	int ret = 0;

    DBG("Enter %s\n", __func__);

	if (!pdata) {
		LOG("%s: No platform data specified\n", __func__);
		return -EINVAL;
	}

    pdata->name = (char*)bt_name;

	rfkill = kzalloc(sizeof(*rfkill), GFP_KERNEL);
	if (!rfkill)
		return -ENOMEM;

	rfkill->pdata = pdata;
    g_rfkill = rfkill;

    // 申请GPIO以及IRQ
    DBG("init gpio\n");
    // 对于RK29 BCM4329,它的poweron io与wifi共用,在boad文件中已经request
    // 此处不用去申请
#if !WIFI_BT_POWER_TOGGLE
    ret = rfkill_rk_setup_gpio(&pdata->poweron_gpio, IOMUX_FGPIO, pdata->name, "poweron");
    if (ret) goto fail_alloc;
#endif

    ret = rfkill_rk_setup_gpio(&pdata->reset_gpio, IOMUX_FGPIO, pdata->name, "reset");
    if (ret) goto fail_poweron;

    ret = rfkill_rk_setup_gpio(&pdata->wake_gpio, IOMUX_FGPIO, pdata->name, "wake");
    if (ret) goto fail_reset;

    ret = rfkill_rk_setup_wake_irq(rfkill);
    if (ret) goto fail_wake;

    ret = rfkill_rk_setup_gpio(&(pdata->rts_gpio), IOMUX_FNORMAL, rfkill->pdata->name, "rts");
    if (ret) goto fail_wake_host_irq;

    // 创建并注册RFKILL设备
    DBG("setup rfkill\n");
	rfkill->rfkill_dev = rfkill_alloc(pdata->name, &pdev->dev, pdata->type,
				&rfkill_rk_ops, rfkill);
	if (!rfkill->rfkill_dev)
		goto fail_rts;

    // cmy: 设置rfkill初始状态为blocked,在注册时不会调用 set_blocked函数
    rfkill_set_states(rfkill->rfkill_dev, BT_BLOCKED, false);
	ret = rfkill_register(rfkill->rfkill_dev);
	if (ret < 0)
		goto fail_rfkill;

    wake_lock_init(&(rfkill->bt_irq_wl), WAKE_LOCK_SUSPEND, "rfkill_rk_irq_wl");
    INIT_DELAYED_WORK(&rfkill->bt_sleep_delay_work, rfkill_rk_delay_sleep_bt);

    // cmy: 设置蓝牙电源的状态为 blocked
    rfkill_rk_set_power(rfkill, BT_BLOCKED);

	platform_set_drvdata(pdev, rfkill);

    LOG("%s device registered.\n", pdata->name);

	return 0;

fail_rfkill:
	rfkill_destroy(rfkill->rfkill_dev);
fail_rts:
    if (gpio_is_valid(pdata->rts_gpio.io))
        gpio_free(pdata->rts_gpio.io);
fail_wake_host_irq:
    if (gpio_is_valid(pdata->wake_host_irq.gpio.io)){
        free_irq(pdata->wake_host_irq.irq, rfkill);
        gpio_free(pdata->wake_host_irq.gpio.io);
    }
fail_wake:
    if (gpio_is_valid(pdata->wake_gpio.io))
        gpio_free(pdata->wake_gpio.io);
fail_reset:
	if (gpio_is_valid(pdata->reset_gpio.io))
		gpio_free(pdata->reset_gpio.io);
fail_poweron:
#if !WIFI_BT_POWER_TOGGLE
    if (gpio_is_valid(pdata->poweron_gpio.io))
        gpio_free(pdata->poweron_gpio.io);
#endif
fail_alloc:
	kfree(rfkill);
    g_rfkill = NULL;

	return ret;
}
Пример #13
0
static int wl127x_rfkill_probe(struct platform_device *pdev)
{
	int rc = 0;
	struct wl127x_rfkill_platform_data *pdata = pdev->dev.platform_data;

	if (pdata->bt_nshutdown_gpio >= 0) {
		rc = gpio_request(pdata->bt_nshutdown_gpio,
				  "wl127x_bt_nshutdown_gpio");
		if (unlikely(rc))
			return rc;

		rc = gpio_direction_output(pdata->bt_nshutdown_gpio, 0);
		if (unlikely(rc))
			return rc;

		if (pdata->bt_hw_init)
			rc = pdata->bt_hw_init();
		if (unlikely(rc))
			return rc;

		wl127x_bt_rfkill_set_power((void *)pdata, 1);

		pdata->rfkill[WL127X_BLUETOOTH] =
			rfkill_alloc("wl127x Bluetooth", &pdev->dev,
				RFKILL_TYPE_BLUETOOTH, &wl127x_bt_rfkill_ops, (void *)pdata);

		if (unlikely(!pdata->rfkill[WL127X_BLUETOOTH]))
			return -ENOMEM;

		rc = rfkill_register(pdata->rfkill[WL127X_BLUETOOTH]);
		if (unlikely(rc)) {
			rfkill_destroy(pdata->rfkill[WL127X_BLUETOOTH]);
			return rc;
		}
	}

	if (pdata->fm_enable_gpio >= 0) {
		rc = gpio_request(pdata->fm_enable_gpio,
				  "wl127x_fm_enable_gpio");
		if (unlikely(rc))
			return rc;

		rc = gpio_direction_output(pdata->fm_enable_gpio, 0);
		if (unlikely(rc))
			return rc;

		wl127x_fm_rfkill_set_power((void *)pdata->fm_enable_gpio, 1);

		pdata->rfkill[WL127X_FM] =
			rfkill_alloc("wl127x FM Radio", &pdev->dev,
				RFKILL_TYPE_FM, &wl127x_fm_rfkill_ops, (void *)pdata->fm_enable_gpio);
		if (unlikely(!pdata->rfkill[WL127X_FM]))
			return -ENOMEM;

		rc = rfkill_register(pdata->rfkill[WL127X_FM]);
		if (unlikely(rc)) {
			rfkill_destroy(pdata->rfkill[WL127X_FM]);
			return rc;
		}
	}

	return 0;
}
Пример #14
0
static int __init hp_wmi_rfkill2_setup(struct platform_device *device)
{
	struct bios_rfkill2_state state;
	int err, i;

	err = hp_wmi_perform_query(HPWMI_WIRELESS2_QUERY, HPWMI_READ, &state,
				   0, sizeof(state));
	if (err)
		return err < 0 ? err : -EINVAL;

	if (state.count > HPWMI_MAX_RFKILL2_DEVICES) {
		pr_warn("unable to parse 0x1b query output\n");
		return -EINVAL;
	}

	for (i = 0; i < state.count; i++) {
		struct rfkill *rfkill;
		enum rfkill_type type;
		char *name;
		switch (state.device[i].radio_type) {
		case HPWMI_WIFI:
			type = RFKILL_TYPE_WLAN;
			name = "hp-wifi";
			break;
		case HPWMI_BLUETOOTH:
			type = RFKILL_TYPE_BLUETOOTH;
			name = "hp-bluetooth";
			break;
		case HPWMI_WWAN:
			type = RFKILL_TYPE_WWAN;
			name = "hp-wwan";
			break;
		case HPWMI_GPS:
			type = RFKILL_TYPE_GPS;
			name = "hp-gps";
			break;
		default:
			pr_warn("unknown device type 0x%x\n",
				state.device[i].radio_type);
			continue;
		}

		if (!state.device[i].vendor_id) {
			pr_warn("zero device %d while %d reported\n",
				i, state.count);
			continue;
		}

		rfkill = rfkill_alloc(name, &device->dev, type,
				      &hp_wmi_rfkill2_ops, (void *)(long)i);
		if (!rfkill) {
			err = -ENOMEM;
			goto fail;
		}

		rfkill2[rfkill2_count].id = state.device[i].rfkill_id;
		rfkill2[rfkill2_count].num = i;
		rfkill2[rfkill2_count].rfkill = rfkill;

		rfkill_init_sw_state(rfkill,
				     IS_SWBLOCKED(state.device[i].power));
		rfkill_set_hw_state(rfkill,
				    IS_HWBLOCKED(state.device[i].power));

		if (!(state.device[i].power & HPWMI_POWER_BIOS))
			pr_info("device %s blocked by BIOS\n", name);

		err = rfkill_register(rfkill);
		if (err) {
			rfkill_destroy(rfkill);
			goto fail;
		}

		rfkill2_count++;
	}

	return 0;
fail:
	for (; rfkill2_count > 0; rfkill2_count--) {
		rfkill_unregister(rfkill2[rfkill2_count - 1].rfkill);
		rfkill_destroy(rfkill2[rfkill2_count - 1].rfkill);
	}
	return err;
}
static int bcm4335_bluetooth_probe(struct platform_device *pdev)
{
	int rc = 0;
	int ret;

	rc = gpio_request(GPIO_BT_EN, "bcm4335_bten_gpio");
	if (unlikely(rc)) {
		pr_err("[BT] GPIO_BT_EN request failed.\n");
		return rc;
	}
	rc = gpio_request(GPIO_BT_WAKE, "bcm4335_btwake_gpio");
	if (unlikely(rc)) {
		pr_err("[BT] GPIO_BT_WAKE request failed.\n");
		gpio_free(GPIO_BT_EN);
		return rc;
	}
	rc = gpio_request(GPIO_BT_HOST_WAKE, "bcm4335_bthostwake_gpio");
	if (unlikely(rc)) {
		pr_err("[BT] GPIO_BT_HOST_WAKE request failed.\n");
		gpio_free(GPIO_BT_WAKE);
		gpio_free(GPIO_BT_EN);
		return rc;
	}
	s3c_gpio_setpull(GPIO_BT_HOST_WAKE, S3C_GPIO_PULL_NONE);
	gpio_direction_input(GPIO_BT_HOST_WAKE);
	gpio_direction_output(GPIO_BT_WAKE, 0);
	gpio_direction_output(GPIO_BT_EN, 0);

	bt_rfkill = rfkill_alloc("bcm4335 Bluetooth", &pdev->dev,
				RFKILL_TYPE_BLUETOOTH, &bcm4335_bt_rfkill_ops,
				NULL);

	if (unlikely(!bt_rfkill)) {
		pr_err("[BT] bt_rfkill alloc failed.\n");
		gpio_free(GPIO_BT_HOST_WAKE);
		gpio_free(GPIO_BT_WAKE);
		gpio_free(GPIO_BT_EN);
		return -ENOMEM;
	}

	rfkill_init_sw_state(bt_rfkill, 0);

	rc = rfkill_register(bt_rfkill);

	if (unlikely(rc)) {
		pr_err("[BT] bt_rfkill register failed.\n");
		rfkill_destroy(bt_rfkill);
		gpio_free(GPIO_BT_HOST_WAKE);
		gpio_free(GPIO_BT_WAKE);
		gpio_free(GPIO_BT_EN);
		return -1;
	}

	rfkill_set_sw_state(bt_rfkill, true);

#ifdef BT_LPM_ENABLE
	ret = bcm_bt_lpm_init(pdev);
	if (ret) {
		rfkill_unregister(bt_rfkill);
		rfkill_destroy(bt_rfkill);

		gpio_free(GPIO_BT_HOST_WAKE);
		gpio_free(GPIO_BT_WAKE);
		gpio_free(GPIO_BT_EN);
	}
#endif
	return rc;
}
static int __init smba_gsm_probe(struct platform_device *pdev)
{
	struct rfkill *rfkill;
	struct regulator *regulator[2];
	struct smba_pm_gsm_data *gsm_data;
	int ret;

	gsm_data = kzalloc(sizeof(*gsm_data), GFP_KERNEL);
	if (!gsm_data) {
		dev_err(&pdev->dev, "no memory for context\n");
		return -ENOMEM;
	}
	dev_set_drvdata(&pdev->dev, gsm_data);

	regulator[0] = regulator_get(&pdev->dev, "avdd_usb_pll");
	if (IS_ERR(regulator[0])) {
		dev_err(&pdev->dev, "unable to get regulator for usb pll\n");
		kfree(gsm_data);
		dev_set_drvdata(&pdev->dev, NULL);
		return -ENODEV;
	}
	gsm_data->regulator[0] = regulator[0];

	regulator[1] = regulator_get(&pdev->dev, "avdd_usb");
	if (IS_ERR(regulator[1])) {
		dev_err(&pdev->dev, "unable to get regulator for usb\n");
		regulator_put(regulator[0]);
		gsm_data->regulator[0] = NULL;
		kfree(gsm_data);
		dev_set_drvdata(&pdev->dev, NULL);
		return -ENODEV;
	}
	gsm_data->regulator[1] = regulator[1];
	
	/* Init control pins */
	gpio_request(SMBA9701_3G_DISABLE, "gsm_disable");
	gpio_direction_output(SMBA9701_3G_DISABLE, 1);
//	smba_3g_gps_init();

	/* register rfkill interface */
	rfkill = rfkill_alloc(pdev->name, &pdev->dev, RFKILL_TYPE_WWAN,
                            &smba_gsm_rfkill_ops, &pdev->dev);

	if (!rfkill) {
		dev_err(&pdev->dev, "Failed to allocate rfkill\n");
		regulator_put(regulator[1]);
		gsm_data->regulator[1] = NULL;
		regulator_put(regulator[0]);
		gsm_data->regulator[0] = NULL;
		kfree(gsm_data);
		dev_set_drvdata(&pdev->dev, NULL);
		return -ENOMEM;
	}
	gsm_data->rfkill = rfkill;

	/* Disable bluetooth */
    rfkill_init_sw_state(rfkill, 0);

	ret = rfkill_register(rfkill);
	if (ret) {
		rfkill_destroy(rfkill);
		dev_err(&pdev->dev, "Failed to register rfkill\n");
		return ret;
	}

	dev_info(&pdev->dev, "GSM/UMTS RFKill driver loaded\n");
	
	return sysfs_create_group(&pdev->dev.kobj, &smba_gsm_attr_group);
}
static int tcc_bluetooth_probe(struct platform_device *pdev)
{
	int rc = 0;
	int ret = 0;

	printk("[## BT ##] tcc_bluetooth_probe\n");
	if( machine_is_tcc8800()|| machine_is_tcc8920()) {      // #elif defined (CONFIG_MACH_TCC9300)
			//gpio_set_value(TCC_GPEXT1(7), 0);   /* BT-ON Disable */
		gpio_request(TCC_GPEXT3(2), "bt_wake");
	       gpio_request(TCC_GPEXT2(4), "bt_reset");
		gpio_direction_output(TCC_GPEXT3(2), 0); // output
		gpio_direction_output(TCC_GPEXT2(4), 0);
#if defined(CONFIG_TCC_CSR_BC0406_MODULE_SUPPORT) && defined(CONFIG_TCC_CSR_HOST_WAKE_UP)
		tcc_gpio_config(TCC_GPB(31), GPIO_FN(0));
		gpio_request(TCC_GPEXT3(3), "bt_hwake");
		gpio_direction_input(TCC_GPEXT3(3));
#endif // for CSR Bluetooth host wake up
	}
	else if(machine_is_m801_88() || machine_is_m803())
	{
		#if defined(CONFIG_TCC_RDA_587X_MODULE_SUPPORT)
		gpio_request(TCC_GPA(13), "LDO_ON");
		tcc_gpio_config(TCC_GPA(13), GPIO_FN(0));
		gpio_direction_output(TCC_GPA(13), 0);
		#else
		gpio_request(TCC_GPA(13), "bt_reset");
		gpio_request(TCC_GPB(22), "BT WAKE");
		gpio_direction_output(TCC_GPA(13), 0); // output
		gpio_direction_output(TCC_GPB(22), 0); // output
		#endif

	}
	else if(machine_is_tcc8800st())
	{
		gpio_request(TCC_GPC(31), "bt_power");
		gpio_request(TCC_GPD(12), "bt_reset");
		gpio_direction_output(TCC_GPC(31), 0); // output
		gpio_direction_output(TCC_GPD(12), 0); // output
	}
/*
	rc = gpio_request(BT_RESET_GPIO, "bcm4330_nreset_gpip");
	if (unlikely(rc)) {
		return rc;
	}

	rc = gpio_request(BT_REG_GPIO, "bcm4330_nshutdown_gpio");
	if (unlikely(rc)) {
		gpio_free(BT_RESET_GPIO);
		return rc;
	}
*/
	bt_rfkill = rfkill_alloc("Telechips Bluetooth", &pdev->dev,
				RFKILL_TYPE_BLUETOOTH, &tcc_bt_rfkill_ops,
				NULL);

	if (unlikely(!bt_rfkill)) {
		//gpio_free(BT_RESET_GPIO);
		//gpio_free(BT_REG_GPIO);
		printk("[## BT ##] rfkill_alloc failed \n");
		return -ENOMEM;
	}

	rc = rfkill_register(bt_rfkill);

	if (unlikely(rc)) {
		printk("[## BT ##] rfkill_register failed \n");
		rfkill_destroy(bt_rfkill);
		//gpio_free(BT_RESET_GPIO);
		//gpio_free(BT_REG_GPIO);
		return -1;
	}

	printk("[## BT ##] rfkill_register Telechips Bluetooth \n");

	rfkill_set_states(bt_rfkill, true, false);
	tcc_bt_rfkill_set_power(NULL, true);

#if defined (CONFIG_TCC_BRCM_BCM4330_MODULE_SUPPORT)
	ret = bcm_bt_lpm_init(pdev);
	if (ret) {
		rfkill_unregister(bt_rfkill);
		rfkill_destroy(bt_rfkill);

		//gpio_free(BT_RESET_GPIO);
		//gpio_free(BT_REG_GPIO);
	}
#endif

	return ret;
}
Пример #18
0
static int __devinit bt_probe(struct platform_device *pdev)
{
	int ret = 0;
	struct bt_rfkill_info *bt_info;
	struct mx_rfkill_pd *pdata = pdev->dev.platform_data;

	if (pdata == NULL) {
		dev_err(&pdev->dev,"Failed to get platform data\n");
		return -ENOENT;
	}
	bt_info = kzalloc(sizeof(struct bt_rfkill_info), GFP_KERNEL);
	if(!bt_info) {
		ret = -ENOMEM;
		pr_debug("[BT]  sysfs_create_group failed\n");
		goto err_req_bt_mem;
	}

	bt_info->name = pdata->name;
	bt_info->gpio_bt_power = pdata->bt_power;
	bt_info->gpio_bt_reset = pdata->bt_reset;
	bt_info->gpio_bt_wake = pdata->bt_wake;
	bt_info->gpio_bt_host_wake = pdata->bt_host_wake;
	bt_info->gpio_wifi_power = pdata->wifi_power;
	bt_info->gpio_wifi_reset = pdata->wifi_reset;
	bt_info->dev = &pdev->dev;
	
	/* Initialize wake locks */
	wake_lock_init(&bt_info->rfk_lock, WAKE_LOCK_SUSPEND, "bt_host_wake");

	/* BT Host Wake IRQ */
	bt_info->wake_irq = gpio_to_irq(bt_info->gpio_bt_host_wake);
	ret = request_threaded_irq(bt_info->wake_irq, NULL, bt_host_wake_irq_handler,
			IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING,
			"bt_host_wake_irq_handler", bt_info);

	if (ret < 0) {
		pr_err("[BT] Request_irq failed\n");
		goto err_req_irq;
	}

	disable_irq(bt_info->wake_irq);

	/* init rfkill */
	bt_info->bt_rfk = rfkill_alloc(bt_info->name, &pdev->dev, RFKILL_TYPE_BLUETOOTH,
			&bt_rfkill_ops, bt_info);

	if (!bt_info->bt_rfk) {
		pr_err("[BT] bt_rfk : rfkill_alloc is failed\n");
		ret = -ENOMEM;
		goto err_rfkill_alloc;
	}

	rfkill_init_sw_state(bt_info->bt_rfk, 0);	

	ret = rfkill_register(bt_info->bt_rfk);
	if (ret) {
		pr_debug("********ERROR IN REGISTERING THE RFKILL********\n");
		goto err_register;
	}

	rfkill_set_sw_state(bt_info->bt_rfk, 1);
	
	/* init low power state*/
	ret = bt_lpm_init(bt_info);
	if (ret < 0) {
		pr_debug("[BT]  set low power failed\n");
		goto err_register;
	}

	bt_info->bt_test_mode =0;     //bt   in normal mode
	bt_info->bt_enable = 0;
	bt_info->bt_wake = 0;
	mutex_init(&bt_info->bt_lock);

	/* create sysfs attributes */
	ret = sysfs_create_group(&pdev->dev.kobj, &bcm_attribute_group);
	if (ret < 0) {
		pr_debug("[BT]  sysfs_create_group failed\n");
		goto err_register;
	}

	device_init_wakeup(&pdev->dev, 1);

	/* set init power state*/
	bt_set_power(bt_info, RFKILL_USER_STATE_SOFT_BLOCKED);

	platform_set_drvdata(pdev, bt_info);
	g_bt_info = bt_info;

	pr_info("[BT] driver loaded!\n");
	return ret;

err_register:
	rfkill_destroy(bt_info->bt_rfk);

err_rfkill_alloc:
	free_irq(bt_info->wake_irq, NULL);

err_req_irq:
	wake_lock_destroy(&bt_info->rfk_lock);
	kfree(bt_info);

err_req_bt_mem:
	return ret;
}
static int bcm4339_bluetooth_probe(struct platform_device *pdev)
{
    int rc = 0;

#ifdef BT_UART_CFG
    int pin = 0;
#endif
#if defined(CONFIG_BCM4335) || defined(CONFIG_BCM4335_MODULE) || defined(CONFIG_BCM4339) || defined(CONFIG_BCM4339_MODULE)
    bt_is_running = 0;
#endif
    rc = gpio_request(get_gpio_hwrev(BT_EN), "bcm4339_bten_gpio");
    if (unlikely(rc)) {
        pr_err("[BT] GPIO_BT_EN request failed.\n");
        return rc;
    }

#if defined(CONFIG_SEC_PATEK_PROJECT)
    gpio_tlmm_config(GPIO_CFG(BT_EN, 0, GPIO_CFG_OUTPUT,
                              GPIO_CFG_PULL_DOWN, GPIO_CFG_8MA), GPIO_CFG_ENABLE);
    gpio_set_value(BT_EN, 0);
    gpio_tlmm_config(GPIO_CFG(BT_WAKE, 0, GPIO_CFG_OUTPUT,
                              GPIO_CFG_NO_PULL, GPIO_CFG_8MA), GPIO_CFG_ENABLE);
    gpio_set_value(BT_WAKE, 0);
#else
    gpio_direction_output(get_gpio_hwrev(BT_EN), 0);
#endif

    /* gpio request for bt_wake will be in bluesleeep.
    rc = gpio_request(get_gpio_hwrev(BT_WAKE), "bcm4339_btwake_gpio");
    if (unlikely(rc)) {
        pr_err("[BT] GPIO_BT_WAKE request failed.\n");
        return rc;
    }
    gpio_direction_output(get_gpio_hwrev(BT_WAKE), 0);
    */

    /* temporailiy set HOST_WAKE OUT direction until FPGA work finishs */
    /* if setting HOST_WAKE to NO PULL, BT would not be turned on. */
    /* By guideline of BRCM, it is needed to determine pull status */
#ifndef BT_LPM_ENABLE
    gpio_tlmm_config(GPIO_CFG(get_gpio_hwrev(GPIO_BT_HOST_WAKE), 0, GPIO_CFG_OUTPUT,
                              GPIO_CFG_PULL_UP, GPIO_CFG_8MA), GPIO_CFG_ENABLE);
    gpio_set_value(get_gpio_hwrev(GPIO_BT_HOST_WAKE), 1);

#endif

#ifdef BT_UART_CFG
    for (pin = 0; pin < ARRAY_SIZE(bt_uart_off_table); pin++) {
        rc = gpio_tlmm_config(bt_uart_off_table[pin], GPIO_CFG_ENABLE);
        if (rc < 0)
            pr_err("%s: gpio_tlmm_config(%#x)=%d\n",
                   __func__, bt_uart_off_table[pin], rc);
    }
#endif

    bt_rfkill = rfkill_alloc("bcm4339 Bluetooth", &pdev->dev,
                             RFKILL_TYPE_BLUETOOTH, &bcm4339_bt_rfkill_ops,
                             NULL);

    if (unlikely(!bt_rfkill)) {
        pr_err("[BT] bt_rfkill alloc failed.\n");
        gpio_free(get_gpio_hwrev(BT_EN));
        return -ENOMEM;
    }


    rfkill_init_sw_state(bt_rfkill, 0);

    rc = rfkill_register(bt_rfkill);

    if (unlikely(rc)) {
        pr_err("[BT] bt_rfkill register failed.\n");
        rfkill_destroy(bt_rfkill);
        gpio_free(get_gpio_hwrev(BT_EN));
        gpio_free(get_gpio_hwrev(BT_WAKE));
        return rc;
    }


    rfkill_set_sw_state(bt_rfkill, true);

    return rc;
}
Пример #20
0
static int bcm4329_rfkill_probe(struct platform_device *pdev)
{
	struct rfkill *bt_rfkill;
	struct resource *res;
	int ret;
	bool enable = false;  /* off */
	bool default_sw_block_state;

	bcm4329_rfkill = kzalloc(sizeof(*bcm4329_rfkill), GFP_KERNEL);
	if (!bcm4329_rfkill)
		return -ENOMEM;

	/**
	bcm4329_rfkill->bt_32k_clk = clk_get(&pdev->dev, "bcm4329_32k_clk");
	if (IS_ERR(bcm4329_rfkill->bt_32k_clk)) {
		pr_warn("%s: can't find bcm4329_32k_clk.\
				assuming 32k clock to chip\n", __func__);
		bcm4329_rfkill->bt_32k_clk = NULL;
	}
	**/

	res = platform_get_resource_byname(pdev, IORESOURCE_IO,
						"bcm4329_nreset_gpio");
	if (res) {
		bcm4329_rfkill->gpio_reset = res->start;
		ret = gpio_request(bcm4329_rfkill->gpio_reset,
						"bcm4329_nreset_gpio");
	} else {
		pr_warn("%s : can't find reset gpio. "
			"reset gpio may not be defined for "
			"this platform \n", __func__);
		bcm4329_rfkill->gpio_reset = 0;
	}

	res = platform_get_resource_byname(pdev, IORESOURCE_IO,
						"bcm4329_nshutdown_gpio");
	if (res) {
		bcm4329_rfkill->gpio_shutdown = res->start;
		ret = gpio_request(bcm4329_rfkill->gpio_shutdown,
						"bcm4329_nshutdown_gpio");
	} else {
		pr_warn("%s : can't find shutdown gpio "
			"shutdown gpio may not be defined for "
			"this platform \n", __func__);
		bcm4329_rfkill->gpio_shutdown = 0;
	}

	/* make sure at-least one of the GPIO is defined */
	if (!bcm4329_rfkill->gpio_reset && !bcm4329_rfkill->gpio_shutdown)
		goto free_bcm_res;
	/**
	if (bcm4329_rfkill->bt_32k_clk && enable)
		clk_enable(bcm4329_rfkill->bt_32k_clk);
	**/
	if (bcm4329_rfkill->gpio_shutdown)
		gpio_direction_output(bcm4329_rfkill->gpio_shutdown, enable);
	if (bcm4329_rfkill->gpio_reset)
		gpio_direction_output(bcm4329_rfkill->gpio_reset, enable);

	bt_rfkill = rfkill_alloc("bcm4329 Bluetooth", &pdev->dev,
				RFKILL_TYPE_BLUETOOTH, &bcm4329_bt_rfkill_ops,
				NULL);

	if (unlikely(!bt_rfkill))
		goto free_bcm_res;

	default_sw_block_state = !enable;
	rfkill_set_states(bt_rfkill, default_sw_block_state, false);

	ret = rfkill_register(bt_rfkill);

	if (unlikely(ret)) {
		rfkill_destroy(bt_rfkill);
		goto free_bcm_res;
	}

	return 0;

free_bcm_res:
	if (bcm4329_rfkill->gpio_shutdown)
		gpio_free(bcm4329_rfkill->gpio_shutdown);
	if (bcm4329_rfkill->gpio_reset)
		gpio_free(bcm4329_rfkill->gpio_reset);
	/**
	if (bcm4329_rfkill->bt_32k_clk && enable)
		clk_disable(bcm4329_rfkill->bt_32k_clk);
	if (bcm4329_rfkill->bt_32k_clk)
		clk_put(bcm4329_rfkill->bt_32k_clk);
	**/
	kfree(bcm4329_rfkill);
	return -ENODEV;
}
static int __init bluetooth_rfkill_probe(struct platform_device *pdev)
{
	int ret;

	/* Initialize wake locks */
	wake_lock_init(&rfkill_wake_lock, WAKE_LOCK_SUSPEND, "bt_host_wake");

	bt_dev = pdev;

	ret = gpio_request(OMAP_GPIO_BT_EN, "gpio_bt_en");
	if (ret < 0) {
		pr_err("[BT] Failed to request GPIO_BT_EN!\n");
		goto err_req_gpio_bt_en;
	}

	ret = gpio_request(OMAP_GPIO_BT_nRST, "gpio_bt_nrst");
	if (ret < 0) {
		pr_err("[BT] Failed to request GPIO_BT_nRST!\n");
		goto err_req_gpio_bt_nrst;
	}

	/* BT Host Wake IRQ */

	irq = gpio_to_irq(OMAP_GPIO_BT_HOST_WAKE);

	ret = request_irq(irq, bt_host_wake_irq_handler,
			IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING,
			"bt_host_wake_irq_handler", NULL);

	if (ret < 0) {
		pr_err("[BT] Request_irq failed\n");
		goto err_req_irq;
	}

	disable_irq(irq);

	bt_rfk = rfkill_alloc(bt_name, &pdev->dev, RFKILL_TYPE_BLUETOOTH,
			&bt_rfkill_ops, NULL);

	if (!bt_rfk) {
		pr_err("[BT] bt_rfk : rfkill_alloc is failed\n");
		ret = -ENOMEM;
		goto err_alloc;
	}

	rfkill_init_sw_state(bt_rfk, 0);

	pr_info("[BT] rfkill_register(bt_rfk)\n");

	ret = rfkill_register(bt_rfk);
	if (ret) {
		pr_err("********ERROR IN REGISTERING THE bt_rfk********\n");
		goto err_register;
	}

	rfkill_set_sw_state(bt_rfk, 1);

#ifdef BT_SLEEP_ENABLE
	wake_lock_init(&bt_wake_lock, WAKE_LOCK_SUSPEND, "bt_wake");

	ret = gpio_request(OMAP_GPIO_BT_WAKE, "gpio_bt_wake");
	if (ret < 0) {
		pr_err("[BT] Failed to request GPIO_BT_WAKE\n");
		goto err_req_gpio_bt_wake;
	}

	gpio_direction_output(OMAP_GPIO_BT_WAKE, GPIO_LEVEL_LOW);

	bt_sleep_rfk = rfkill_alloc(bt_name, &pdev->dev, RFKILL_TYPE_BLUETOOTH,
			&btsleep_rfkill_ops, NULL);

	if (!bt_sleep_rfk) {
		pr_err("[BT] bt_sleep_rfk : rfkill_alloc is failed\n");
		ret = -ENOMEM;
		goto err_sleep_alloc;
	}

	rfkill_set_sw_state(bt_sleep_rfk, 1);

	pr_info("[BT] rfkill_register(bt_sleep_rfk)\n");

	ret = rfkill_register(bt_sleep_rfk);
	if (ret) {
		pr_err("********ERROR IN REGISTERING THE bt_sleep_rfk********\n");
		goto err_sleep_register;
	}
#endif

	return ret;

#ifdef BT_SLEEP_ENABLE
err_sleep_register:
	rfkill_destroy(bt_sleep_rfk);

err_sleep_alloc:
	gpio_free(OMAP_GPIO_BT_WAKE);
	
err_req_gpio_bt_wake:
	rfkill_unregister(bt_rfk);
#endif

 err_register:
	rfkill_destroy(bt_rfk);

 err_alloc:
	free_irq(irq, NULL);

 err_req_irq:
	gpio_free(OMAP_GPIO_BT_nRST);

 err_req_gpio_bt_nrst:
	gpio_free(OMAP_GPIO_BT_EN);

 err_req_gpio_bt_en:
	return ret;
}
Пример #22
0
static int __init crespo_rfkill_probe(struct platform_device *pdev)
{
	int irq;
	int ret;

	/* Initialize wake locks */
	wake_lock_init(&rfkill_wake_lock, WAKE_LOCK_SUSPEND, "bt_host_wake");

/* CSR8811 Project(Alan.Ko) 2011.07.02 */
#if 0
	ret = gpio_request(GPIO_BT_EN, "GPB");
	if (ret < 0) {
		pr_err("[BT] Failed to request GPIO_BT_EN!\n");
		goto err_req_gpio_bt_en;
	}
#endif
/* CSR8811 Project(Alan.Ko) End */

	ret = gpio_request(GPIO_BT_nRST, "GPB");
	if (ret < 0) {
		pr_err("[BT] Failed to request GPIO_BT_nRST!\n");
		goto err_req_gpio_bt_nrst;
	}

	/* BT Host Wake IRQ */
	irq = IRQ_BT_HOST_WAKE;

	ret = request_irq(irq, bt_host_wake_irq_handler,
			IRQF_TRIGGER_RISING,
			"bt_host_wake_irq_handler", NULL);

	if (ret < 0) {
		pr_err("[BT] Request_irq failed\n");
		goto err_req_irq;
	}

	disable_irq(irq);

	bt_rfk = rfkill_alloc(bt_name, &pdev->dev, RFKILL_TYPE_BLUETOOTH,
			&bt_rfkill_ops, NULL);

	if (!bt_rfk) {
		pr_err("[BT] bt_rfk : rfkill_alloc is failed\n");
		ret = -ENOMEM;
		goto err_alloc;
	}

	rfkill_init_sw_state(bt_rfk, 0);

	pr_debug("[BT] rfkill_register(bt_rfk)\n");

	ret = rfkill_register(bt_rfk);
	if (ret) {
		pr_err("********ERROR IN REGISTERING THE bt_rfk********\n");
		goto err_register;
	}

	rfkill_set_sw_state(bt_rfk, 1);
	bluetooth_set_power(NULL, RFKILL_USER_STATE_SOFT_BLOCKED);

#ifdef BT_SLEEP_ENABLE
	wake_lock_init(&bt_wake_lock, WAKE_LOCK_SUSPEND, "bt_wake");

/* CSR8811 Project(Alan.Ko) 2011.07.02 */
#if 0
	ret = gpio_request(GPIO_BT_WAKE, "gpio_bt_wake");
	if (ret < 0) {
		pr_err("[BT] Failed to request GPIO_BT_WAKE\n");
		goto err_req_gpio_bt_wake;
	}

	gpio_direction_output(GPIO_BT_WAKE, GPIO_LEVEL_LOW);
#endif
/* CSR8811 Project(Alan.Ko) End */

	bt_sleep_rfk = rfkill_alloc(bt_name, &pdev->dev, RFKILL_TYPE_BLUETOOTH,
			&btsleep_rfkill_ops, NULL);

	if (!bt_sleep_rfk) {
		pr_err("[BT] bt_sleep_rfk : rfkill_alloc is failed\n");
		ret = -ENOMEM;
		goto err_sleep_alloc;
	}

	rfkill_set_sw_state(bt_sleep_rfk, 1);

	pr_debug("[BT] rfkill_register(bt_sleep_rfk)\n");

	ret = rfkill_register(bt_sleep_rfk);
	if (ret) {
		pr_err("********ERROR IN REGISTERING THE bt_sleep_rfk********\n");
		goto err_sleep_register;
	}
#endif

	return ret;

#ifdef BT_SLEEP_ENABLE
err_sleep_register:
	rfkill_destroy(bt_sleep_rfk);

err_sleep_alloc:
/* CSR8811 Project(Alan.Ko) 2011.07.02 */
#if 0
	gpio_free(GPIO_BT_WAKE);
#endif
/* CSR8811 Project(Alan.Ko) End */

err_req_gpio_bt_wake:
	rfkill_unregister(bt_rfk);
#endif

 err_register:
	rfkill_destroy(bt_rfk);

 err_alloc:
	free_irq(irq, NULL);

 err_req_irq:
	gpio_free(GPIO_BT_nRST);

 err_req_gpio_bt_nrst:
/* CSR8811 Project(Alan.Ko) 2011.07.02 */
#if 0
	gpio_free(GPIO_BT_EN);
#endif
/* CSR8811 Project(Alan.Ko) End */
 err_req_gpio_bt_en:
	return ret;
}
Пример #23
0
static int __devinit bcm4329_rfkill_probe(struct platform_device *pdev)
{
	int rc = 0;
	bool default_state = true;
	
	DBG("Enter %s\n",__FUNCTION__);
	
	/* default to bluetooth off */
 	bcm4329_set_block(NULL, default_state); /* blocked -> bt off */
	 
	gBtCtrl.bt_rfk = rfkill_alloc(bt_name, 
                NULL, 
                RFKILL_TYPE_BLUETOOTH, 
                &bcm4329_rfk_ops, 
                NULL);

	if (!gBtCtrl.bt_rfk)
	{
		LOG("fail to rfkill_allocate\n");
		return -ENOMEM;
	}
	
	rfkill_set_states(gBtCtrl.bt_rfk, default_state, false);

	rc = rfkill_register(gBtCtrl.bt_rfk);
	if (rc)
	{
		LOG("failed to rfkill_register,rc=0x%x\n",rc);
		rfkill_destroy(gBtCtrl.bt_rfk);
	}
	
	gpio_request(BT_GPIO_POWER, NULL);
	gpio_request(BT_GPIO_RESET, NULL);
	gpio_request(BT_GPIO_WAKE_UP, NULL);
    
#ifdef CONFIG_BT_AUTOSLEEP
    init_timer(&bt_sleep_tl);
    bt_sleep_tl.expires = 0;
    bt_sleep_tl.function = bcm4325_sleep;
    bt_sleep_tl.data = 1;
    add_timer(&bt_sleep_tl);
#endif

#if BT_WAKE_HOST_SUPPORT
    init_timer(&(gBtCtrl.tl));
    gBtCtrl.tl.expires = 0;
    gBtCtrl.tl.function = timer_hostSleep;
    add_timer(&(gBtCtrl.tl));
    gBtCtrl.b_HostWake = false;
    
	wake_lock_init(&(gBtCtrl.bt_wakelock), WAKE_LOCK_SUSPEND, "bt_wake");
	
	rc = gpio_request(BT_GPIO_WAKE_UP_HOST, "bt_wake");
	if (rc) {
		LOG("Failed to request BT_WAKE_UP_HOST\n");
	}
	
	IOMUX_BT_GPIO_WAKE_UP_HOST();
	gpio_pull_updown(BT_GPIO_WAKE_UP_HOST,GPIOPullUp);
 #endif
 
    LOG("bcm4329 module has been initialized,rc=0x%x\n",rc);
 
	return rc;
}
Пример #24
0
static int __devinit bcm4329_rfkill_probe(struct platform_device *pdev)
{
	int rc = 0;
	bool default_state = true;
	
	DBG("Enter::%s,line=%d\n",__FUNCTION__,__LINE__);
	
	/* default to bluetooth off */
 	bcm4329_set_block(NULL, default_state); /* blocked -> bt off */
	 
	gBtCtrl.bt_rfk = rfkill_alloc(bt_name, 
                NULL, 
                RFKILL_TYPE_BLUETOOTH, 
                &bcm4329_rfk_ops, 
                NULL);

	if (!gBtCtrl.bt_rfk)
	{
		printk("fail to rfkill_allocate************\n");
		return -ENOMEM;
	}
	
	rfkill_set_states(gBtCtrl.bt_rfk, default_state, false);

	rc = rfkill_register(gBtCtrl.bt_rfk);
	if (rc)
	{
		printk("failed to rfkill_register,rc=0x%x\n",rc);
		rfkill_destroy(gBtCtrl.bt_rfk);
	}
	
	gpio_request(BT_GPIO_POWER, NULL);
	gpio_request(BT_GPIO_RESET, NULL);
	gpio_request(BT_GPIO_WAKE_UP, NULL);

#if BT_WAKE_HOST_SUPPORT
    init_timer(&(gBtCtrl.tl));
    gBtCtrl.tl.expires = jiffies + BT_WAKE_LOCK_TIMEOUT*HZ;        
    gBtCtrl.tl.function = timer_hostSleep;        
    add_timer(&(gBtCtrl.tl));
    gBtCtrl.b_HostWake = false;
    
	wake_lock_init(&(gBtCtrl.bt_wakelock), WAKE_LOCK_SUSPEND, "bt_wake");
	
	rc = gpio_request(BT_GPIO_WAKE_UP_HOST, "bt_wake");
	if (rc) {
		printk("%s:failed to request RAHO_BT_WAKE_UP_HOST\n",__FUNCTION__);
	}
	
	IOMUX_BT_GPIO_WAKE_UP_HOST();
	gpio_pull_updown(BT_GPIO_WAKE_UP_HOST,GPIOPullUp);
	rc = request_irq(gpio_to_irq(BT_GPIO_WAKE_UP_HOST),bcm4329_wake_host_irq,IRQF_TRIGGER_FALLING,NULL,NULL);
	if(rc)
	{
		printk("%s:failed to request RAHO_BT_WAKE_UP_HOST irq\n",__FUNCTION__);
		gpio_free(BT_GPIO_WAKE_UP_HOST);
	}
	enable_irq_wake(gpio_to_irq(BT_GPIO_WAKE_UP_HOST)); // so RAHO_BT_WAKE_UP_HOST can wake up system

	printk(KERN_INFO "bcm4329 module has been initialized,rc=0x%x\n",rc);
 #endif
 
	return rc;

	
}
Пример #25
0
static int rfkill_gpio_probe(struct platform_device *pdev)
{
	struct rfkill_gpio_data *rfkill;
	struct rfkill_gpio_platform_data *pdata = pdev->dev.platform_data;
	int ret = 0;
	int len = 0;

	if (!pdata) {
		pr_warn("%s: No platform data specified\n", __func__);
		return -EINVAL;
	}

	/* make sure at-least one of the GPIO is defined and that
	 * a name is specified for this instance */
	if (!pdata->name || (!gpio_is_valid(pdata->reset_gpio) &&
		!gpio_is_valid(pdata->shutdown_gpio))) {
		pr_warn("%s: invalid platform data\n", __func__);
		return -EINVAL;
	}

	rfkill = kzalloc(sizeof(*rfkill), GFP_KERNEL);
	if (!rfkill)
		return -ENOMEM;

	rfkill->pdata = pdata;

	len = strlen(pdata->name);
	rfkill->reset_name = kzalloc(len + 7, GFP_KERNEL);
	if (!rfkill->reset_name) {
		ret = -ENOMEM;
		goto fail_alloc;
	}

	rfkill->shutdown_name = kzalloc(len + 10, GFP_KERNEL);
	if (!rfkill->shutdown_name) {
		ret = -ENOMEM;
		goto fail_reset_name;
	}

	snprintf(rfkill->reset_name, len + 6 , "%s_reset", pdata->name);
	snprintf(rfkill->shutdown_name, len + 9, "%s_shutdown", pdata->name);

	if (pdata->power_clk_name) {
		rfkill->pwr_clk = clk_get(&pdev->dev, pdata->power_clk_name);
		if (IS_ERR(rfkill->pwr_clk)) {
			pr_warn("%s: can't find pwr_clk.\n", __func__);
			goto fail_shutdown_name;
		}
	}

	if (gpio_is_valid(pdata->reset_gpio)) {
		ret = gpio_request(pdata->reset_gpio, rfkill->reset_name);
		if (ret) {
			pr_warn("%s: failed to get reset gpio.\n", __func__);
			goto fail_clock;
		}
	}

	if (gpio_is_valid(pdata->shutdown_gpio)) {
		ret = gpio_request(pdata->shutdown_gpio, rfkill->shutdown_name);
		if (ret) {
			pr_warn("%s: failed to get shutdown gpio.\n", __func__);
			goto fail_reset;
		}
	}

	rfkill->rfkill_dev = rfkill_alloc(pdata->name, &pdev->dev, pdata->type,
				&rfkill_gpio_ops, rfkill);
	if (!rfkill->rfkill_dev)
		goto fail_shutdown;

	ret = rfkill_register(rfkill->rfkill_dev);
	if (ret < 0)
		goto fail_rfkill;

	platform_set_drvdata(pdev, rfkill);

	dev_info(&pdev->dev, "%s device registered.\n", pdata->name);

	return 0;

fail_rfkill:
	rfkill_destroy(rfkill->rfkill_dev);
fail_shutdown:
	if (gpio_is_valid(pdata->shutdown_gpio))
		gpio_free(pdata->shutdown_gpio);
fail_reset:
	if (gpio_is_valid(pdata->reset_gpio))
		gpio_free(pdata->reset_gpio);
fail_clock:
	if (rfkill->pwr_clk)
		clk_put(rfkill->pwr_clk);
fail_shutdown_name:
	kfree(rfkill->shutdown_name);
fail_reset_name:
	kfree(rfkill->reset_name);
fail_alloc:
	kfree(rfkill);

	return ret;
}
Пример #26
0
static int lbee9qmb_rfkill_probe(struct platform_device *pdev)
{
	struct lbee9qmb_platform_data *plat = pdev->dev.platform_data;
	struct rfkill *rfkill;

	int rc;

	if (!plat) {
		dev_err(&pdev->dev, "no platform data\n");
		return -ENOSYS;
	}

	rc = gpio_request(plat->gpio_reset, "lbee9qmb_reset");
	if (rc < 0) {
		dev_err(&pdev->dev, "gpio_request failed\n");
		return rc;
	}
	if (plat->gpio_pwr!=-1)
	{
		rc = gpio_request(plat->gpio_pwr, "lbee9qmb_pwr");
		gpio_direction_output(plat->gpio_pwr,0);
	}
	if (plat->gpio_oldrst!=-1)
	{
		rc = gpio_request(plat->gpio_oldrst, "lbee9qmb_oldrst");
		gpio_direction_output(plat->gpio_oldrst,0);
	}
	if (plat->gpio_btwake!=-1)
	{
		rc = gpio_request(plat->gpio_btwake, "lbee9qmb_btwake");
		gpio_direction_output(plat->gpio_btwake,0);
	}
	if (plat->gpio_oldbtwake!=-1)
	{
		rc = gpio_request(plat->gpio_oldbtwake, "lbee9qmb_oldbtwake");
		gpio_direction_output(plat->gpio_oldbtwake,0);
	}

	rfkill = rfkill_alloc("lbee9qmb-rfkill", &pdev->dev,
			RFKILL_TYPE_BLUETOOTH, &lbee9qmb_rfkill_ops, pdev);
	if (!rfkill) {
		rc = -ENOMEM;
		goto fail_gpio;
	}
	platform_set_drvdata(pdev, rfkill);
	gpio_direction_output(plat->gpio_reset, 0);
	
	rc = rfkill_register(rfkill);
	if (rc < 0)
		goto fail_alloc;

	return 0;

fail_alloc:
	rfkill_destroy(rfkill);
fail_gpio:
	gpio_free(plat->gpio_reset);
	if (plat->gpio_pwr!=-1)
		gpio_free(plat->gpio_pwr);
	if (plat->gpio_oldrst!=-1)
		gpio_free(plat->gpio_oldrst);
	if (plat->gpio_btwake!=-1)
		gpio_free(plat->gpio_btwake);
	if (plat->gpio_oldbtwake!=-1)
		gpio_free(plat->gpio_oldbtwake);
	return rc;
		
}
Пример #27
0
static int bluedroid_pm_probe(struct platform_device *pdev)
{
    static struct bluedroid_pm_data *bluedroid_pm;
    struct rfkill *rfkill;
    struct resource *res;
    int ret;
    bool enable = false;  /* off */
    bool default_sw_block_state;

    bluedroid_pm = kzalloc(sizeof(*bluedroid_pm), GFP_KERNEL);
    if (!bluedroid_pm)
        return -ENOMEM;

    bluedroid_pm->vdd_3v3 = regulator_get(&pdev->dev, "vdd_bt_3v3");
    if (IS_ERR_OR_NULL(bluedroid_pm->vdd_3v3)) {
        pr_warn("%s: regulator vdd_bt_3v3 not available\n", __func__);
        bluedroid_pm->vdd_3v3 = NULL;
    }
    bluedroid_pm->vdd_1v8 = regulator_get(&pdev->dev, "vddio_bt_1v8");
    if (IS_ERR_OR_NULL(bluedroid_pm->vdd_1v8)) {
        pr_warn("%s: regulator vddio_bt_1v8 not available\n", __func__);
        bluedroid_pm->vdd_1v8 = NULL;
    }

    res = platform_get_resource_byname(pdev, IORESOURCE_IO, "reset_gpio");
    if (res) {
        bluedroid_pm->gpio_reset = res->start;
        ret = gpio_request(bluedroid_pm->gpio_reset, "reset_gpio");
        if (ret) {
            pr_err("%s: Failed to get reset gpio\n", __func__);
            goto free_res;
        }
        gpio_direction_output(bluedroid_pm->gpio_reset, enable);
    } else {
        pr_debug("%s: Reset gpio not registered.\n", __func__);
        bluedroid_pm->gpio_reset = 0;
    }

    res = platform_get_resource_byname(pdev, IORESOURCE_IO,
                                       "shutdown_gpio");
    if (res) {
        bluedroid_pm->gpio_shutdown = res->start;
        ret = gpio_request(bluedroid_pm->gpio_shutdown,
                           "shutdown_gpio");
        if (ret) {
            pr_err("%s: Failed to get shutdown gpio\n", __func__);
            goto free_res;
        }
        gpio_direction_output(bluedroid_pm->gpio_shutdown, enable);
    } else {
        pr_debug("%s: shutdown gpio not registered\n", __func__);
        bluedroid_pm->gpio_shutdown = 0;
    }

    /*
     * make sure at-least one of the GPIO or regulators avaiable to
     * register with rfkill is defined
     */
    if (bluedroid_pm->gpio_reset || bluedroid_pm->gpio_shutdown ||
            bluedroid_pm->vdd_1v8 || bluedroid_pm->vdd_3v3) {
        rfkill = rfkill_alloc(pdev->name, &pdev->dev,
                              RFKILL_TYPE_BLUETOOTH, &bluedroid_pm_rfkill_ops,
                              bluedroid_pm);

        if (unlikely(!rfkill))
            goto free_res;

        default_sw_block_state = !enable;
        rfkill_set_states(rfkill, default_sw_block_state, false);

        ret = rfkill_register(rfkill);

        if (unlikely(ret)) {
            rfkill_destroy(rfkill);
            kfree(rfkill);
            goto free_res;
        }
        bluedroid_pm->rfkill = rfkill;
    }

    res = platform_get_resource_byname(pdev, IORESOURCE_IO,
                                       "gpio_host_wake");
    if (res) {
        bluedroid_pm->host_wake = res->start;
        ret = gpio_request(bluedroid_pm->host_wake, "bt_host_wake");
        if (ret) {
            pr_err("%s: Failed to get host_wake gpio\n", __func__);
            goto free_res;
        }
        /* configure host_wake as input */
        gpio_direction_input(bluedroid_pm->host_wake);
    } else {
        pr_debug("%s: gpio_host_wake not registered\n", __func__);
        bluedroid_pm->host_wake = 0;
    }


    res = platform_get_resource_byname(pdev, IORESOURCE_IRQ, "host_wake");
    if (res) {
        pr_err("%s : found host_wake irq\n", __func__);
        bluedroid_pm->host_wake_irq = res->start;
        ret = request_irq(bluedroid_pm->host_wake_irq,
                          bluedroid_pm_hostwake_isr,
                          IRQF_DISABLED | IRQF_TRIGGER_RISING,
                          "bluetooth hostwake", bluedroid_pm);
        if (ret) {
            pr_err("%s: Failed to get host_wake irq\n", __func__);
            goto free_res;
        }
    } else {
        pr_debug("%s: host_wake not registered\n", __func__);
        bluedroid_pm->host_wake_irq = 0;
    }

    res = platform_get_resource_byname(pdev, IORESOURCE_IO,
                                       "gpio_ext_wake");
    if (res) {
        bluedroid_pm->ext_wake = res->start;
        ret = gpio_request(bluedroid_pm->ext_wake, "bt_ext_wake");
        if (ret) {
            pr_err("%s: Failed to get ext_wake gpio\n", __func__);
            goto free_res;
        }
        /* configure ext_wake as output mode*/
        gpio_direction_output(bluedroid_pm->ext_wake, 1);
        if (create_bt_proc_interface(bluedroid_pm)) {
            pr_err("%s: Failed to create proc interface", __func__);
            goto free_res;
        }
    } else {
        pr_debug("%s: gpio_ext_wake not registered\n", __func__);
        bluedroid_pm->ext_wake = 0;
    }

    platform_set_drvdata(pdev, bluedroid_pm);
    pr_debug("RFKILL BT driver successfully registered");
    return 0;

free_res:
    if (bluedroid_pm->vdd_3v3)
        regulator_put(bluedroid_pm->vdd_3v3);
    if (bluedroid_pm->vdd_1v8)
        regulator_put(bluedroid_pm->vdd_1v8);
    if (bluedroid_pm->gpio_shutdown)
        gpio_free(bluedroid_pm->gpio_shutdown);
    if (bluedroid_pm->gpio_reset)
        gpio_free(bluedroid_pm->gpio_reset);
    if (bluedroid_pm->ext_wake)
        gpio_free(bluedroid_pm->ext_wake);
    if (bluedroid_pm->host_wake)
        gpio_free(bluedroid_pm->host_wake);
    if (bluedroid_pm->rfkill) {
        rfkill_unregister(bluedroid_pm->rfkill);
        rfkill_destroy(bluedroid_pm->rfkill);
        kfree(bluedroid_pm->rfkill);
    }
    kfree(bluedroid_pm);
    return -ENODEV;
}
Пример #28
0
static int bt_probe(struct platform_device *pdev)
{
	int ret = 0;
	struct rfkill *bt_rfk;
	struct bt_dev_data *pdata = NULL;
	struct bt_dev_runtime_data *prdata;

#ifdef CONFIG_OF
	//plat = aml_get_driver_data(pdev);
	if (pdev->dev.of_node) {
	    const char *str;
	    
	    printk(KERN_DEBUG "enter bt_probe of_node\n");
	    pdata = kzalloc(sizeof(struct bt_dev_data), GFP_KERNEL);
		ret = of_property_read_string(pdev->dev.of_node,"gpio_reset",&str);
		if(ret){
			printk(KERN_WARNING "not get gpio_reset\n");
			pdata->gpio_reset = 0;
		} else {
		    pdata->gpio_reset = amlogic_gpio_name_map_num(str);
		}
		
        ret = of_property_read_string(pdev->dev.of_node,"gpio_en",&str);
		if(ret){
			printk(KERN_WARNING "not get gpio_en\n");
			pdata->gpio_en = 0;
		} else {
		    pdata->gpio_en = amlogic_gpio_name_map_num(str);
		}
		
		ret = of_property_read_string(pdev->dev.of_node,"gpio_wake",&str);
		if(ret){
			printk(KERN_WARNING "not get gpio_wake\n");
			pdata->gpio_wake = 0;
		} else {
		    pdata->gpio_wake = amlogic_gpio_name_map_num(str);
		}
	}
#else
    pdata = (struct bt_dev_data *)(pdev->dev.platform_data);
#endif
    
    bt_device_init(pdata);
    /* default to bluetooth off */
    //rfkill_switch_all(RFKILL_TYPE_BLUETOOTH, 1);
    bt_device_off(pdata);
    
	bt_rfk = rfkill_alloc("bt-dev", &pdev->dev, RFKILL_TYPE_BLUETOOTH,
			&bt_rfkill_ops, pdata);
						   
	if (!bt_rfk) {
        printk("rfk alloc fail\n");
		ret = -ENOMEM;
		goto err_rfk_alloc;
	}
	/* if not set false, the bt_set_block will call when rfkill class resume */
    rfkill_init_sw_state(bt_rfk, false);      //we want to reset bt when system resume
	ret = rfkill_register(bt_rfk);
	if (ret){
        printk(KERN_ERR "rfkill_register fail\n");
		goto err_rfkill;
    }
    prdata = kmalloc(sizeof(struct bt_dev_runtime_data), GFP_KERNEL);
    if (!prdata) {
        printk(KERN_ERR  "bt_dev_runtime_data alloc fail\n");
		goto err_rfkill;
    }
#ifdef CONFIG_AM_WIFI_SD_MMC
    //setup 32k clock
    wifi_request_32k_clk(1, BT_RFKILL);
    msleep(100);
#endif
    
    prdata->bt_rfk = bt_rfk;
    prdata->pdata = pdata;
	platform_set_drvdata(pdev, prdata);
#ifdef CONFIG_HAS_EARLYSUSPEND                                                                                        
        bt_early_suspend.level = EARLY_SUSPEND_LEVEL_DISABLE_FB;
        bt_early_suspend.suspend = bt_earlysuspend;
        bt_early_suspend.resume = bt_lateresume;
        bt_early_suspend.param = pdev;
        register_early_suspend(&bt_early_suspend);
#endif

	bt_device_on(pdata);

	return 0;	
	
err_rfkill:
	rfkill_destroy(bt_rfk);
err_rfk_alloc:
    bt_device_deinit(pdata);
	return ret;
	
}
static int htc_rfkill_probe(struct platform_device *pdev)
{
    int rc = 0;
    bool default_state = true;
    struct pinctrl_state *set_state;

    printk(KERN_INFO "[BT]== rfkill_probe ==\n");

    bt_export_bd_address();
    fm_ant_node_init();


    if (pdev->dev.of_node) {
        gpio_bt_reg_on = of_get_named_gpio(pdev->dev.of_node,
                                           "brcm,bt-regon-gpio", 0);
        if (gpio_bt_reg_on < 0) {
            printk("[BT]bt-regon-gpio not provided in device tree !!!");

        } else {
            printk("[BT]bt-regon-gpio: %d", gpio_bt_reg_on);
        }
    }


    bt_pinctrl = devm_pinctrl_get(&pdev->dev);
    if (IS_ERR(bt_pinctrl)) {
        if (PTR_ERR(bt_pinctrl) == -EPROBE_DEFER) {
            printk("[BT] bt_pinctrl EPROBE_DEFER !!");
            return -EPROBE_DEFER;
        }
    }

    if (bt_pinctrl) {
        printk("[BT] Init GPIO pins\n");
        set_state = pinctrl_lookup_state(bt_pinctrl, "bt_wake_host_gpio_on");
        if (IS_ERR(set_state)) {
            printk("[BT] cannot get BT pinctrl state bt_wake_host_gpio_on\n");

        } else
            bt_wake_host_set_state_on = set_state;

        set_state = pinctrl_lookup_state(bt_pinctrl, "bt_wake_host_gpio_off");
        if (IS_ERR(set_state)) {
            printk("[BT] cannot get BT pinctrl state bt_wake_host_gpio_off\n");

        } else
            bt_wake_host_set_state_off = set_state;

    }





    bluetooth_set_power(NULL, default_state);

    bt_rfk = rfkill_alloc(bt_name, &pdev->dev, RFKILL_TYPE_BLUETOOTH,
                          &htc_rfkill_ops, NULL);
    if (!bt_rfk) {
        rc = -ENOMEM;
        goto err_rfkill_alloc;
    }

    rfkill_set_states(bt_rfk, default_state, false);



    rc = rfkill_register(bt_rfk);
    if (rc)
        goto err_rfkill_reg;

    return 0;

err_rfkill_reg:
    rfkill_destroy(bt_rfk);
err_rfkill_alloc:
    return rc;
}
Пример #30
0
static int rfkill_init(struct platform_device *sdev)
{
	/* add rfkill */
	int retval;

	/* keep the hardware wireless state */
	get_wireless_state_ec_standard();

	rfk_bluetooth = rfkill_alloc("msi-bluetooth", &sdev->dev,
				RFKILL_TYPE_BLUETOOTH,
				&rfkill_bluetooth_ops, NULL);
	if (!rfk_bluetooth) {
		retval = -ENOMEM;
		goto err_bluetooth;
	}
	retval = rfkill_register(rfk_bluetooth);
	if (retval)
		goto err_bluetooth;

	rfk_wlan = rfkill_alloc("msi-wlan", &sdev->dev, RFKILL_TYPE_WLAN,
				&rfkill_wlan_ops, NULL);
	if (!rfk_wlan) {
		retval = -ENOMEM;
		goto err_wlan;
	}
	retval = rfkill_register(rfk_wlan);
	if (retval)
		goto err_wlan;

	if (threeg_exists) {
		rfk_threeg = rfkill_alloc("msi-threeg", &sdev->dev,
				RFKILL_TYPE_WWAN, &rfkill_threeg_ops, NULL);
		if (!rfk_threeg) {
			retval = -ENOMEM;
			goto err_threeg;
		}
		retval = rfkill_register(rfk_threeg);
		if (retval)
			goto err_threeg;
	}

	/* schedule to run rfkill state initial */
	if (quirks->ec_delay) {
		schedule_delayed_work(&msi_rfkill_init,
			round_jiffies_relative(1 * HZ));
	} else
		schedule_work(&msi_rfkill_work);

	return 0;

err_threeg:
	rfkill_destroy(rfk_threeg);
	if (rfk_wlan)
		rfkill_unregister(rfk_wlan);
err_wlan:
	rfkill_destroy(rfk_wlan);
	if (rfk_bluetooth)
		rfkill_unregister(rfk_bluetooth);
err_bluetooth:
	rfkill_destroy(rfk_bluetooth);

	return retval;
}