Skip to content

Commit

Permalink
Add usb_configuration and usb_connected switches
Browse files Browse the repository at this point in the history
  • Loading branch information
psyke83 committed Sep 12, 2011
1 parent 621455b commit 039582a
Show file tree
Hide file tree
Showing 2 changed files with 59 additions and 1 deletion.
49 changes: 49 additions & 0 deletions drivers/usb/gadget/composite.c
Expand Up @@ -440,6 +440,8 @@ static int set_config(struct usb_composite_dev *cdev,
power = c->bMaxPower ? (2 * c->bMaxPower) : CONFIG_USB_GADGET_VBUS_DRAW;
done:
usb_gadget_vbus_draw(gadget, power);

schedule_work(&cdev->switch_work);
return result;
}

Expand Down Expand Up @@ -692,6 +694,15 @@ composite_setup(struct usb_gadget *gadget, const struct usb_ctrlrequest *ctrl)
u16 w_value = le16_to_cpu(ctrl->wValue);
u16 w_length = le16_to_cpu(ctrl->wLength);
struct usb_function *f = NULL;
unsigned long flags;

spin_lock_irqsave(&cdev->lock, flags);
if (!cdev->connected) {
cdev->connected = 1;
schedule_work(&cdev->switch_work);
}
spin_unlock_irqrestore(&cdev->lock, flags);


/* partial re-init of the response message; the function or the
* gadget might need to intercept e.g. a control-OUT completion
Expand Down Expand Up @@ -882,6 +893,8 @@ static void composite_disconnect(struct usb_gadget *gadget)
spin_lock_irqsave(&cdev->lock, flags);
if (cdev->config)
reset_config(cdev);
cdev->connected = 0;
schedule_work(&cdev->switch_work);
spin_unlock_irqrestore(&cdev->lock, flags);
}

Expand Down Expand Up @@ -934,6 +947,8 @@ composite_unbind(struct usb_gadget *gadget)
kfree(cdev->req->buf);
usb_ep_free_request(gadget->ep0, cdev->req);
}
switch_dev_unregister(&cdev->sw_connected);
switch_dev_unregister(&cdev->sw_config);
kfree(cdev);
set_gadget_data(gadget, NULL);
composite = NULL;
Expand Down Expand Up @@ -961,6 +976,30 @@ string_override(struct usb_gadget_strings **tab, u8 id, const char *s)
}
}

static void
composite_switch_work(struct work_struct *data)
{
struct usb_composite_dev *cdev =
container_of(data, struct usb_composite_dev, switch_work);
struct usb_configuration *config = cdev->config;
int connected;
unsigned long flags;

spin_lock_irqsave(&cdev->lock, flags);
if (cdev->connected != cdev->sw_connected.state) {
connected = cdev->connected;
spin_unlock_irqrestore(&cdev->lock, flags);
switch_set_state(&cdev->sw_connected, connected);
} else {
spin_unlock_irqrestore(&cdev->lock, flags);
}

if (config)
switch_set_state(&cdev->sw_config, config->bConfigurationValue);
else
switch_set_state(&cdev->sw_config, 0);
}

static int composite_bind(struct usb_gadget *gadget)
{
struct usb_composite_dev *cdev;
Expand Down Expand Up @@ -1008,6 +1047,16 @@ static int composite_bind(struct usb_gadget *gadget)
if (status < 0)
goto fail;

cdev->sw_connected.name = "usb_connected";
status = switch_dev_register(&cdev->sw_connected);
if (status < 0)
goto fail;
cdev->sw_config.name = "usb_configuration";
status = switch_dev_register(&cdev->sw_config);
if (status < 0)
goto fail;
INIT_WORK(&cdev->switch_work, composite_switch_work);

cdev->desc = *composite->dev;
cdev->desc.bMaxPacketSize0 = gadget->ep0->maxpacket;

Expand Down
11 changes: 10 additions & 1 deletion include/linux/usb/composite.h
Expand Up @@ -36,6 +36,7 @@

#include <linux/usb/ch9.h>
#include <linux/usb/gadget.h>
#include <linux/switch.h>


struct usb_configuration;
Expand Down Expand Up @@ -343,7 +344,15 @@ struct usb_composite_dev {
unsigned deactivations;

/* protects at least deactivation count */
spinlock_t lock;
spinlock_t lock;
/* switch indicating connected/disconnected state */
struct switch_dev sw_connected;
/* switch indicating current configuration */
struct switch_dev sw_config;
/* current connected state for sw_connected */
bool connected;

