linux-input.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH 4/4] Detect the WiFi/Bluetooth/3G devices available
@ 2010-10-18 15:07 Lee, Chun-Yi
  2010-10-18 15:55 ` Dmitry Torokhov
  0 siblings, 1 reply; 9+ messages in thread
From: Lee, Chun-Yi @ 2010-10-18 15:07 UTC (permalink / raw)
  To: platform-driver-x86
  Cc: mjg59, carlos, linux-input, dmitry.torokhov, tiwai, trenn, jbenc,
	corentin.chary, GregKH, Lee, Chun-Yi

Check the Acer OEM-specific Type AA to detect the WiFi/Bluetooth/3G
devices available or not, and set the devices capability flag.

Signed-off-by: Lee, Chun-Yi <jlee@novell.com>
---
 drivers/platform/x86/acer-wmi.c |   49 ++++++++++++++++++++++++++++++++------
 1 files changed, 41 insertions(+), 8 deletions(-)

diff --git a/drivers/platform/x86/acer-wmi.c b/drivers/platform/x86/acer-wmi.c
index 7a17ebe..24f31b4 100644
--- a/drivers/platform/x86/acer-wmi.c
+++ b/drivers/platform/x86/acer-wmi.c
@@ -39,6 +39,7 @@
 #include <linux/slab.h>
 #include <linux/input.h>
 #include <linux/input/sparse-keymap.h>
+#include <linux/dmi.h>
 
 #include <acpi/acpi_drivers.h>
 
@@ -138,7 +139,9 @@ struct lm_return_value {
 /*
  * GUID3 Get Device Status device flags
  */
-#define ACER_WMID3_GDS_THREEG		(1<<6)	/* 3G */
+#define ACER_WMID3_GDS_WIRELESS           (1<<0)  /* WiFi */
+#define ACER_WMID3_GDS_THREEG             (1<<6)  /* 3G */
+#define ACER_WMID3_GDS_BLUETOOTH          (1<<11) /* BT */
 
 struct wmid3_gds_input_param {	/* Get Device Status input parameter */
 	u8 function_num;	/* Function Number */
@@ -153,6 +156,15 @@ struct wmid3_gds_return_value {	/* Get Device Status return value*/
 	u32 reserved;
 } __attribute__((packed));
 
+#define ACER_DMI_DEV_TYPE_AA		170
+
+struct hotkey_function_type_aa {
+	u8 type;
+	u8 length;
+	u16 handle;
+	u16 commun_func_bitmap;
+} __attribute__((packed));
+
 /*
  * Interface capability flags
  */
@@ -184,6 +196,7 @@ static int brightness = -1;
 static int threeg = -1;
 static int force_series;
 static bool launch_manager;
+static struct hotkey_function_type_aa *type_aa;
 
 module_param(mailled, int, 0444);
 module_param(brightness, int, 0444);
@@ -824,6 +837,24 @@ static acpi_status WMID_set_u32(u32 value, u32 cap, struct wmi_interface *iface)
 	return WMI_execute_u32(method_id, (u32)value, NULL);
 }
 
+static void type_aa_dmi_decode(const struct dmi_header *header, void *dummy)
+{
+	/* We are looking for OEM-specific Type Aah */
+	if (header->type != ACER_DMI_DEV_TYPE_AA)
+		return;
+
+	type_aa = (struct hotkey_function_type_aa *) header;
+
+	printk(ACER_INFO "Function biti map for Communication Button: 0x%x\n",
+		type_aa->commun_func_bitmap);
+	if (!!(type_aa->commun_func_bitmap & ACER_WMID3_GDS_WIRELESS))
+		interface->capability |= ACER_CAP_WIRELESS;
+	if (!!(type_aa->commun_func_bitmap & ACER_WMID3_GDS_THREEG))
+		interface->capability |= ACER_CAP_THREEG;
+	if (!!(type_aa->commun_func_bitmap & ACER_WMID3_GDS_BLUETOOTH))
+		interface->capability |= ACER_CAP_BLUETOOTH;
+}
+
 static acpi_status WMID_set_capabilities(void)
 {
 	struct acpi_buffer out = {ACPI_ALLOCATE_BUFFER, NULL};
@@ -844,16 +875,17 @@ static acpi_status WMID_set_capabilities(void)
 		return AE_ERROR;
 	}
 
-	/* Not sure on the meaning of the relevant bits yet to detect these */
-	interface->capability |= ACER_CAP_WIRELESS;
-	interface->capability |= ACER_CAP_THREEG;
+	dmi_walk(type_aa_dmi_decode, NULL);
+	if (!type_aa) {
+		interface->capability |= ACER_CAP_WIRELESS;
+		interface->capability |= ACER_CAP_THREEG;
+		if (devices & 0x10)
+			interface->capability |= ACER_CAP_BLUETOOTH;
+	}
 
 	/* WMID always provides brightness methods */
 	interface->capability |= ACER_CAP_BRIGHTNESS;
 
-	if (devices & 0x10)
-		interface->capability |= ACER_CAP_BLUETOOTH;
-
 	if (!(devices & 0x20))
 		max_brightness = 0x9;
 
@@ -932,7 +964,8 @@ static void __init acer_commandline_init(void)
 	 * capability isn't available on the given interface
 	 */
 	set_u32(mailled, ACER_CAP_MAILLED);
-	set_u32(threeg, ACER_CAP_THREEG);
+	if (!type_aa)
+		set_u32(threeg, ACER_CAP_THREEG);
 	set_u32(brightness, ACER_CAP_BRIGHTNESS);
 }
 
-- 
1.6.0.2

^ permalink raw reply related	[flat|nested] 9+ messages in thread
* Re: [PATCH 4/4] Detect the WiFi/Bluetooth/3G devices available
@ 2010-10-20  4:12 Joey Lee
  0 siblings, 0 replies; 9+ messages in thread
From: Joey Lee @ 2010-10-20  4:12 UTC (permalink / raw)
  To: dmitry.torokhov
  Cc: corentin.chary, Greg Kroah-Hartman, Takashi Iwai,
	Thomas Renninger, mjg59, carlos, jbenc, linux-input,
	platform-driver-x86

Hi Dmitry, 

Thank's for your review.

於 一,2010-10-18 於 08:55 -0700,Dmitry Torokhov 提到:
> Hi,
> 
> On Mon, Oct 18, 2010 at 11:07:43PM +0800, Lee, Chun-Yi wrote:
> > +static void type_aa_dmi_decode(const struct dmi_header *header, void *dummy)
> > +{
> > +	/* We are looking for OEM-specific Type Aah */
> > +	if (header->type != ACER_DMI_DEV_TYPE_AA)
> > +		return;
> > +
> > +	type_aa = (struct hotkey_function_type_aa *) header;
> > +
> > +	printk(ACER_INFO "Function biti map for Communication Button: 0x%x\n",
> > +		type_aa->commun_func_bitmap);
> > +	if (!!(type_aa->commun_func_bitmap & ACER_WMID3_GDS_WIRELESS))
> > +		interface->capability |= ACER_CAP_WIRELESS;
> > +	if (!!(type_aa->commun_func_bitmap & ACER_WMID3_GDS_THREEG))
> > +		interface->capability |= ACER_CAP_THREEG;
> > +	if (!!(type_aa->commun_func_bitmap & ACER_WMID3_GDS_BLUETOOTH))
> > +		interface->capability |= ACER_CAP_BLUETOOTH;
> 
> The "!!" is completely redundant here.
> 

Sorry my fail, removed.

> > +}
> > +
> >  static acpi_status WMID_set_capabilities(void)
> >  {
> >  	struct acpi_buffer out = {ACPI_ALLOCATE_BUFFER, NULL};
> > @@ -844,16 +875,17 @@ static acpi_status WMID_set_capabilities(void)
> >  		return AE_ERROR;
> >  	}
> >  
> > -	/* Not sure on the meaning of the relevant bits yet to detect these */
> > -	interface->capability |= ACER_CAP_WIRELESS;
> > -	interface->capability |= ACER_CAP_THREEG;
> > +	dmi_walk(type_aa_dmi_decode, NULL);
> > +	if (!type_aa) {
> > +		interface->capability |= ACER_CAP_WIRELESS;
> > +		interface->capability |= ACER_CAP_THREEG;
> > +		if (devices & 0x10)
> > +			interface->capability |= ACER_CAP_BLUETOOTH;
> > +	}
> 
> Since you are storing "type_aa" anyways it probably would be better to
> set all capabilities here, in one place...
> 

Follow your suggestion to modified the patch like following:


>From ca67b42b36dea9b5e8d3ac8560f29622447ea470 Mon Sep 17 00:00:00 2001
From: Lee, Chun-Yi <jlee@novell.com>
Date: Wed, 20 Oct 2010 10:50:46 +0100
Subject: [PATCH 4/4] Detect the WiFi/Bluetooth/3G devices available

Check the Acer OEM-specific Type AA to detect the WiFi/Bluetooth/3G
devices available or not, and set the devices capability flag.

Signed-off-by: Lee, Chun-Yi <jlee@novell.com>
---
 drivers/platform/x86/acer-wmi.c |   50
++++++++++++++++++++++++++++++++------
 1 files changed, 42 insertions(+), 8 deletions(-)

diff --git a/drivers/platform/x86/acer-wmi.c
b/drivers/platform/x86/acer-wmi.c
index 7a17ebe..a5ac42c 100644
--- a/drivers/platform/x86/acer-wmi.c
+++ b/drivers/platform/x86/acer-wmi.c
@@ -39,6 +39,7 @@
 #include <linux/slab.h>
 #include <linux/input.h>
 #include <linux/input/sparse-keymap.h>
+#include <linux/dmi.h>
 
 #include <acpi/acpi_drivers.h>
 
@@ -138,7 +139,9 @@ struct lm_return_value {
 /*
  * GUID3 Get Device Status device flags
  */
-#define ACER_WMID3_GDS_THREEG		(1<<6)	/* 3G */
+#define ACER_WMID3_GDS_WIRELESS           (1<<0)  /* WiFi */
+#define ACER_WMID3_GDS_THREEG             (1<<6)  /* 3G */
+#define ACER_WMID3_GDS_BLUETOOTH          (1<<11) /* BT */
 
 struct wmid3_gds_input_param {	/* Get Device Status input parameter */
 	u8 function_num;	/* Function Number */
@@ -153,6 +156,15 @@ struct wmid3_gds_return_value {	/* Get Device
Status return value*/
 	u32 reserved;
 } __attribute__((packed));
 
+#define ACER_DMI_DEV_TYPE_AA		170
+
+struct hotkey_function_type_aa {
+	u8 type;
+	u8 length;
+	u16 handle;
+	u16 commun_func_bitmap;
+} __attribute__((packed));
+
 /*
  * Interface capability flags
  */
@@ -184,6 +196,7 @@ static int brightness = -1;
 static int threeg = -1;
 static int force_series;
 static bool launch_manager;
+static struct hotkey_function_type_aa *type_aa;
 
 module_param(mailled, int, 0444);
 module_param(brightness, int, 0444);
@@ -824,6 +837,18 @@ static acpi_status WMID_set_u32(u32 value, u32 cap,
struct wmi_interface *iface)
 	return WMI_execute_u32(method_id, (u32)value, NULL);
 }
 
+static void type_aa_dmi_decode(const struct dmi_header *header, void
*dummy)
+{
+	/* We are looking for OEM-specific Type Aah */
+	if (header->type != ACER_DMI_DEV_TYPE_AA)
+		return;
+
+	type_aa = (struct hotkey_function_type_aa *) header;
+
+	printk(ACER_INFO "Function biti map for Communication Button: 0x%x\n",
+		type_aa->commun_func_bitmap);
+}
+
 static acpi_status WMID_set_capabilities(void)
 {
 	struct acpi_buffer out = {ACPI_ALLOCATE_BUFFER, NULL};
@@ -844,16 +869,24 @@ static acpi_status WMID_set_capabilities(void)
 		return AE_ERROR;
 	}
 
-	/* Not sure on the meaning of the relevant bits yet to detect these */
-	interface->capability |= ACER_CAP_WIRELESS;
-	interface->capability |= ACER_CAP_THREEG;
+	dmi_walk(type_aa_dmi_decode, NULL);
+	if (type_aa) {
+		if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_WIRELESS)
+			interface->capability |= ACER_CAP_WIRELESS;
+		if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_THREEG)
+			interface->capability |= ACER_CAP_THREEG;
+		if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_BLUETOOTH)
+			interface->capability |= ACER_CAP_BLUETOOTH;
+	} else {
+		interface->capability |= ACER_CAP_WIRELESS;
+		interface->capability |= ACER_CAP_THREEG;
+		if (devices & 0x10)
+			interface->capability |= ACER_CAP_BLUETOOTH;
+	}
 
 	/* WMID always provides brightness methods */
 	interface->capability |= ACER_CAP_BRIGHTNESS;
 
-	if (devices & 0x10)
-		interface->capability |= ACER_CAP_BLUETOOTH;
-
 	if (!(devices & 0x20))
 		max_brightness = 0x9;
 
@@ -932,7 +965,8 @@ static void __init acer_commandline_init(void)
 	 * capability isn't available on the given interface
 	 */
 	set_u32(mailled, ACER_CAP_MAILLED);
-	set_u32(threeg, ACER_CAP_THREEG);
+	if (!type_aa)
+		set_u32(threeg, ACER_CAP_THREEG);
 	set_u32(brightness, ACER_CAP_BRIGHTNESS);
 }
 
-- 
1.6.0.2



--
To unsubscribe from this list: send the line "unsubscribe linux-input" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply related	[flat|nested] 9+ messages in thread
* [PATCH 1/4] Add acer wmi hotkey events support
@ 2010-10-30 16:36 Lee, Chun-Yi
  2010-10-30 16:36 ` [PATCH 2/4] Enabled Acer Launch Manager mode Lee, Chun-Yi
  0 siblings, 1 reply; 9+ messages in thread
