Skip site navigation (1)Skip section navigation (2)
Date:      Tue, 22 Sep 2009 11:21:28 -0400
From:      Pierre-Luc Drouin <pldrouin@pldrouin.net>
To:        Hans Petter Selasky <hselasky@c2i.net>
Cc:        ed@freebsd.org, freebsd-usb@freebsd.org
Subject:   Re: usb/138659: uftdi driver broken in RELENG_8/CURRENT
Message-ID:  <4AB8EB78.2020809@pldrouin.net>
In-Reply-To: <200909221638.47642.hselasky@c2i.net>
References:  <4AB6DA79.7050209@pldrouin.net> <200909220916.46186.hselasky@c2i.net> <4AB8C9CA.407@pldrouin.net> <200909221638.47642.hselasky@c2i.net>

next in thread | previous in thread | raw e-mail | index | archive | help
Hans Petter Selasky wrote:
> On Tuesday 22 September 2009 14:57:46 Pierre-Luc Drouin wrote:
>   
>> Hans Petter Selasky wrote:
>>     
>>> On Monday 21 September 2009 20:58:40 Pierre-Luc Drouin wrote:
>>>       
>>>> Hans Petter Selasky wrote:
>>>>         
>>>>> On Monday 21 September 2009 20:28:58 Pierre-Luc Drouin wrote:
>>>>>           
>>>>>> Hans Petter Selasky wrote:
>>>>>>             
>>>>>>> On Monday 21 September 2009 19:52:13 Pierre-Luc Drouin wrote:
>>>>>>>               
>>>>>>>> Hans Petter Selasky wrote:
>>>>>>>>                 
>>>>>>>>> On Monday 21 September 2009 19:29:10 Pierre-Luc Drouin wrote:
>>>>>>>>>                   
>>>>>>>>>> Hans Petter Selasky wrote:
>>>>>>>>>>                     
>>>>>>>>>>> On Monday 21 September 2009 03:44:25 Pierre-Luc Drouin wrote:
>>>>>>>>>>>                       
>>>>>>>>>>>> Hi,
>>>>>>>>>>>>
>>>>>>>>>>>> I am also having troubles with the uftdi driver on 8.0-BETA4.
>>>>>>>>>>>> I am trying to use a fan controller (mCubed bigNG) that uses a
>>>>>>>>>>>> FT232BL chip and it does not seem to be responding on FreeBSD
>>>>>>>>>>>> 8.0 while the same code works perfectly on Linux (I have not
>>>>>>>>>>>> tried the code on RELENG_7 yet but I could install it if
>>>>>>>>>>>> necessary).
>>>>>>>>>>>>
>>>>>>>>>>>> Here is the very simple code I am using for testing:
>>>>>>>>>>>> #include <termios.h>
>>>>>>>>>>>> #include <fcntl.h>
>>>>>>>>>>>> #include <string.h>
>>>>>>>>>>>> #include <unistd.h>
>>>>>>>>>>>> #include <stdio.h>
>>>>>>>>>>>>
>>>>>>>>>>>> int main();
>>>>>>>>>>>>
>>>>>>>>>>>> #define DEV "/dev/ttyU0"
>>>>>>>>>>>>
>>>>>>>>>>>> #define TBAN_SER_SOURCE1        0x05 /* Primary source */
>>>>>>>>>>>> #define TBAN_SER_SOURCE2        0x06 /* Alternative source
>>>>>>>>>>>> (miniNG...) */
>>>>>>>>>>>>
>>>>>>>>>>>> #define TBAN_SER_REQUEST        0x36
>>>>>>>>>>>>
>>>>>>>>>>>> int main()
>>>>>>>>>>>> {
>>>>>>>>>>>>   int fd;
>>>>>>>>>>>>   int result;
>>>>>>>>>>>>   struct termios oldtio, newtio;
>>>>>>>>>>>>   unsigned char buf[285];
>>>>>>>>>>>>
>>>>>>>>>>>>   printf("Opening device\n");
>>>>>>>>>>>>   fd=open(DEV, O_RDWR | O_NOCTTY);
>>>>>>>>>>>>
>>>>>>>>>>>>   if(fd<0) {
>>>>>>>>>>>>     perror(DEV);
>>>>>>>>>>>>     return 1;
>>>>>>>>>>>>   }
>>>>>>>>>>>>
>>>>>>>>>>>>   result=tcgetattr(fd,&oldtio);
>>>>>>>>>>>>   if(result<0) {
>>>>>>>>>>>>     perror("tcgetattr");
>>>>>>>>>>>>     return 1;
>>>>>>>>>>>>   }
>>>>>>>>>>>>
>>>>>>>>>>>>   memcpy(&newtio,&oldtio,sizeof(struct termios));
>>>>>>>>>>>>   newtio.c_cflag = B19200
>>>>>>>>>>>>
>>>>>>>>>>>>     | CRTSCTS
>>>>>>>>>>>>     | CS8
>>>>>>>>>>>>     | CREAD;
>>>>>>>>>>>>
>>>>>>>>>>>>   newtio.c_iflag     = IGNPAR;
>>>>>>>>>>>>   newtio.c_oflag     = 0;
>>>>>>>>>>>>   newtio.c_lflag     = 0;
>>>>>>>>>>>>   newtio.c_cc[VMIN]  = 1;
>>>>>>>>>>>>   newtio.c_cc[VTIME] = 0;
>>>>>>>>>>>>
>>>>>>>>>>>>   result=tcflush(fd, TCIFLUSH);
>>>>>>>>>>>>   if(result<0) {
>>>>>>>>>>>>     perror("tcflush");
>>>>>>>>>>>>     return 1;
>>>>>>>>>>>>   }
>>>>>>>>>>>>
>>>>>>>>>>>>   result=tcsetattr(fd,TCSANOW,&newtio);
>>>>>>>>>>>>   if(result<0) {
>>>>>>>>>>>>     perror("tcsetattr");
>>>>>>>>>>>>     return 1;
>>>>>>>>>>>>   }
>>>>>>>>>>>>
>>>>>>>>>>>>   sleep(1);
>>>>>>>>>>>>
>>>>>>>>>>>>   printf("Performing initial query\n");
>>>>>>>>>>>>   buf[0]=TBAN_SER_SOURCE1;
>>>>>>>>>>>>   buf[1]=TBAN_SER_REQUEST;
>>>>>>>>>>>>
>>>>>>>>>>>>   printf("Requesting status\n");
>>>>>>>>>>>>   result=write(fd,buf,2);
>>>>>>>>>>>>   if(result<0) {
>>>>>>>>>>>>     perror("write");
>>>>>>>>>>>>     return 1;
>>>>>>>>>>>>   }
>>>>>>>>>>>>
>>>>>>>>>>>>   sleep(1);
>>>>>>>>>>>>
>>>>>>>>>>>>   printf("Reading status\n");
>>>>>>>>>>>>   result=read(fd,buf,32);
>>>>>>>>>>>>   if(result<0) {
>>>>>>>>>>>>     perror("read");
>>>>>>>>>>>>     return 1;
>>>>>>>>>>>>   }
>>>>>>>>>>>>
>>>>>>>>>>>>   result=tcsetattr(fd,TCSANOW,&oldtio);
>>>>>>>>>>>>   if(result<0) {
>>>>>>>>>>>>     perror("tcsetattr");
>>>>>>>>>>>>     return 1;
>>>>>>>>>>>>   }
>>>>>>>>>>>>
>>>>>>>>>>>>   result=close(fd);
>>>>>>>>>>>>   if(result<0) {
>>>>>>>>>>>>     perror("close");
>>>>>>>>>>>>     return 1;
>>>>>>>>>>>>   }
>>>>>>>>>>>>   return 0;
>>>>>>>>>>>> }
>>>>>>>>>>>>
>>>>>>>>>>>> It hangs while reading independently of the number of bits I am
>>>>>>>>>>>> reading.
>>>>>>>>>>>>
>>>>>>>>>>>> Here is the output from dmesg when I load the uftdi module:
>>>>>>>>>>>> Sep 20 21:31:31 ldaemon kernel: uftdi0: <USB - Serial> on usbus6
>>>>>>>>>>>> Sep 20 21:31:31 ldaemon kernel: ucom_attach_tty:317: tp =
>>>>>>>>>>>> 0xffffff001f12b400, unit = 0 Sep 20 21:31:31 ldaemon kernel:
>>>>>>>>>>>> ucom_attach_tty:346: ttycreate: U0 Sep 20 21:31:34 ldaemon root:
>>>>>>>>>>>> Unknown USB device: vendor 0x051d product 0x0002 bus uhub0
>>>>>>>>>>>>
>>>>>>>>>>>> Here is the output in /var/log/messages when I enable the debug
>>>>>>>>>>>> output for ucom and uftdi: Sep 20 21:33:30 ldaemon kernel:
>>>>>>>>>>>> ucom_open:554: tp = 0xffffff001f12b400 Sep 20 21:33:30 ldaemon
>>>>>>>>>>>> kernel: ucom_dtr:827: onoff = 1 Sep 20 21:33:30 ldaemon kernel:
>>>>>>>>>>>> ucom_line_state:799: on=0x01, off=0x00 Sep 20 21:33:30 ldaemon
>>>>>>>>>>>> kernel: ucom_rts:838: onoff = 1
>>>>>>>>>>>> Sep 20 21:33:30 ldaemon kernel: ucom_line_state:799: on=0x02,
>>>>>>>>>>>> off=0x00 Sep 20 21:33:30 ldaemon kernel: ucom_break:816: onoff =
>>>>>>>>>>>> 0 Sep 20 21:33:30 ldaemon kernel: ucom_line_state:799: on=0x00,
>>>>>>>>>>>> off=0x04 Sep 20 21:33:30 ldaemon kernel: ucom_status_change:901:
>>>>>>>>>>>> Sep 20 21:33:30 ldaemon kernel: ucom_param:950: sc =
>>>>>>>>>>>> 0xffffff001f12ac58 Sep 20 21:33:30 ldaemon kernel:
>>>>>>>>>>>> uftdi_pre_param:653:
>>>>>>>>>>>> Sep 20 21:33:30 ldaemon kernel: ucom_dtr:827: onoff = 1
>>>>>>>>>>>> Sep 20 21:33:30 ldaemon kernel: ucom_line_state:799: on=0x01,
>>>>>>>>>>>> off=0x00 Sep 20 21:33:30 ldaemon kernel: ucom_rts:838: onoff = 1
>>>>>>>>>>>> Sep 20 21:33:30 ldaemon kernel: ucom_line_state:799: on=0x02,
>>>>>>>>>>>> off=0x00 Sep 20 21:33:30 ldaemon kernel: ucom_cfg_open:520:
>>>>>>>>>>>> Sep 20 21:33:30 ldaemon kernel: uftdi_cfg_open:354:
>>>>>>>>>>>> Sep 20 21:33:30 ldaemon kernel: uftdi_read_callback:459: status
>>>>>>>>>>>> change msr=0xf0 (0x00) lsr=0x60 (0x00) Sep 20 21:33:30 ldaemon
>>>>>>>>>>>> kernel: ucom_status_change:901:
>>>>>>>>>>>> Sep 20 21:33:30 ldaemon kernel: uftdi_cfg_get_status:705:
>>>>>>>>>>>> msr=0xf0 lsr=0x60 Sep 20 21:33:30 ldaemon kernel:
>>>>>>>>>>>> ucom_cfg_status_change:887: DCD changed to 1 Sep 20 21:33:30
>>>>>>>>>>>> ldaemon kernel:
>>>>>>>>>>>> uftdi_cfg_param:672: Sep 20 21:33:30 ldaemon kernel:
>>>>>>>>>>>> ucom_ioctl:653: cmd = 0x402c7413 Sep 20 21:33:30 ldaemon kernel:
>>>>>>>>>>>> ucom_ioctl:653: cmd = 0x80047410 Sep 20 21:33:30 ldaemon kernel:
>>>>>>>>>>>> ucom_ioctl:653: cmd = 0x802c7414 Sep 20 21:33:30 ldaemon kernel:
>>>>>>>>>>>> ucom_param:950: sc = 0xffffff001f12ac58 Sep 20 21:33:30 ldaemon
>>>>>>>>>>>> kernel:
>>>>>>>>>>>> uftdi_pre_param:653:
>>>>>>>>>>>> Sep 20 21:33:30 ldaemon kernel: uftdi_cfg_get_status:705:
>>>>>>>>>>>> msr=0xf0 lsr=0x60 Sep 20 21:33:30 ldaemon kernel:
>>>>>>>>>>>> uftdi_cfg_param:672: Sep 20 21:33:30 ldaemon kernel:
>>>>>>>>>>>> ucom_get_data:1064: cnt=0 Sep 20 21:33:31 ldaemon kernel:
>>>>>>>>>>>> ucom_ioctl:653: cmd = 0x80047410 Sep 20 21:33:32 ldaemon kernel:
>>>>>>>>>>>> ucom_outwakeup:1009: sc = 0xffffff001f12ac58 Sep 20 21:33:32
>>>>>>>>>>>> ldaemon kernel:
>>>>>>>>>>>> ucom_get_data:1064: cnt=2
>>>>>>>>>>>> Sep 20 21:33:32 ldaemon kernel: ucom_get_data:1064: cnt=0
>>>>>>>>>>>>
>>>>>>>>>>>> I really need to get this working so I am ready to test things
>>>>>>>>>>>> as much as I can...
>>>>>>>>>>>>                         
>>>>>>>>>>> Hi,
>>>>>>>>>>>
>>>>>>>>>>> You need to set raw mode for the TTY device I think. Maybe Ed can
>>>>>>>>>>> give you the function name you need to call to do that?
>>>>>>>>>>>
>>>>>>>>>>> --HPS
>>>>>>>>>>>                       
>>>>>>>>>> Do I need to do something like that?
>>>>>>>>>> ioctl(fileno(stdin), TIOCGETP, &tty_org);
>>>>>>>>>> tty = tty_org;
>>>>>>>>>>
>>>>>>>>>> /* set terminal to raw mode ... */
>>>>>>>>>> tty.sg_flags |= CRMOD;
>>>>>>>>>> tty.sg_flags &= ~ECHO;
>>>>>>>>>> tty.sg_flags &= ~XTABS;
>>>>>>>>>> tty.sg_flags |= RAW;
>>>>>>>>>>
>>>>>>>>>> Thanks!
>>>>>>>>>> Pierre-Luc Drouin
>>>>>>>>>>                     
>>>>>>>>> Hi,
>>>>>>>>>
>>>>>>>>> You need to call this function:
>>>>>>>>>
>>>>>>>>>      void
>>>>>>>>>      cfmakeraw(struct termios *t);
>>>>>>>>>
>>>>>>>>> --HPS
>>>>>>>>>                   
>>>>>>>> Hi,
>>>>>>>>
>>>>>>>> it still does not work. I have added the line
>>>>>>>> cfmakeraw(&newtio);
>>>>>>>>
>>>>>>>> just before the call to tcflush and I get the following output in
>>>>>>>> /var/log/messages:
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_open:554: tp =
>>>>>>>> 0xffffff001f12b400 Sep 21 13:38:46 ldaemon kernel: ucom_dtr:827:
>>>>>>>> onoff = 1
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_line_state:799: on=0x01,
>>>>>>>> off=0x00 Sep 21 13:38:46 ldaemon kernel: ucom_rts:838: onoff = 1
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_line_state:799: on=0x02,
>>>>>>>> off=0x00 Sep 21 13:38:46 ldaemon kernel: ucom_break:816: onoff = 0
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_line_state:799: on=0x00,
>>>>>>>> off=0x04 Sep 21 13:38:46 ldaemon kernel: ucom_status_change:901:
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_param:950: sc =
>>>>>>>> 0xffffff001f12ac58 Sep 21 13:38:46 ldaemon kernel:
>>>>>>>> uftdi_pre_param:653:
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_dtr:827: onoff = 1
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_line_state:799: on=0x01,
>>>>>>>> off=0x00 Sep 21 13:38:46 ldaemon kernel: ucom_rts:838: onoff = 1
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_line_state:799: on=0x02,
>>>>>>>> off=0x00 Sep 21 13:38:46 ldaemon kernel: ucom_cfg_open:520:
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: uftdi_cfg_open:354:
>>>>>>>> uftdi_cfg_get_status:705: msr=0xf0 lsr=0x60
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_cfg_status_change:887: DCD
>>>>>>>> changed to 1 Sep 21 13:38:46 ldaemon kernel: uftdi_cfg_param:672:
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_ioctl:653: cmd = 0x402c7413
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_ioctl:653: cmd = 0x80047410
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_ioctl:653: cmd = 0x802c7414
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_param:950: sc =
>>>>>>>> 0xffffff001f12ac58 Sep 21 13:38:46 ldaemon kernel:
>>>>>>>> uftdi_pre_param:653:
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: uftdi_cfg_param:672:
>>>>>>>> Sep 21 13:38:46 ldaemon kernel: ucom_get_data:1064: cnt=0
>>>>>>>> Sep 21 13:38:47 ldaemon kernel: ucom_ioctl:653: cmd = 0x80047410
>>>>>>>> Sep 21 13:38:48 ldaemon kernel: ucom_outwakeup:1009: sc =
>>>>>>>> 0xffffff001f12ac58 Sep 21 13:38:48 ldaemon kernel:
>>>>>>>> ucom_get_data:1064: cnt=2
>>>>>>>> Sep 21 13:38:48 ldaemon kernel: ucom_get_data:1064: cnt=0
>>>>>>>>                 
>>>>>>> Can you try adding a delay after setting the baud rate?
>>>>>>>
>>>>>>> --HPS
>>>>>>>               
>>>>>> The code already sleeps for 1 second after I applying the baud rate
>>>>>> (via tcsetattr(fd,TCSANOW,&newtio)). I am not sure to understand what
>>>>>> you mean...
>>>>>>             
>>>>> Hi,
>>>>>
>>>>> I mean try adding some:
>>>>>
>>>>> usleep(1000000);
>>>>>
>>>>> To your code to see if that changes anything.
>>>>>
>>>>> Also try reading one byte instead of 32.
>>>>>
>>>>> Last, try adding a printout to:
>>>>>
>>>>> src/sys/dev/usb/serial/uftdi.c
>>>>>
>>>>> uftdi_read_callback()
>>>>>
>>>>> and printout the actlen variable.
>>>>>
>>>>> --HPS
>>>>>           
>>>> ok, so I added the usleep statement right after the existing sleep
>>>> statement. I also tried reading a single byte. It did not make any
>>>> difference... I added a print statement to print the value of actlen
>>>> right after it is set via
>>>> usbd_xfer_status(xfer, &actlen, NULL, NULL, NULL);
>>>>
>>>> Here is the new output in /var/log/messages:
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_open:554: tp = 0xffffff0139488800
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_dtr:827: onoff = 1
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_line_state:799: on=0x01, off=0x00
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_rts:838: onoff = 1
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_line_state:799: on=0x02, off=0x00
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_break:816: onoff = 0
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_line_state:799: on=0x00, off=0x04
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_status_change:901:
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_param:950: sc = 0xffffff013bcac458
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_dtr:827: onoff = 1
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_line_state:799: on=0x01, off=0x00
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_rts:838: onoff = 1
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_line_state:799: on=0x02, off=0x00
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_cfg_open:520:
>>>> Sep 21 14:55:28 ldaemon kernel: actlen is 0
>>>> Sep 21 14:55:28 ldaemon kernel: actlen is 2
>>>> Sep 21 14:55:28 ldaemon kernel: actlen is 2
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_cfg_status_change:887: DCD changed
>>>> to 1 Sep 21 14:55:28 ldaemon kernel: ucom_ioctl:653: cmd = 0x402c7413
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_ioctl:653: cmd = 0x80047410 Sep 21
>>>> 14:55:28 ldaemon kernel: ucom_ioctl:653: cmd = 0x802c7414 Sep 21
>>>> 14:55:28 ldaemon kernel: ucom_param:950: sc = 0xffffff013bcac458 Sep 21
>>>> 14:55:28 ldaemon kernel: actlen is 2
>>>> Sep 21 14:55:28 ldaemon last message repeated 12 times
>>>> Sep 21 14:55:28 ldaemon kernel: ucom_get_data:1064: cnt=0
>>>> Sep 21 14:55:28 ldaemon kernel: actlen is 2
>>>> Sep 21 14:55:30 ldaemon last message repeated 111 times
>>>> Sep 21 14:55:30 ldaemon kernel: ucom_ioctl:653: cmd = 0x80047410
>>>> Sep 21 14:55:30 ldaemon kernel: actlen is 2
>>>> Sep 21 14:55:31 ldaemon last message repeated 62 times
>>>> Sep 21 14:55:31 ldaemon kernel: ucom_outwakeup:1009: sc =
>>>> 0xffffff013bcac458 Sep 21 14:55:31 ldaemon kernel: ucom_get_data:1064:
>>>> cnt=2
>>>> Sep 21 14:55:31 ldaemon kernel: ucom_get_data:1064: cnt=0
>>>> Sep 21 14:55:31 ldaemon kernel: actlen is 2
>>>>         
>>> If actlen is 2 then no modem data is transferred from the device.
>>>
>>> --HPS
>>>       
>> Hmm, so does it indicate a bug in uftdi? In asynchronous mode, SIGIO is
>> generated but when try reading I get error EINTR...
>>
>> Thanks!
>>     
>
> It indicates that your device is not sending any data.
>
> --HPS
>
>   
So does it mean that the write statement (a status request) is not 
transmitted to the device either? Because this write statement should be 
followed by data sent from the device and it effectively does on Linux. 
And about SIGIO, shouldn't this signal be generated only when there is 
data available to read? Why is it generated in asynchronous mode and 
then the read statement returns EINTR?

Thanks!
Pierre-Luc



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?4AB8EB78.2020809>