struct work_struct switch_work;
};

extern int usb_string_id(struct usb_composite_dev *c);
Expand Down

12 comments on commit 039582a

@alanorth
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What is this for?... tethering? USB host?

@psyke83
Copy link
Owner Author

@psyke83 psyke83 commented on 039582a Oct 2, 2011

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's some code backported from the 2.6.35 kernel for USB tethering, yes.

In order for it to work properly, you also need to compile netd with a custom USBController.cpp implementation that takes into account the proper USB product IDs for tethered and untethered states. My phone uses ID 1038 for untethered and 1039 for tethered (RNDIS), and the code is here: https://github.com/psyke83/android_device_huawei_u8160/blob/master/UsbController.cpp

You can check your phone's product IDs by looking at board-msm7225.c and/or checking the output of /sys/module/g_android/parameters/product_id while tethered/untethered (the former would require you to test on a stock ROM, I guess). I have a strong suspicion that your U8150 will use the same IDs, however.

Don't forget to define the custom controller code in your BoardConfig.mk. Mine is like so:

BOARD_CUSTOM_USB_CONTROLLER := ../../device/huawei/u8160/UsbController.cpp

@alanorth
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah, yes, I remember you discussing this some weeks ago in the U8150 CM7 thread on XDA... 1038 looks familiar to me, I'm pretty sure I've seen that in my udev rules (among the dozen I have for oddball devices). I'll port this to U8150 when I get some time to test. Adios!

@alanorth
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think tilal's got it working in our U8150 but I haven't tried, and his commits are a bit hard to follow :). I might ask for help in a bit.

On a related note, I keep seeing this error in logcat: D/Vold ( 117): USB mass storage support is not enabled in the kernel

Which I'm assuming is related to USB mounting of the sdcard on the host computer. I notice we don't have anything like CONFIG_USB_ANDROID_MASS_STORAGE=y in our kernel, so what could it be missing?

@psyke83
Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@LalitMaganti
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've got tethering working on linux. From next time I'll make commits clearer :)

@alanorth
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

AHhahah future generations of hackers will thank you ;). I'll still keep pursuing it in my kernel/device tree so I can understand what's going on when I'm haxx0ring and troubleshooting.

@alanorth
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok, my USB tethering is finally working. Actually it was working lastnight, I just had to rebuild CM with the new UsbController and reflash, but got busy.

My kernel patches to JoeyJiao's source are exactly the same as yours, but the changes were already present in the kernel (only commented out). Weird, eh? See: alanorth/android-huawei-kernel-common@482f13d

Thanks for the help. The tethering is buggy, but working; still gotta debug a bit.

@psyke83
Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

JoeyJiao added this same switch code to his kernel source, and then commented the code for some unknown reason.

@alanorth
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Where'd you get yours?

@psyke83
Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't remember where it came from exactly; I found it for another device's .32 kernel... perhaps the Blade ZTE. The code itself is from the 2.6.35 kernel.

@alanorth
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It must have been this one: https://www.codeaurora.org/gitweb/quic/la/?p=kernel/common.git;a=commit;h=3fa64c7f7fc44d88bfbb6cb925882017850c0c69

Just poring through the msm 2.6.35 for interesting patches and I saw that :)

Please sign in to comment.