X-Git-Url: http://pilppa.org/gitweb/?a=blobdiff_plain;f=drivers%2Fusb%2Fmisc%2Fberry_charge.c;h=24e2dc3148a492d6b1adaf40a484b21717ae72bd;hb=eb86be5424d4c08e686d5e578b72a26c516ae58a;hp=b15f2fd8dab459b7ef4ea581f4192e7aae4c5c75;hpb=54b8c39fbd76a7341b66e49de677ea366737fce7;p=linux-2.6-omap-h63xx.git diff --git a/drivers/usb/misc/berry_charge.c b/drivers/usb/misc/berry_charge.c index b15f2fd8dab..24e2dc3148a 100644 --- a/drivers/usb/misc/berry_charge.c +++ b/drivers/usb/misc/berry_charge.c @@ -26,8 +26,11 @@ #define RIM_VENDOR 0x0fca #define BLACKBERRY 0x0001 +#define BLACKBERRY_PEARL_DUAL 0x0004 +#define BLACKBERRY_PEARL 0x0006 static int debug; +static int pearl_dual_mode = 1; #ifdef dbg #undef dbg @@ -38,6 +41,8 @@ static int debug; static struct usb_device_id id_table [] = { { USB_DEVICE(RIM_VENDOR, BLACKBERRY) }, + { USB_DEVICE(RIM_VENDOR, BLACKBERRY_PEARL) }, + { USB_DEVICE(RIM_VENDOR, BLACKBERRY_PEARL_DUAL) }, { }, /* Terminating entry */ }; MODULE_DEVICE_TABLE(usb, id_table); @@ -66,7 +71,7 @@ static int magic_charge(struct usb_device *udev) if (retval != 2) { dev_err(&udev->dev, "First magic command failed: %d.\n", retval); - return retval; + goto exit; } dbg(&udev->dev, "Sending second magic command\n"); @@ -75,7 +80,7 @@ static int magic_charge(struct usb_device *udev) if (retval != 0) { dev_err(&udev->dev, "Second magic command failed: %d.\n", retval); - return retval; + goto exit; } dbg(&udev->dev, "Calling set_configuration\n"); @@ -83,6 +88,33 @@ static int magic_charge(struct usb_device *udev) if (retval) dev_err(&udev->dev, "Set Configuration failed :%d.\n", retval); +exit: + kfree(dummy_buffer); + return retval; +} + +static int magic_dual_mode(struct usb_device *udev) +{ + char *dummy_buffer = kzalloc(2, GFP_KERNEL); + int retval; + + if (!dummy_buffer) + return -ENOMEM; + + /* send magic command so that the Blackberry Pearl device exposes + * two interfaces: both the USB mass-storage one and one which can + * be used for database access. */ + dbg(&udev->dev, "Sending magic pearl command\n"); + retval = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0), + 0xa9, 0xc0, 1, 1, dummy_buffer, 2, 100); + dbg(&udev->dev, "Magic pearl command returned %d\n", retval); + + dbg(&udev->dev, "Calling set_configuration\n"); + retval = usb_driver_set_configuration(udev, 1); + if (retval) + dev_err(&udev->dev, "Set Configuration failed :%d.\n", retval); + + kfree(dummy_buffer); return retval; } @@ -105,6 +137,10 @@ static int berry_probe(struct usb_interface *intf, /* turn the power on */ magic_charge(udev); + if ((le16_to_cpu(udev->descriptor.idProduct) == BLACKBERRY_PEARL) && + (pearl_dual_mode)) + magic_dual_mode(udev); + /* we don't really want to bind to the device, userspace programs can * handle the syncing just fine, so get outta here. */ return -ENODEV; @@ -138,3 +174,5 @@ MODULE_LICENSE("GPL"); MODULE_AUTHOR("Greg Kroah-Hartman "); module_param(debug, bool, S_IRUGO | S_IWUSR); MODULE_PARM_DESC(debug, "Debug enabled or not"); +module_param(pearl_dual_mode, bool, S_IRUGO | S_IWUSR); +MODULE_PARM_DESC(pearl_dual_mode, "Change Blackberry Pearl to run in dual mode");