From: Lee, Chun-Yi @ 2010-10-30 16:36 UTC (permalink / raw)
  To: platform-driver-x86
  Cc: linux-input, carlos, corentin.chary, dmitry.torokhov, tiwai,
	trenn, mjg59, jbenc, Lee, Chun-Yi

Add acer wmi hotkey event support. Install a wmi notify handler to
transfer wmi event key to key code, then send out keycode through acer
wmi input device to userland.

Signed-off-by: Lee, Chun-Yi <jlee@novell.com>
---
 drivers/platform/x86/Kconfig    |    2 +
 drivers/platform/x86/acer-wmi.c |  139 +++++++++++++++++++++++++++++++++++++++
 2 files changed, 141 insertions(+), 0 deletions(-)

diff --git a/drivers/platform/x86/Kconfig b/drivers/platform/x86/Kconfig
index cff7cc2..c242fdd 100644
--- a/drivers/platform/x86/Kconfig
+++ b/drivers/platform/x86/Kconfig
@@ -23,7 +23,9 @@ config ACER_WMI
 	depends on BACKLIGHT_CLASS_DEVICE
 	depends on SERIO_I8042
 	depends on RFKILL || RFKILL = n
+	depends on INPUT
 	select ACPI_WMI
+	select INPUT_SPARSEKMAP
 	---help---
 	  This is a driver for newer Acer (and Wistron) laptops. It adds
 	  wireless radio and bluetooth control, and on some laptops,
