> >> +  if (num_bulk_out == 0) {
> >> +          dbg("Invalid interface, discarding.\n");
> >> +          return -5;
> > 
> > symbolic values are mandatory
> Where are they defined, so I can see which best fits my needs.

include/asm/errno.h and files included from that
 
> >> +  }
> >> +
> >> +  /* only do something if we have a bulk out endpoint */
> >> +  if (serial->num_bulk_out) {
> >> +          if (port->write_urb->status == -EINPROGRESS) {
> > 
> > this is a race condition, use a flag
> This was taken from usbserial too. Why do you mean a rare condition? I 
> think you mean the first checking serial->num_bulk_out, that is not 
> needed, the other I think is needed.

No, you must not read the status field before the completion handler is
called. The value you read is in flux. You must manage the occupation
of the urb yourself.


> >> +                  pBuf[offset] = HCI_HEADER_0;
> >> +                  pBuf[offset+1] = HCI_HEADER_1;
> >> +                  pBuf[offset+2] = (unsigned char) length;
> >> +                  pBuf[offset+3] = (unsigned char)(length >> 8);
> > 
> > We have macros for that
> Do you mean that there is allready a Macro defined, or that I must 
> define one?.

There are macros for writing little endian values defined.

> >> +                  memcpy(pBuf + offset + HCI_HEADER_LENGTH,       +       
> >>                                 pSrcBuf + 
> >> src_offset, length);
> >> +          }
> >> +
> >> +          port->write_urb->transfer_buffer = pBuf;
> >> +          
> >> +          /* set up our urb */
> >> +          usb_fill_bulk_urb (port->write_urb, serial->dev,
> >> +                             usb_sndbulkpipe (serial->dev,        +       
> >>                          
> >> port->bulk_out_endpointAddress),
> >> +                             port->write_urb->transfer_buffer,    +       
> >>                                 (count + 
> >> (no_headers                +                                               
> >> *HCI_HEADER_LENGTH )),
> >> +                             serial->type->write_bulk_callback,   +       
> >>                                                         port);
> >> +
> >> +          /* send the data out the bulk port */
> >> +          result = usb_submit_urb(port->write_urb, GFP_ATOMIC);
> > 
> > No need for atomic
> Ok, this was taken from usbserial too, Is GFP_KERNEL best? Which do you 
> suggest.

I am unsure. For now, use GFP_ATOMIC


> >> +void aircable_read_bulk_callback(struct urb *urb, struct pt_regs *regs)

                                                ^ callback
> >> +{
> >> +  struct usb_serial_port *port = (struct usb_serial_port  
> >> +                                                  *)urb->context;
> >> +  struct usb_serial *serial = port->serial;
> >> +  struct tty_struct *tty;
> >> +  unsigned char *data;
> >> +  unsigned long no_packages;
> >> +  unsigned long remaining, package_length;        
> >> +  unsigned long i;
> >> +  int result;
> >> +
> >> +  dbg("%s - port %d", __FUNCTION__, port->number);
> >> +
> >> +  if (urb->status) {
> >> +          dbg("%s - nonzero read bulk status received: %d",
> >> +                                  __FUNCTION__, urb->status);
> >> +          return;
> >> +  }
> >> +  
> >> +  usb_serial_debug_data(debug, &port->dev, __FUNCTION__,
> >> +                  urb->actual_length, urb->transfer_buffer);
> >> +
> >> +  tty = port->tty;        
> >> +  if (tty && urb->actual_length) {                
> >> +  //Does this package includes more information than the header???
> >> +          if (urb->actual_length > HCI_HEADER_LENGTH) {
> >> +                  remaining = urb->actual_length;
> >> +
> >> +                  no_packages = (urb->actual_length /
> >> +                                          COMPLETE_PACKAGE )+1;
> >> +                  
> >> +                  for (i = 0; i < no_packages ; ++i) {
> >> +                          if (remaining > COMPLETE_PACKAGE)               
> >> +               
> >> +                               package_length =  COMPLETE_PACKAGE;
> >> +                          else
> >> +                               package_length = remaining;                
> >> +               
> >> +
> >> +                          remaining -= package_length;                    
> >> +       
> >> +
> >> +                          data = kmalloc(package_length,
> >> +                                                  GFP_KERNEL);
> > 
> > No. You are in interrupt. Preallocate a buffer if you can. If you cannot 
> > GFP_ATOMIC
> I can not exactly see what you are talking of. Is there any example or 
> anywhere i can get further information about what you want to say.

If the kernel cannot schedule, and while an interrupt handler is running
it cannot, any attempt to swap will crash the machine. USB callbacks
are running as interrupt handlers. GFP_ATOMIC tells the memory management
code not to schedule.

        Regards
                Oliver



Using Tomcat but need to do more? Need to support web services, security?
Get stuff done quickly with pre-integrated technology to make your job easier
Download IBM WebSphere Application Server v.1.0.1 based on Apache Geronimo
http://sel.as-us.falkag.net/sel?cmd=lnk&kid=120709&bid=263057&dat=121642
_______________________________________________
linux-usb-devel@lists.sourceforge.net
To unsubscribe, use the last form field at:
https://lists.sourceforge.net/lists/listinfo/linux-usb-devel

Reply via email to