greybus: es1: handle cport data in and out

This commit is contained in:
Greg Kroah-Hartman 2014-09-13 11:09:35 -07:00
parent 0dad95dc37
commit 9c8d3afdb5
4 changed files with 71 additions and 5 deletions

View file

@ -298,6 +298,12 @@ int gb_new_ap_msg(u8 *data, int size, struct greybus_host_device *hd)
}
EXPORT_SYMBOL_GPL(gb_new_ap_msg);
void greybus_cport_in_data(struct greybus_host_device *hd, int cport, u8 *data,
size_t length)
{
// FIXME - implement...
}
EXPORT_SYMBOL_GPL(greybus_cport_in_data);
int gb_thread_init(void)
{

View file

@ -233,7 +233,11 @@ static void svc_callback(struct urb *urb)
static void cport_in_callback(struct urb *urb)
{
struct device *dev = &urb->dev->dev;
struct es1_ap_dev *es1 = urb->context;
int status = urb->status;
int retval;
u8 cport;
u8 *data;
switch (status) {
case 0:
@ -252,15 +256,40 @@ static void cport_in_callback(struct urb *urb)
goto exit;
}
// FIXME - handle the CPort in data
/* The size has to be more then just an "empty" transfer */
if (urb->actual_length <= 2) {
dev_err(dev, "%s: \"short\" cport in transfer of %d bytes?\n",
__func__, urb->actual_length);
goto exit;
}
/*
* The CPort number is the first byte of the data stream, the rest of
* the stream is "real" data
*/
data = urb->transfer_buffer;
cport = data[0];
data = &data[1];
/* Pass this data to the greybus core */
greybus_cport_in_data(es1->hd, cport, data, urb->actual_length - 1);
exit:
return;
/* put our urb back in the request pool */
retval = usb_submit_urb(urb, GFP_ATOMIC);
if (retval)
dev_err(dev, "%s: error %d in submitting urb.\n",
__func__, retval);
}
static void cport_out_callback(struct urb *urb)
{
struct device *dev = &urb->dev->dev;
struct gbuf *gbuf = urb->context;
struct es1_ap_dev *es1 = gbuf->hdpriv;
unsigned long flags;
int status = urb->status;
int i;
switch (status) {
case 0:
@ -273,15 +302,34 @@ static void cport_out_callback(struct urb *urb)
case -ESHUTDOWN:
case -EILSEQ:
/* device is gone, stop sending */
return;
goto exit;
default:
dev_err(dev, "%s: unknown status %d\n", __func__, status);
goto exit;
}
// FIXME - handle the CPort out data callback
// FIXME - do we care about errors going back up?
/* Tell the core the gbuf is properly sent */
greybus_gbuf_finished(gbuf);
exit:
return;
/*
* See if this was an urb in our pool, if so mark it "free", otherwise we
* need to free it ourselves.
*/
spin_lock_irqsave(&es1->cport_out_urb_lock, flags);
for (i = 0; i < NUM_CPORT_OUT_URB; ++i) {
if (urb == es1->cport_out_urb[i]) {
es1->cport_out_urb_busy[i] = false;
urb = NULL;
break;
}
}
spin_unlock_irqrestore(&es1->cport_out_urb_lock, flags);
if (urb)
usb_free_urb(urb);
}
/*

View file

@ -98,10 +98,19 @@ EXPORT_SYMBOL_GPL(greybus_get_gbuf);
int greybus_submit_gbuf(struct gbuf *gbuf, gfp_t mem_flags)
{
// FIXME - implement
return -ENOMEM;
}
int greybus_kill_gbuf(struct gbuf *gbuf)
{
// FIXME - implement
return -ENOMEM;
}
/* Can be called in interrupt context, do the work and get out of here */
void greybus_gbuf_finished(struct gbuf *gbuf)
{
// FIXME - implement
}
EXPORT_SYMBOL_GPL(greybus_gbuf_finished);

View file

@ -126,6 +126,9 @@ struct greybus_host_device {
struct greybus_host_device *greybus_create_hd(struct greybus_host_driver *host_driver,
struct device *parent);
void greybus_remove_hd(struct greybus_host_device *hd);
void greybus_cport_in_data(struct greybus_host_device *hd, int cport, u8 *data,
size_t length);
void greybus_gbuf_finished(struct gbuf *gbuf);
/* Increase these values if needed */