diff --git a/drivers/platform/x86/acer-wmi.c b/drivers/platform/x86/acer-wmi.c
index 2badee2..930df56 100644
--- a/drivers/platform/x86/acer-wmi.c
+++ b/drivers/platform/x86/acer-wmi.c
@@ -37,6 +37,8 @@
 #include <linux/workqueue.h>
 #include <linux/debugfs.h>
 #include <linux/slab.h>
+#include <linux/input.h>
+#include <linux/input/sparse-keymap.h>
 
 #include <acpi/acpi_drivers.h>
 
@@ -48,6 +50,7 @@ MODULE_LICENSE("GPL");
 #define ACER_ERR KERN_ERR ACER_LOGPREFIX
 #define ACER_NOTICE KERN_NOTICE ACER_LOGPREFIX
 #define ACER_INFO KERN_INFO ACER_LOGPREFIX
+#define ACER_WARNING KERN_WARNING ACER_LOGPREFIX
 
 /*
  * Magic Number
@@ -83,8 +86,39 @@ MODULE_LICENSE("GPL");
 #define WMID_GUID1		"6AF4F258-B401-42fd-BE91-3D4AC2D7C0D3"
 #define WMID_GUID2		"95764E09-FB56-4e83-B31A-37761F60994A"
 
+/*
+ * Acer ACPI event GUIDs
+ */
+#define ACERWMID_EVENT_GUID "676AA15E-6A47-4D9F-A2CC-1E6D18D14026"
+
 MODULE_ALIAS("wmi:67C3371D-95A3-4C37-BB61-DD47B491DAAB");
 MODULE_ALIAS("wmi:6AF4F258-B401-42fd-BE91-3D4AC2D7C0D3");
