tree:   https://git.kernel.org/pub/scm/linux/kernel/git/balbi/usb.git 
testing/next
head:   862b43460309779e5814616a68aa36d29a70d6e0
commit: 2b4e4d3c929db0fc7cf99212bfac0570b6902c14 [48/49] usb: gadget: serial: 
fix oops when data rx'd after close
config: xtensa-allmodconfig (attached as .config)
compiler: xtensa-linux-gcc (GCC) 4.9.0
reproduce:
        wget 
https://raw.githubusercontent.com/01org/lkp-tests/master/sbin/make.cross -O 
~/bin/make.cross
        chmod +x ~/bin/make.cross
        git checkout 2b4e4d3c929db0fc7cf99212bfac0570b6902c14
        # save the attached .config to linux build tree
        make.cross ARCH=xtensa 

All errors (new ones prefixed by >>):

   drivers/usb//gadget/function/u_serial.c: In function 'gs_rx_push':
>> drivers/usb//gadget/function/u_serial.c:540:19: error: invalid operands to 
>> binary & (have 'unsigned int' and 'struct tty_struct *')
      if (req->actual & tty) {
                      ^

vim +540 drivers/usb//gadget/function/u_serial.c

   492  
   493  /*
   494   * RX tasklet takes data out of the RX queue and hands it up to the TTY
   495   * layer until it refuses to take any more data (or is throttled back).
   496   * Then it issues reads for any further data.
   497   *
   498   * If the RX queue becomes full enough that no usb_request is queued,
   499   * the OUT endpoint may begin NAKing as soon as its FIFO fills up.
   500   * So QUEUE_SIZE packets plus however many the FIFO holds (usually two)
   501   * can be buffered before the TTY layer's buffers (currently 64 KB).
   502   */
   503  static void gs_rx_push(unsigned long _port)
   504  {
   505          struct gs_port          *port = (void *)_port;
   506          struct tty_struct       *tty;
   507          struct list_head        *queue = &port->read_queue;
   508          bool                    disconnect = false;
   509          bool                    do_push = false;
   510  
   511          /* hand any queued data to the tty */
   512          spin_lock_irq(&port->port_lock);
   513          tty = port->port.tty;
   514          while (!list_empty(queue)) {
   515                  struct usb_request      *req;
   516  
   517                  req = list_first_entry(queue, struct usb_request, list);
   518  
   519                  /* leave data queued if tty was rx throttled */
   520                  if (tty && tty_throttled(tty))
   521                          break;
   522  
   523                  switch (req->status) {
   524                  case -ESHUTDOWN:
   525                          disconnect = true;
   526                          pr_vdebug("ttyGS%d: shutdown\n", 
port->port_num);
   527                          break;
   528  
   529                  default:
   530                          /* presumably a transient fault */
   531                          pr_warn("ttyGS%d: unexpected RX status %d\n",
   532                                  port->port_num, req->status);
   533                          /* FALLTHROUGH */
   534                  case 0:
   535                          /* normal completion */
   536                          break;
   537                  }
   538  
   539                  /* push data to (open) tty */
 > 540                  if (req->actual & tty) {
   541                          char            *packet = req->buf;
   542                          unsigned        size = req->actual;
   543                          unsigned        n;
   544                          int             count;
   545  
   546                          /* we may have pushed part of this packet 
already... */
   547                          n = port->n_read;
   548                          if (n) {
   549                                  packet += n;
   550                                  size -= n;
   551                          }
   552  
   553                          count = tty_insert_flip_string(&port->port, 
packet,
   554                                          size);
   555                          if (count)
   556                                  do_push = true;
   557                          if (count != size) {
   558                                  /* stop pushing; TTY layer can't handle 
more */
   559                                  port->n_read += count;
   560                                  pr_vdebug("ttyGS%d: rx block %d/%d\n",
   561                                            port->port_num, count, 
req->actual);
   562                                  break;
   563                          }
   564                          port->n_read = 0;
   565                  }
   566  
   567                  list_move(&req->list, &port->read_pool);
   568                  port->read_started--;
   569          }
   570  
   571          /* Push from tty to ldisc; this is handled by a workqueue,
   572           * so we won't get callbacks and can hold port_lock
   573           */
   574          if (do_push)
   575                  tty_flip_buffer_push(&port->port);
   576  
   577  
   578          /* We want our data queue to become empty ASAP, keeping data
   579           * in the tty and ldisc (not here).  If we couldn't push any
   580           * this time around, there may be trouble unless there's an
   581           * implicit tty_unthrottle() call on its way...
   582           *
   583           * REVISIT we should probably add a timer to keep the tasklet
   584           * from starving ... but it's not clear that case ever happens.
   585           */
   586          if (!list_empty(queue) && tty) {
   587                  if (!tty_throttled(tty)) {
   588                          if (do_push)
   589                                  tasklet_schedule(&port->push);
   590                          else
   591                                  pr_warn("ttyGS%d: RX not scheduled?\n",
   592                                          port->port_num);
   593                  }
   594          }
   595  
   596          /* If we're still connected, refill the USB RX queue. */
   597          if (!disconnect && port->port_usb)
   598                  gs_start_rx(port);
   599  
   600          spin_unlock_irq(&port->port_lock);
   601  }
   602  

---
0-DAY kernel test infrastructure                Open Source Technology Center
https://lists.01.org/pipermail/kbuild-all                   Intel Corporation

Attachment: .config.gz
Description: application/gzip

Reply via email to