+MODULE_ALIAS("wmi:676AA15E-6A47-4D9F-A2CC-1E6D18D14026");
+
+enum acer_wmi_event_ids {
+	WMID_HOTKEY_EVENT = 0x1,
+};
+
+static const struct key_entry acer_wmi_keymap[] = {
+	{KE_KEY, 0x01, {KEY_WLAN} },     /* WiFi */
+	{KE_KEY, 0x12, {KEY_BLUETOOTH} },	/* BT */
+	{KE_KEY, 0x21, {KEY_PROG1} },    /* Backup */
+	{KE_KEY, 0x22, {KEY_PROG2} },    /* Aracade */
+	{KE_KEY, 0x23, {KEY_PROG3} },    /* P_Key */
+	{KE_KEY, 0x24, {KEY_PROG4} },    /* Social networking_Key */
+	{KE_KEY, 0x64, {KEY_SWITCHVIDEOMODE} },	/* Display Switch */
+	{KE_KEY, 0x82, {KEY_F22} },      /* Touch Pad On/Off */
+	{KE_END, 0}
+};
+
+static struct input_dev *acer_wmi_input_dev;
+
+struct event_return_value {
+	u8 function;
+	u8 key_num;
+	u16 device_state;
+	u32 reserved;
+} __attribute__((packed));
 
 /*
  * Interface capability flags
@@ -1085,6 +1119,99 @@ static ssize_t show_interface(struct device *dev, struct device_attribute *attr,
 
 static DEVICE_ATTR(interface, S_IRUGO, show_interface, NULL);
 
+static void acer_wmi_notify(u32 value, void *context)
+{
+	struct acpi_buffer response = { ACPI_ALLOCATE_BUFFER, NULL };
+	union acpi_object *obj;
+	struct event_return_value return_value;
+	acpi_status status;
+
+	status = wmi_get_event_data(value, &response);
+	if (status != AE_OK) {
+		printk(ACER_WARNING "bad event status 0x%x\n", status);
+		return;
+	}
+
+	obj = (union acpi_object *)response.pointer;
+
+	if (!obj)
+		return;
+	if (obj->type != ACPI_TYPE_BUFFER) {
+		printk(ACER_WARNING "Unknown response received %d\n",
+			obj->type);
+		kfree(obj);
+		return;
+	}
+	if (obj->buffer.length != 8) {
+		printk(ACER_WARNING "Unknown buffer length %d\n",
+			obj->buffer.length);
+		kfree(obj);
+		return;
+	}
+
+	return_value = *((struct event_return_value *)obj->buffer.pointer);
+	kfree(obj);
+
+	switch (return_value.function) {
+	case WMID_HOTKEY_EVENT:
+		if (!sparse_keymap_report_event(acer_wmi_input_dev,
+				return_value.key_num, 1, true))
+			printk(ACER_WARNING "Unknown key number - 0x%x\n",
+				return_value.key_num);
+		break;
+	default:
+		printk(ACER_WARNING "Unknown function number - %d - %d\n",
+			return_value.function, return_value.key_num);
+		break;
+	}
+}
+
+static int __init acer_wmi_input_setup(void)
+{
+	acpi_status status;
+	int err;
+
+	acer_wmi_input_dev = input_allocate_device();
+	if (!acer_wmi_input_dev)
+		return -ENOMEM;
+
+	acer_wmi_input_dev->name = "Acer WMI hotkeys";
+	acer_wmi_input_dev->phys = "wmi/input0";
+	acer_wmi_input_dev->id.bustype = BUS_HOST;
+
+	err = sparse_keymap_setup(acer_wmi_input_dev, acer_wmi_keymap, NULL);
+	if (err)
+		goto err_free_dev;
+
+	status = wmi_install_notify_handler(ACERWMID_EVENT_GUID,
+						acer_wmi_notify, NULL);
+	if (ACPI_FAILURE(status)) {
+		err = -EIO;
+		goto err_free_keymap;
+	}
+
+	err = input_register_device(acer_wmi_input_dev);
+	if (err)
+		goto err_uninstall_notifier;
+
+	return 0;
+
+err_uninstall_notifier:
+	wmi_remove_notify_handler(ACERWMID_EVENT_GUID);
+err_free_keymap:
+	sparse_keymap_free(acer_wmi_input_dev);
+err_free_dev:
+	input_free_device(acer_wmi_input_dev);
+	return err;
+}
+
+static void acer_wmi_input_destroy(void)
+{
+	wmi_remove_notify_handler(ACERWMID_EVENT_GUID);
+	sparse_keymap_free(acer_wmi_input_dev);
+	input_unregister_device(acer_wmi_input_dev);
+}
+
 /*
  * debugfs functions
  */
@@ -1327,6 +1454,12 @@ static int __init acer_wmi_init(void)
 		       "generic video driver\n");
 	}
 
+	if (wmi_has_guid(ACERWMID_EVENT_GUID)) {
+		err = acer_wmi_input_setup();
+		if (err)
+			return err;
+	}
+
 	err = platform_driver_register(&acer_platform_driver);
 	if (err) {
 		printk(ACER_ERR "Unable to register platform driver.\n");
@@ -1368,11 +1501,17 @@ error_device_add:
 error_device_alloc:
 	platform_driver_unregister(&acer_platform_driver);
 error_platform_register:
+	if (wmi_has_guid(ACERWMID_EVENT_GUID))
+		acer_wmi_input_destroy();
+
 	return err;
 }
 
 static void __exit acer_wmi_exit(void)
 {
+	if (wmi_has_guid(ACERWMID_EVENT_GUID))
+		acer_wmi_input_destroy();
+
 	remove_sysfs(acer_platform_device);
 	remove_debugfs();
 	platform_device_unregister(acer_platform_device);
-- 
1.6.0.2

^ permalink raw reply related	[flat|nested] 9+ messages in thread
* Re: [PATCH 4/4] Detect the WiFi/Bluetooth/3G devices available
@ 2010-10-30 16:44 Joey Lee
  0 siblings, 0 replies; 9+ messages in thread
From: Joey Lee @ 2010-10-30 16:44 UTC (permalink / raw)
  To: platform-driver-x86
  Cc: corentin.chary, dmitry.torokhov, Takashi Iwai, Thomas Renninger,
	mjg59, carlos, jbenc, trenn, linux-input

Add CC. Thomas

於 日,2010-10-31 於 00:36 +0800,Lee, Chun-Yi 提到:
> Check the Acer OEM-specific Type AA to detect the WiFi/Bluetooth/3G
> devices available or not, and set the devices capability flag.
> 
> Signed-off-by: Lee, Chun-Yi <jlee@novell.com>
> ---
>  drivers/platform/x86/acer-wmi.c |   50 ++++++++++++++++++++++++++++++++------
>  1 files changed, 42 insertions(+), 8 deletions(-)
> 
> diff --git a/drivers/platform/x86/acer-wmi.c b/drivers/platform/x86/acer-wmi.c
> index 9656464..0247a70 100644
> --- a/drivers/platform/x86/acer-wmi.c
> +++ b/drivers/platform/x86/acer-wmi.c
> @@ -39,6 +39,7 @@
>  #include <linux/slab.h>
>  #include <linux/input.h>
>  #include <linux/input/sparse-keymap.h>
> +#include <linux/dmi.h>
>  
>  #include <acpi/acpi_drivers.h>
>  
> @@ -138,7 +139,9 @@ struct lm_return_value {
>  /*
>   * GUID3 Get Device Status device flags
>   */
> -#define ACER_WMID3_GDS_THREEG		(1<<6)	/* 3G */
> +#define ACER_WMID3_GDS_WIRELESS           (1<<0)  /* WiFi */
> +#define ACER_WMID3_GDS_THREEG             (1<<6)  /* 3G */
> +#define ACER_WMID3_GDS_BLUETOOTH          (1<<11) /* BT */
>  
>  struct wmid3_gds_input_param {	/* Get Device Status input parameter */
>  	u8 function_num;	/* Function Number */
> @@ -153,6 +156,15 @@ struct wmid3_gds_return_value {	/* Get Device Status return value*/
>  	u32 reserved;
>  } __attribute__((packed));
>  
> +#define ACER_DMI_DEV_TYPE_AA		170
> +
> +struct hotkey_function_type_aa {
> +	u8 type;
> +	u8 length;
> +	u16 handle;
> +	u16 commun_func_bitmap;
> +} __attribute__((packed));
> +
>  /*
>   * Interface capability flags
>   */
> @@ -184,6 +196,7 @@ static int brightness = -1;
>  static int threeg = -1;
>  static int force_series;
>  static bool ec_raw_mode;
> +static struct hotkey_function_type_aa *type_aa;
>  
>  module_param(mailled, int, 0444);
>  module_param(brightness, int, 0444);
> @@ -824,6 +837,18 @@ static acpi_status WMID_set_u32(u32 value, u32 cap, struct wmi_interface *iface)
>  	return WMI_execute_u32(method_id, (u32)value, NULL);
>  }
>  
> +static void type_aa_dmi_decode(const struct dmi_header *header, void *dummy)
> +{
> +	/* We are looking for OEM-specific Type Aah */
> +	if (header->type != ACER_DMI_DEV_TYPE_AA)
> +		return;
> +
> +	type_aa = (struct hotkey_function_type_aa *) header;
> +
> +	printk(ACER_INFO "Function biti map for Communication Button: 0x%x\n",
> +		type_aa->commun_func_bitmap);
> +}
> +
>  static acpi_status WMID_set_capabilities(void)
>  {
>  	struct acpi_buffer out = {ACPI_ALLOCATE_BUFFER, NULL};
> @@ -844,16 +869,24 @@ static acpi_status WMID_set_capabilities(void)
>  		return AE_ERROR;
>  	}
>  
> -	/* Not sure on the meaning of the relevant bits yet to detect these */
> -	interface->capability |= ACER_CAP_WIRELESS;
> -	interface->capability |= ACER_CAP_THREEG;
> +	dmi_walk(type_aa_dmi_decode, NULL);
> +	if (type_aa) {
> +		if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_WIRELESS)
> +			interface->capability |= ACER_CAP_WIRELESS;
> +		if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_THREEG)
> +			interface->capability |= ACER_CAP_THREEG;
> +		if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_BLUETOOTH)
> +			interface->capability |= ACER_CAP_BLUETOOTH;
> +	} else {
> +		interface->capability |= ACER_CAP_WIRELESS;
> +		interface->capability |= ACER_CAP_THREEG;
> +		if (devices & 0x10)
> +			interface->capability |= ACER_CAP_BLUETOOTH;
> +	}
>  
>  	/* WMID always provides brightness methods */
>  	interface->capability |= ACER_CAP_BRIGHTNESS;
>  
> -	if (devices & 0x10)
> -		interface->capability |= ACER_CAP_BLUETOOTH;
> -
>  	if (!(devices & 0x20))
>  		max_brightness = 0x9;
>  
> @@ -932,7 +965,8 @@ static void __init acer_commandline_init(void)
>  	 * capability isn't available on the given interface
>  	 */
>  	set_u32(mailled, ACER_CAP_MAILLED);
> -	set_u32(threeg, ACER_CAP_THREEG);
> +	if (!type_aa)
> +		set_u32(threeg, ACER_CAP_THREEG);
>  	set_u32(brightness, ACER_CAP_BRIGHTNESS);
>  }
>  

^ permalink raw reply	[flat|nested] 9+ messages in thread
* Re: [PATCH 4/4] Detect the WiFi/Bluetooth/3G devices available
@ 2010-11-08  4:54 Joey Lee
  0 siblings, 0 replies; 9+ messages in thread
From: Joey Lee @ 2010-11-08  4:54 UTC (permalink / raw)
  To: jdelvare
  Cc: corentin.chary, dmitry.torokhov, Takashi Iwai, Thomas Renninger,
	mjg59, carlos, jbenc, trenn, linux-input, platform-driver-x86

Hi Jean, 

On 日, 2010-10-31 at 00:36 +0800, Lee, Chun-Yi wrote:
>  static acpi_status WMID_set_capabilities(void)
>  {
>  	struct acpi_buffer out = {ACPI_ALLOCATE_BUFFER, NULL};
> @@ -844,16 +869,24 @@ static acpi_status WMID_set_capabilities(void)
>  		return AE_ERROR;
>  	}
>  
> -	/* Not sure on the meaning of the relevant bits yet to detect these */
> -	interface->capability |= ACER_CAP_WIRELESS;
> -	interface->capability |= ACER_CAP_THREEG;
> +	dmi_walk(type_aa_dmi_decode, NULL);
> +	if (type_aa) {
> +		if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_WIRELESS)
> +			interface->capability |= ACER_CAP_WIRELESS;
> +		if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_THREEG)
> +			interface->capability |= ACER_CAP_THREEG;
> +		if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_BLUETOOTH)
> +			interface->capability |= ACER_CAP_BLUETOOTH;
> +	} else {
> +		interface->capability |= ACER_CAP_WIRELESS;
> +		interface->capability |= ACER_CAP_THREEG;
> +		if (devices & 0x10)
> +			interface->capability |= ACER_CAP_BLUETOOTH;
> +	}
>  

Thank's for your review and found out cann't use a global pointer to a
DMI record to keep track of what dmi_walk() found. I modified the patch
like following:


>From c8f99f9856bc79aa8f525595e5ff115f3d6c3c69 Mon Sep 17 00:00:00 2001
From: Lee, Chun-Yi <jlee@novell.com>
Date: Mon, 8 Nov 2010 16:40:55 +0800
Subject: [PATCH 4/4] Detect the WiFi/Bluetooth/3G devices available

Check the Acer OEM-specific Type AA to detect the WiFi/Bluetooth/3G
devices available or not, and set the devices capability flag.

Signed-off-by: Lee, Chun-Yi <jlee@novell.com>
Reviewed-by: Jean Delvare <jdelvare@suse.de>
---
 drivers/platform/x86/acer-wmi.c |   49 +++++++++++++++++++++++++++++++++-----
 1 files changed, 42 insertions(+), 7 deletions(-)

diff --git a/drivers/platform/x86/acer-wmi.c b/drivers/platform/x86/acer-wmi.c
index 6ac4656..dc23140 100644
--- a/drivers/platform/x86/acer-wmi.c
+++ b/drivers/platform/x86/acer-wmi.c
@@ -39,6 +39,7 @@
 #include <linux/slab.h>
 #include <linux/input.h>
 #include <linux/input/sparse-keymap.h>
+#include <linux/dmi.h>
 
 #include <acpi/acpi_drivers.h>
 
@@ -138,7 +139,9 @@ struct lm_return_value {
 /*
  * GUID3 Get Device Status device flags
  */
+#define ACER_WMID3_GDS_WIRELESS		(1<<0)	/* WiFi */
 #define ACER_WMID3_GDS_THREEG		(1<<6)	/* 3G */
+#define ACER_WMID3_GDS_BLUETOOTH	(1<<11)	/* BT */
 
 struct wmid3_gds_input_param {	/* Get Device Status input parameter */
 	u8 function_num;	/* Function Number */
@@ -153,6 +156,13 @@ struct wmid3_gds_return_value {	/* Get Device Status return value*/
 	u32 reserved;
 } __attribute__((packed));
 
+struct hotkey_function_type_aa {
+	u8 type;
+	u8 length;
+	u16 handle;
+	u16 commun_func_bitmap;
+} __attribute__((packed));
+
 /*
  * Interface capability flags
  */
@@ -184,6 +194,7 @@ static int brightness = -1;
 static int threeg = -1;
 static int force_series;
 static bool ec_raw_mode;
+static bool has_type_aa;
 
 module_param(mailled, int, 0444);
 module_param(brightness, int, 0444);
@@ -824,6 +835,28 @@ static acpi_status WMID_set_u32(u32 value, u32 cap, struct wmi_interface *iface)
 	return WMI_execute_u32(method_id, (u32)value, NULL);
 }
 
+static void type_aa_dmi_decode(const struct dmi_header *header, void *dummy)
+{
+	struct hotkey_function_type_aa *type_aa;
+
+	/* We are looking for OEM-specific Type AAh */
+	if (header->type != 0xAA)
+		return;
+
+	has_type_aa = true;
+	type_aa = (struct hotkey_function_type_aa *) header;
+
+	printk(ACER_INFO "Function bitmap for Communication Button: 0x%x\n",
+		type_aa->commun_func_bitmap);
+
+	if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_WIRELESS)
+		interface->capability |= ACER_CAP_WIRELESS;
+	if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_THREEG)
+		interface->capability |= ACER_CAP_THREEG;
+	if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_BLUETOOTH)
+		interface->capability |= ACER_CAP_BLUETOOTH;
+}
+
 static acpi_status WMID_set_capabilities(void)
 {
 	struct acpi_buffer out = {ACPI_ALLOCATE_BUFFER, NULL};
@@ -844,16 +877,17 @@ static acpi_status WMID_set_capabilities(void)
 		return AE_ERROR;
 	}
 
-	/* Not sure on the meaning of the relevant bits yet to detect these */
-	interface->capability |= ACER_CAP_WIRELESS;
-	interface->capability |= ACER_CAP_THREEG;
+	dmi_walk(type_aa_dmi_decode, NULL);
+	if (!has_type_aa) {
+		interface->capability |= ACER_CAP_WIRELESS;
+		interface->capability |= ACER_CAP_THREEG;
+		if (devices & 0x10)
+			interface->capability |= ACER_CAP_BLUETOOTH;
+	}
 
 	/* WMID always provides brightness methods */
 	interface->capability |= ACER_CAP_BRIGHTNESS;
 
-	if (devices & 0x10)
-		interface->capability |= ACER_CAP_BLUETOOTH;
-
 	if (!(devices & 0x20))
 		max_brightness = 0x9;
 
@@ -932,7 +966,8 @@ static void __init acer_commandline_init(void)
 	 * capability isn't available on the given interface
 	 */
 	set_u32(mailled, ACER_CAP_MAILLED);
-	set_u32(threeg, ACER_CAP_THREEG);
+	if (!has_type_aa)
+		set_u32(threeg, ACER_CAP_THREEG);
 	set_u32(brightness, ACER_CAP_BRIGHTNESS);
 }
 
-- 
1.6.0.2

^ permalink raw reply related	[flat|nested] 9+ messages in thread
* Re: [PATCH 4/4] Detect the WiFi/Bluetooth/3G devices available
@ 2010-11-12  8:36 Joey Lee
  0 siblings, 0 replies; 9+ messages in thread
From: Joey Lee @ 2010-11-12  8:36 UTC (permalink / raw)
  Cc: corentin.chary, dmitry.torokhov, Takashi Iwai, Thomas Renninger,
	mjg59, carlos, jbenc, jdelvare, trenn, linux-input,
	platform-driver-x86

Hi Carlos, 

於 日,2010-11-07 於 21:54 -0700,Joey Lee 提到:
> Hi Jean, 
> 
> On 日, 2010-10-31 at 00:36 +0800, Lee, Chun-Yi wrote:
> >  static acpi_status WMID_set_capabilities(void)
> >  {
> >  	struct acpi_buffer out = {ACPI_ALLOCATE_BUFFER, NULL};
> > @@ -844,16 +869,24 @@ static acpi_status WMID_set_capabilities(void)
> >  		return AE_ERROR;
> >  	}
> >  
> > -	/* Not sure on the meaning of the relevant bits yet to detect these */
> > -	interface->capability |= ACER_CAP_WIRELESS;
> > -	interface->capability |= ACER_CAP_THREEG;
> > +	dmi_walk(type_aa_dmi_decode, NULL);
> > +	if (type_aa) {
> > +		if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_WIRELESS)
> > +			interface->capability |= ACER_CAP_WIRELESS;
> > +		if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_THREEG)
> > +			interface->capability |= ACER_CAP_THREEG;
> > +		if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_BLUETOOTH)
> > +			interface->capability |= ACER_CAP_BLUETOOTH;
> > +	} else {
> > +		interface->capability |= ACER_CAP_WIRELESS;
> > +		interface->capability |= ACER_CAP_THREEG;
> > +		if (devices & 0x10)
> > +			interface->capability |= ACER_CAP_BLUETOOTH;
> > +	}
> >  
> 
> Thank's for your review and found out cann't use a global pointer to a
> DMI record to keep track of what dmi_walk() found. I modified the patch
> like following:
> 
> 
> >From c8f99f9856bc79aa8f525595e5ff115f3d6c3c69 Mon Sep 17 00:00:00 2001
> From: Lee, Chun-Yi <jlee@novell.com>
> Date: Mon, 8 Nov 2010 16:40:55 +0800
> Subject: [PATCH 4/4] Detect the WiFi/Bluetooth/3G devices available
> 
> Check the Acer OEM-specific Type AA to detect the WiFi/Bluetooth/3G
> devices available or not, and set the devices capability flag.
> 
> Signed-off-by: Lee, Chun-Yi <jlee@novell.com>
> Reviewed-by: Jean Delvare <jdelvare@suse.de>
> ---
>  drivers/platform/x86/acer-wmi.c |   49 +++++++++++++++++++++++++++++++++-----
>  1 files changed, 42 insertions(+), 7 deletions(-)
> 
> diff --git a/drivers/platform/x86/acer-wmi.c b/drivers/platform/x86/acer-wmi.c
> index 6ac4656..dc23140 100644
> --- a/drivers/platform/x86/acer-wmi.c
> +++ b/drivers/platform/x86/acer-wmi.c
> @@ -39,6 +39,7 @@
>  #include <linux/slab.h>
>  #include <linux/input.h>
>  #include <linux/input/sparse-keymap.h>
> +#include <linux/dmi.h>
>  
>  #include <acpi/acpi_drivers.h>
>  
> @@ -138,7 +139,9 @@ struct lm_return_value {
>  /*
>   * GUID3 Get Device Status device flags
>   */
> +#define ACER_WMID3_GDS_WIRELESS		(1<<0)	/* WiFi */
>  #define ACER_WMID3_GDS_THREEG		(1<<6)	/* 3G */
> +#define ACER_WMID3_GDS_BLUETOOTH	(1<<11)	/* BT */
>  
>  struct wmid3_gds_input_param {	/* Get Device Status input parameter */
>  	u8 function_num;	/* Function Number */
> @@ -153,6 +156,13 @@ struct wmid3_gds_return_value {	/* Get Device Status return value*/
>  	u32 reserved;
>  } __attribute__((packed));
>  
> +struct hotkey_function_type_aa {
> +	u8 type;
> +	u8 length;
> +	u16 handle;
> +	u16 commun_func_bitmap;
> +} __attribute__((packed));
> +
>  /*
>   * Interface capability flags
>   */
> @@ -184,6 +194,7 @@ static int brightness = -1;
>  static int threeg = -1;
>  static int force_series;
>  static bool ec_raw_mode;
> +static bool has_type_aa;
>  
>  module_param(mailled, int, 0444);
>  module_param(brightness, int, 0444);
> @@ -824,6 +835,28 @@ static acpi_status WMID_set_u32(u32 value, u32 cap, struct wmi_interface *iface)
>  	return WMI_execute_u32(method_id, (u32)value, NULL);
>  }
>  
> +static void type_aa_dmi_decode(const struct dmi_header *header, void *dummy)
> +{
> +	struct hotkey_function_type_aa *type_aa;
> +
> +	/* We are looking for OEM-specific Type AAh */
> +	if (header->type != 0xAA)
> +		return;
> +
> +	has_type_aa = true;
> +	type_aa = (struct hotkey_function_type_aa *) header;
> +
> +	printk(ACER_INFO "Function bitmap for Communication Button: 0x%x\n",
> +		type_aa->commun_func_bitmap);
> +
> +	if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_WIRELESS)
> +		interface->capability |= ACER_CAP_WIRELESS;
> +	if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_THREEG)
> +		interface->capability |= ACER_CAP_THREEG;
> +	if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_BLUETOOTH)
> +		interface->capability |= ACER_CAP_BLUETOOTH;
> +}
> +
>  static acpi_status WMID_set_capabilities(void)
>  {
>  	struct acpi_buffer out = {ACPI_ALLOCATE_BUFFER, NULL};
> @@ -844,16 +877,17 @@ static acpi_status WMID_set_capabilities(void)
>  		return AE_ERROR;
>  	}
>  
> -	/* Not sure on the meaning of the relevant bits yet to detect these */
> -	interface->capability |= ACER_CAP_WIRELESS;
> -	interface->capability |= ACER_CAP_THREEG;
> +	dmi_walk(type_aa_dmi_decode, NULL);
> +	if (!has_type_aa) {
> +		interface->capability |= ACER_CAP_WIRELESS;
> +		interface->capability |= ACER_CAP_THREEG;
> +		if (devices & 0x10)
> +			interface->capability |= ACER_CAP_BLUETOOTH;
> +	}
>  
>  	/* WMID always provides brightness methods */
>  	interface->capability |= ACER_CAP_BRIGHTNESS;
>  
> -	if (devices & 0x10)
> -		interface->capability |= ACER_CAP_BLUETOOTH;
> -
>  	if (!(devices & 0x20))
>  		max_brightness = 0x9;
>  
> @@ -932,7 +966,8 @@ static void __init acer_commandline_init(void)
>  	 * capability isn't available on the given interface
>  	 */
>  	set_u32(mailled, ACER_CAP_MAILLED);
> -	set_u32(threeg, ACER_CAP_THREEG);
> +	if (!has_type_aa)
> +		set_u32(threeg, ACER_CAP_THREEG);
>  	set_u32(brightness, ACER_CAP_BRIGHTNESS);
>  }
>  

Could you please give me any suggestion for the acer-wmi patches 1/4 -
4/4?
Does those patches good enough for you to merge to mainline?


Thank's a lot!
Joey Lee

^ permalink raw reply	[flat|nested] 9+ messages in thread
* [PATCH 0/4] Add new wmi support to acer-wmi driver
@ 2010-11-24 17:39 Lee, Chun-Yi
  2010-11-24 17:39 ` [PATCH 1/4] Add acer wmi hotkey events support Lee, Chun-Yi
  0 siblings, 1 reply; 9+ messages in thread
From: Lee, Chun-Yi @ 2010-11-24 17:39 UTC (permalink / raw)
  To: mjg59
  Cc: corentin.chary, dmitry.torokhov, tiwai, carlos, jbenc, jdelvare,
	trenn, linux-input, platform-driver-x86, Lee, Chun-Yi

Hi Matthew, 

These patches add new wmi support to acer-wmi driver, included the following
functions:

- Acer wmi hotkey events:
  Acer BIOS applied wmi hotkey events from 2010, this patch adds support.

- Enabled Acer Launch Manager mode:
  Directly enable it to avoid the raw EC behavior conflict with rfkill-input or
  userland solution.

- Add 3G rfkill sysfs file:
  Provide interface to userland for enable/disable 3G function by wmi method.

- Detect the WiFi/Bluetooth/3G devices available:
  Look for OEM type AAh in dmi to get the WiFi/BT/3G devices available.

Signed-off-by: Lee, Chun-Yi <jlee@novell.com>
Reviewed-by: Thomas Renninger <trenn@suse.de>

Lee, Chun-Yi (4):
  Add acer wmi hotkey events support
  Enabled Acer Launch Manager mode
  Add 3G rfkill sysfs file
  Detect the WiFi/Bluetooth/3G devices available

 drivers/platform/x86/Kconfig    |    2 +
 drivers/platform/x86/acer-wmi.c |  400 ++++++++++++++++++++++++++++++++++++++-
 2 files changed, 394 insertions(+), 8 deletions(-)

^ permalink raw reply	[flat|nested] 9+ messages in thread
* [PATCH 0/4] Add new wmi support to acer-wmi driver
@ 2010-12-04  1:03 Lee, Chun-Yi
  2010-12-04  1:03 ` [PATCH 1/4] Add acer wmi hotkey events support Lee, Chun-Yi
  0 siblings, 1 reply; 9+ messages in thread
From: Lee, Chun-Yi @ 2010-12-04  1:03 UTC (permalink / raw)
  To: mjg
  Cc: carlos, corentin.chary, dmitry.torokhov, corentincj, tiwai, mjg59,
	jbenc, jdelvare, trenn, platform-driver-x86, linux-input,
	Lee, Chun-Yi

Hi Matthew, 

These patches add new wmi support to acer-wmi driver, included the following
functions:

- Acer wmi hotkey events:
  Acer BIOS applied wmi hotkey events from 2010, this patch adds support.

- Enabled Acer Launch Manager mode:
  Directly enable it to avoid the raw EC behavior conflict with rfkill-input or
  userland solution.

- Add 3G rfkill sysfs file:
  Provide interface to userland for enable/disable 3G function by wmi method.

- Detect the WiFi/Bluetooth/3G devices available:
  Look for OEM type AAh in dmi to get the WiFi/BT/3G devices available.

Signed-off-by: Lee, Chun-Yi <jlee@novell.com>
Reviewed-by: Thomas Renninger <trenn@suse.de>

Lee, Chun-Yi (4):
  Add acer wmi hotkey events support
  Enabled Acer Launch Manager mode
  Add 3G rfkill sysfs file
  Detect the WiFi/Bluetooth/3G devices available

 drivers/platform/x86/Kconfig    |    2 +
 drivers/platform/x86/acer-wmi.c |  400 ++++++++++++++++++++++++++++++++++++++-
 2 files changed, 394 insertions(+), 8 deletions(-)

^ permalink raw reply	[flat|nested] 9+ messages in thread

end of thread, other threads:[~2010-12-04  1:03 UTC | newest]

Thread overview: 9+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2010-10-18 15:07 [PATCH 4/4] Detect the WiFi/Bluetooth/3G devices available Lee, Chun-Yi
2010-10-18 15:55 ` Dmitry Torokhov
  -- strict thread matches above, loose matches on Subject: below --
2010-10-20  4:12 Joey Lee
2010-10-30 16:36 [PATCH 1/4] Add acer wmi hotkey events support Lee, Chun-Yi
2010-10-30 16:36 ` [PATCH 2/4] Enabled Acer Launch Manager mode Lee, Chun-Yi
2010-10-30 16:36   ` [PATCH 3/4] Add 3G rfkill sysfs file Lee, Chun-Yi
2010-10-30 16:36     ` [PATCH 4/4] Detect the WiFi/Bluetooth/3G devices available Lee, Chun-Yi
2010-10-30 16:44 Joey Lee
2010-11-08  4:54 Joey Lee
2010-11-12  8:36 Joey Lee
2010-11-24 17:39 [PATCH 0/4] Add new wmi support to acer-wmi driver Lee, Chun-Yi
2010-11-24 17:39 ` [PATCH 1/4] Add acer wmi hotkey events support Lee, Chun-Yi
2010-11-24 17:39   ` [PATCH 2/4] Enabled Acer Launch Manager mode Lee, Chun-Yi
2010-11-24 17:39     ` [PATCH 3/4] Add 3G rfkill sysfs file Lee, Chun-Yi
2010-11-24 17:39       ` [PATCH 4/4] Detect the WiFi/Bluetooth/3G devices available Lee, Chun-Yi
2010-12-04  1:03 [PATCH 0/4] Add new wmi support to acer-wmi driver Lee, Chun-Yi
2010-12-04  1:03 ` [PATCH 1/4] Add acer wmi hotkey events support Lee, Chun-Yi
2010-12-04  1:03   ` [PATCH 2/4] Enabled Acer Launch Manager mode Lee, Chun-Yi
2010-12-04  1:03     ` [PATCH 3/4] Add 3G rfkill sysfs file Lee, Chun-Yi
2010-12-04  1:03       ` [PATCH 4/4] Detect the WiFi/Bluetooth/3G devices available Lee, Chun-Yi

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).