mbox series

[RFC,0/9] Regmap over USB for Multifunction USB Device (gpio, display, ...)

Message ID 20200216172117.49832-1-noralf@tronnes.org (mailing list archive)
Headers show
Series Regmap over USB for Multifunction USB Device (gpio, display, ...) | expand

Message

Noralf Trønnes Feb. 16, 2020, 5:21 p.m. UTC
Hi,

A while back I had the idea to turn a Raspberry Pi Zero into a $5
USB to HDMI/SDTV/DSI/DPI display adapter.

Thinking about how to represent the display to the driver I realised
that hardware use registers as API. And Linux does have a generic
register abstraction: regmap. Furthermore this means that if I can do a
regmap over USB implementation, it will be easy to do other functions
like gpio, adc and others. After a few iterations trying to understand
the USB subsystem and satisfying driver requirements, I now have
something that looks promising.

I'm sending out an early version hoping to get feedback especially on
the core parts that handles regmap and interrupts.

Overview:

          USB Host          :         USB Device
                            :
            --------------  :  ------------------
----------  | mfd: mud   |  :  | f_mud          |  ----------
| Driver |  --------------  :  |                |  | Driver |
----------  | regmap-usb |  :  | (mud_regmap)   |  ----------
            --------------  :  ------------------


I've attached 2 drivers:
- gpio/pinctrl: is more or less finished
- display: needs a lot more work


USB3 device
I've only tested this with usb2 devices (Pi, BBB) so I should get myself
a usb3 gadget capable board. My searching didn't turn up much, so this
seems to be quite rare. ROCK960 has USB 3.0 type C OTG but the price is
$139 which is a bit expensive for this hobby project. Does anyone know
of a cheap board?

Noralf.


Noralf Trønnes (9):
  regmap: Add USB support
  mfd: Add driver for Multifunction USB Device
  usb: gadget: function: Add Multifunction USB Device support
  pinctrl: Add Multifunction USB Device pinctrl driver
  usb: gadget: function: mud: Add gpio support
  regmap: Speed up _regmap_raw_write_impl() for large buffers
  drm: Add Multifunction USB Device display driver
  drm/client: Add drm_client_init_from_id() and drm_client_modeset_set()
  usb: gadget: function: mud: Add display support

 drivers/base/regmap/Kconfig              |    8 +-
 drivers/base/regmap/Makefile             |    1 +
 drivers/base/regmap/regmap-usb.c         | 1026 ++++++++++++++++++
 drivers/base/regmap/regmap.c             |   10 +-
 drivers/gpu/drm/Kconfig                  |    2 +
 drivers/gpu/drm/Makefile                 |    1 +
 drivers/gpu/drm/drm_client.c             |   37 +
 drivers/gpu/drm/drm_client_modeset.c     |   52 +
 drivers/gpu/drm/mud/Kconfig              |   18 +
 drivers/gpu/drm/mud/Makefile             |    4 +
 drivers/gpu/drm/mud/mud_drm.c            | 1198 ++++++++++++++++++++++
 drivers/gpu/drm/mud/mud_drm.h            |  137 +++
 drivers/gpu/drm/mud/mud_drm_gadget.c     |  889 ++++++++++++++++
 drivers/mfd/Kconfig                      |    8 +
 drivers/mfd/Makefile                     |    1 +
 drivers/mfd/mud.c                        |  580 +++++++++++
 drivers/pinctrl/Kconfig                  |    9 +
 drivers/pinctrl/Makefile                 |    1 +
 drivers/pinctrl/pinctrl-mud.c            |  657 ++++++++++++
 drivers/pinctrl/pinctrl-mud.h            |   89 ++
 drivers/usb/gadget/Kconfig               |   36 +
 drivers/usb/gadget/function/Makefile     |    6 +
 drivers/usb/gadget/function/f_mud.c      |  913 +++++++++++++++++
 drivers/usb/gadget/function/f_mud.h      |  210 ++++
 drivers/usb/gadget/function/f_mud_drm.c  |  181 ++++
 drivers/usb/gadget/function/f_mud_pins.c |  962 +++++++++++++++++
 drivers/usb/gadget/function/mud_regmap.c |  936 +++++++++++++++++
 include/drm/drm_client.h                 |    4 +
 include/linux/mfd/mud.h                  |   16 +
 include/linux/regmap.h                   |   23 +
 include/linux/regmap_usb.h               |   97 ++
 31 files changed, 8107 insertions(+), 5 deletions(-)
 create mode 100644 drivers/base/regmap/regmap-usb.c
 create mode 100644 drivers/gpu/drm/mud/Kconfig
 create mode 100644 drivers/gpu/drm/mud/Makefile
 create mode 100644 drivers/gpu/drm/mud/mud_drm.c
 create mode 100644 drivers/gpu/drm/mud/mud_drm.h
 create mode 100644 drivers/gpu/drm/mud/mud_drm_gadget.c
 create mode 100644 drivers/mfd/mud.c
 create mode 100644 drivers/pinctrl/pinctrl-mud.c
 create mode 100644 drivers/pinctrl/pinctrl-mud.h
 create mode 100644 drivers/usb/gadget/function/f_mud.c
 create mode 100644 drivers/usb/gadget/function/f_mud.h
 create mode 100644 drivers/usb/gadget/function/f_mud_drm.c
 create mode 100644 drivers/usb/gadget/function/f_mud_pins.c
 create mode 100644 drivers/usb/gadget/function/mud_regmap.c
 create mode 100644 include/linux/mfd/mud.h
 create mode 100644 include/linux/regmap_usb.h

Comments

Daniel Vetter Feb. 17, 2020, 9:40 a.m. UTC | #1
On Sun, Feb 16, 2020 at 06:21:08PM +0100, Noralf Trønnes wrote:
> Hi,
> 
> A while back I had the idea to turn a Raspberry Pi Zero into a $5
> USB to HDMI/SDTV/DSI/DPI display adapter.
> 
> Thinking about how to represent the display to the driver I realised
> that hardware use registers as API. And Linux does have a generic
> register abstraction: regmap. Furthermore this means that if I can do a
> regmap over USB implementation, it will be easy to do other functions
> like gpio, adc and others. After a few iterations trying to understand
> the USB subsystem and satisfying driver requirements, I now have
> something that looks promising.
> 
> I'm sending out an early version hoping to get feedback especially on
> the core parts that handles regmap and interrupts.
> 
> Overview:
> 
>           USB Host          :         USB Device
>                             :
>             --------------  :  ------------------
> ----------  | mfd: mud   |  :  | f_mud          |  ----------
> | Driver |  --------------  :  |                |  | Driver |
> ----------  | regmap-usb |  :  | (mud_regmap)   |  ----------
>             --------------  :  ------------------
> 
> 
> I've attached 2 drivers:
> - gpio/pinctrl: is more or less finished
> - display: needs a lot more work
> 
> 
> USB3 device
> I've only tested this with usb2 devices (Pi, BBB) so I should get myself
> a usb3 gadget capable board. My searching didn't turn up much, so this
> seems to be quite rare. ROCK960 has USB 3.0 type C OTG but the price is
> $139 which is a bit expensive for this hobby project. Does anyone know
> of a cheap board?
> 
> Noralf.

Pretty cool idea, and the drm side looks really tiny (after all your
drm_client work that is). I think the important feedback here is for the
usb and regmap stuff, that's totally out of my area. I've commented on the
drm_client patch, but that's just minor stuff, imo looks good.

Cheers, Daniel

> 
> 
> Noralf Trønnes (9):
>   regmap: Add USB support
>   mfd: Add driver for Multifunction USB Device
>   usb: gadget: function: Add Multifunction USB Device support
>   pinctrl: Add Multifunction USB Device pinctrl driver
>   usb: gadget: function: mud: Add gpio support
>   regmap: Speed up _regmap_raw_write_impl() for large buffers
>   drm: Add Multifunction USB Device display driver
>   drm/client: Add drm_client_init_from_id() and drm_client_modeset_set()
>   usb: gadget: function: mud: Add display support
> 
>  drivers/base/regmap/Kconfig              |    8 +-
>  drivers/base/regmap/Makefile             |    1 +
>  drivers/base/regmap/regmap-usb.c         | 1026 ++++++++++++++++++
>  drivers/base/regmap/regmap.c             |   10 +-
>  drivers/gpu/drm/Kconfig                  |    2 +
>  drivers/gpu/drm/Makefile                 |    1 +
>  drivers/gpu/drm/drm_client.c             |   37 +
>  drivers/gpu/drm/drm_client_modeset.c     |   52 +
>  drivers/gpu/drm/mud/Kconfig              |   18 +
>  drivers/gpu/drm/mud/Makefile             |    4 +
>  drivers/gpu/drm/mud/mud_drm.c            | 1198 ++++++++++++++++++++++
>  drivers/gpu/drm/mud/mud_drm.h            |  137 +++
>  drivers/gpu/drm/mud/mud_drm_gadget.c     |  889 ++++++++++++++++
>  drivers/mfd/Kconfig                      |    8 +
>  drivers/mfd/Makefile                     |    1 +
>  drivers/mfd/mud.c                        |  580 +++++++++++
>  drivers/pinctrl/Kconfig                  |    9 +
>  drivers/pinctrl/Makefile                 |    1 +
>  drivers/pinctrl/pinctrl-mud.c            |  657 ++++++++++++
>  drivers/pinctrl/pinctrl-mud.h            |   89 ++
>  drivers/usb/gadget/Kconfig               |   36 +
>  drivers/usb/gadget/function/Makefile     |    6 +
>  drivers/usb/gadget/function/f_mud.c      |  913 +++++++++++++++++
>  drivers/usb/gadget/function/f_mud.h      |  210 ++++
>  drivers/usb/gadget/function/f_mud_drm.c  |  181 ++++
>  drivers/usb/gadget/function/f_mud_pins.c |  962 +++++++++++++++++
>  drivers/usb/gadget/function/mud_regmap.c |  936 +++++++++++++++++
>  include/drm/drm_client.h                 |    4 +
>  include/linux/mfd/mud.h                  |   16 +
>  include/linux/regmap.h                   |   23 +
>  include/linux/regmap_usb.h               |   97 ++
>  31 files changed, 8107 insertions(+), 5 deletions(-)
>  create mode 100644 drivers/base/regmap/regmap-usb.c
>  create mode 100644 drivers/gpu/drm/mud/Kconfig
>  create mode 100644 drivers/gpu/drm/mud/Makefile
>  create mode 100644 drivers/gpu/drm/mud/mud_drm.c
>  create mode 100644 drivers/gpu/drm/mud/mud_drm.h
>  create mode 100644 drivers/gpu/drm/mud/mud_drm_gadget.c
>  create mode 100644 drivers/mfd/mud.c
>  create mode 100644 drivers/pinctrl/pinctrl-mud.c
>  create mode 100644 drivers/pinctrl/pinctrl-mud.h
>  create mode 100644 drivers/usb/gadget/function/f_mud.c
>  create mode 100644 drivers/usb/gadget/function/f_mud.h
>  create mode 100644 drivers/usb/gadget/function/f_mud_drm.c
>  create mode 100644 drivers/usb/gadget/function/f_mud_pins.c
>  create mode 100644 drivers/usb/gadget/function/mud_regmap.c
>  create mode 100644 include/linux/mfd/mud.h
>  create mode 100644 include/linux/regmap_usb.h
> 
> -- 
> 2.23.0
> 
> _______________________________________________
> dri-devel mailing list
> dri-devel@lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/dri-devel
Neil Armstrong Feb. 17, 2020, 10:32 a.m. UTC | #2
Hi,

On 16/02/2020 18:21, Noralf Trønnes wrote:
> Hi,
> 
> A while back I had the idea to turn a Raspberry Pi Zero into a $5
> USB to HDMI/SDTV/DSI/DPI display adapter.
> 
> Thinking about how to represent the display to the driver I realised
> that hardware use registers as API. And Linux does have a generic
> register abstraction: regmap. Furthermore this means that if I can do a
> regmap over USB implementation, it will be easy to do other functions
> like gpio, adc and others. After a few iterations trying to understand
> the USB subsystem and satisfying driver requirements, I now have
> something that looks promising.
> 
> I'm sending out an early version hoping to get feedback especially on
> the core parts that handles regmap and interrupts.
> 
> Overview:
> 
>           USB Host          :         USB Device
>                             :
>             --------------  :  ------------------
> ----------  | mfd: mud   |  :  | f_mud          |  ----------
> | Driver |  --------------  :  |                |  | Driver |
> ----------  | regmap-usb |  :  | (mud_regmap)   |  ----------
>             --------------  :  ------------------
> 

The idea is really like ARA's greybus, but much simpler !
Anyway nice idea, do you have good performance over USB2 and
RPi's awful DWC2 gagdet controller ?

Neil
> 
> I've attached 2 drivers:
> - gpio/pinctrl: is more or less finished
> - display: needs a lot more work
> 
> 
> USB3 device
> I've only tested this with usb2 devices (Pi, BBB) so I should get myself
> a usb3 gadget capable board. My searching didn't turn up much, so this
> seems to be quite rare. ROCK960 has USB 3.0 type C OTG but the price is
> $139 which is a bit expensive for this hobby project. Does anyone know
> of a cheap board?
> 
> Noralf.
> 
> 
> Noralf Trønnes (9):
>   regmap: Add USB support
>   mfd: Add driver for Multifunction USB Device
>   usb: gadget: function: Add Multifunction USB Device support
>   pinctrl: Add Multifunction USB Device pinctrl driver
>   usb: gadget: function: mud: Add gpio support
>   regmap: Speed up _regmap_raw_write_impl() for large buffers
>   drm: Add Multifunction USB Device display driver
>   drm/client: Add drm_client_init_from_id() and drm_client_modeset_set()
>   usb: gadget: function: mud: Add display support
> 
>  drivers/base/regmap/Kconfig              |    8 +-
>  drivers/base/regmap/Makefile             |    1 +
>  drivers/base/regmap/regmap-usb.c         | 1026 ++++++++++++++++++
>  drivers/base/regmap/regmap.c             |   10 +-
>  drivers/gpu/drm/Kconfig                  |    2 +
>  drivers/gpu/drm/Makefile                 |    1 +
>  drivers/gpu/drm/drm_client.c             |   37 +
>  drivers/gpu/drm/drm_client_modeset.c     |   52 +
>  drivers/gpu/drm/mud/Kconfig              |   18 +
>  drivers/gpu/drm/mud/Makefile             |    4 +
>  drivers/gpu/drm/mud/mud_drm.c            | 1198 ++++++++++++++++++++++
>  drivers/gpu/drm/mud/mud_drm.h            |  137 +++
>  drivers/gpu/drm/mud/mud_drm_gadget.c     |  889 ++++++++++++++++
>  drivers/mfd/Kconfig                      |    8 +
>  drivers/mfd/Makefile                     |    1 +
>  drivers/mfd/mud.c                        |  580 +++++++++++
>  drivers/pinctrl/Kconfig                  |    9 +
>  drivers/pinctrl/Makefile                 |    1 +
>  drivers/pinctrl/pinctrl-mud.c            |  657 ++++++++++++
>  drivers/pinctrl/pinctrl-mud.h            |   89 ++
>  drivers/usb/gadget/Kconfig               |   36 +
>  drivers/usb/gadget/function/Makefile     |    6 +
>  drivers/usb/gadget/function/f_mud.c      |  913 +++++++++++++++++
>  drivers/usb/gadget/function/f_mud.h      |  210 ++++
>  drivers/usb/gadget/function/f_mud_drm.c  |  181 ++++
>  drivers/usb/gadget/function/f_mud_pins.c |  962 +++++++++++++++++
>  drivers/usb/gadget/function/mud_regmap.c |  936 +++++++++++++++++
>  include/drm/drm_client.h                 |    4 +
>  include/linux/mfd/mud.h                  |   16 +
>  include/linux/regmap.h                   |   23 +
>  include/linux/regmap_usb.h               |   97 ++
>  31 files changed, 8107 insertions(+), 5 deletions(-)
>  create mode 100644 drivers/base/regmap/regmap-usb.c
>  create mode 100644 drivers/gpu/drm/mud/Kconfig
>  create mode 100644 drivers/gpu/drm/mud/Makefile
>  create mode 100644 drivers/gpu/drm/mud/mud_drm.c
>  create mode 100644 drivers/gpu/drm/mud/mud_drm.h
>  create mode 100644 drivers/gpu/drm/mud/mud_drm_gadget.c
>  create mode 100644 drivers/mfd/mud.c
>  create mode 100644 drivers/pinctrl/pinctrl-mud.c
>  create mode 100644 drivers/pinctrl/pinctrl-mud.h
>  create mode 100644 drivers/usb/gadget/function/f_mud.c
>  create mode 100644 drivers/usb/gadget/function/f_mud.h
>  create mode 100644 drivers/usb/gadget/function/f_mud_drm.c
>  create mode 100644 drivers/usb/gadget/function/f_mud_pins.c
>  create mode 100644 drivers/usb/gadget/function/mud_regmap.c
>  create mode 100644 include/linux/mfd/mud.h
>  create mode 100644 include/linux/regmap_usb.h
>
Noralf Trønnes Feb. 17, 2020, 2:05 p.m. UTC | #3
Den 17.02.2020 11.32, skrev Neil Armstrong:
> Hi,
> 
> On 16/02/2020 18:21, Noralf Trønnes wrote:
>> Hi,
>>
>> A while back I had the idea to turn a Raspberry Pi Zero into a $5
>> USB to HDMI/SDTV/DSI/DPI display adapter.
>>
>> Thinking about how to represent the display to the driver I realised
>> that hardware use registers as API. And Linux does have a generic
>> register abstraction: regmap. Furthermore this means that if I can do a
>> regmap over USB implementation, it will be easy to do other functions
>> like gpio, adc and others. After a few iterations trying to understand
>> the USB subsystem and satisfying driver requirements, I now have
>> something that looks promising.
>>
>> I'm sending out an early version hoping to get feedback especially on
>> the core parts that handles regmap and interrupts.
>>
>> Overview:
>>
>>           USB Host          :         USB Device
>>                             :
>>             --------------  :  ------------------
>> ----------  | mfd: mud   |  :  | f_mud          |  ----------
>> | Driver |  --------------  :  |                |  | Driver |
>> ----------  | regmap-usb |  :  | (mud_regmap)   |  ----------
>>             --------------  :  ------------------
>>
> 
> The idea is really like ARA's greybus, but much simpler !
> Anyway nice idea, do you have good performance over USB2 and
> RPi's awful DWC2 gagdet controller ?
> 

Not as good as I was hoping for. If I disable compression I'm getting 5
fps for a 1.5MB framebuffer (7800 kB/s):

$ modetest -M mud_drm -s 35:1024x768@RG16 -v
setting mode 1024x768-60.00Hz@RG16 on connectors 35, crtc 33
freq: 5.07Hz

When I tried reading I discovered that it was almost 3 times faster than
writing.

The zero gadget (loop testing) confirmed my findings:

Device:
$ sudo modprobe g_zero
[   44.221890] zero gadget: Gadget Zero, version: Cinco de Mayo 2008
[   44.221906] zero gadget: zero ready
[   60.751451] zero gadget: high-speed config #3: source/sink

Host:

$ sudo ~/testusb -a -t <n> -g 64 -s 16384
/dev/bus/usb/001/010 test 27,  107.230669 secs	-> 1000 / 107 =  9MB/s
/dev/bus/usb/001/010 test 28,   37.791292 secs	-> 1000 / 37  = 27MB/s
[73983.796552] usbtest 1-1.3:3.0: TEST 27: bulk write 1000Mbytes
[74205.060204] usbtest 1-1.3:3.0: TEST 28: bulk read 1000Mbytes

$ sudo ~/testusb -a -t <n> -g 64 -s 16384
/dev/bus/usb/001/010 test 5,  107.421535 secs
/dev/bus/usb/001/010 test 6,   38.189712 secs
[74893.204170] usbtest 1-1.3:3.0: TEST 5:  write 1000 sglists 64 entries
of 16384 bytes
[75012.592222] usbtest 1-1.3:3.0: TEST 6:  read 1000 sglists 64 entries
of 16384 bytes


I have tried Raspberry Pi1 and Pi4 as host (2 different controllers)
and Pi Zero and Beaglebone Black as device, getting similar result.

I found this post having the same issue:

Re: Asymmetric speed results with testusb/usbtest/g_zero
https://www.spinics.net/lists/linux-usb/msg100588.html

I haven't got a usb analyzer, but adding printk to
dwc2_assign_and_init_hc() showed that IN interrupts were 2-3 ms apart
but OUT interrupts were ~8 ms apart.

Noralf.
Andy Shevchenko Feb. 18, 2020, 8:57 p.m. UTC | #4
On Sun, Feb 16, 2020 at 7:30 PM Noralf Trønnes <noralf@tronnes.org> wrote:
>
> Hi,
>
> A while back I had the idea to turn a Raspberry Pi Zero into a $5
> USB to HDMI/SDTV/DSI/DPI display adapter.
>
> Thinking about how to represent the display to the driver I realised
> that hardware use registers as API. And Linux does have a generic
> register abstraction: regmap. Furthermore this means that if I can do a
> regmap over USB implementation, it will be easy to do other functions
> like gpio, adc and others. After a few iterations trying to understand
> the USB subsystem and satisfying driver requirements, I now have
> something that looks promising.
>
> I'm sending out an early version hoping to get feedback especially on
> the core parts that handles regmap and interrupts.
>
> Overview:
>
>           USB Host          :         USB Device
>                             :
>             --------------  :  ------------------
> ----------  | mfd: mud   |  :  | f_mud          |  ----------
> | Driver |  --------------  :  |                |  | Driver |
> ----------  | regmap-usb |  :  | (mud_regmap)   |  ----------
>             --------------  :  ------------------
>
>
> I've attached 2 drivers:
> - gpio/pinctrl: is more or less finished
> - display: needs a lot more work

Can regmap-usb be used for drivers/mfd/dln2.c for example?
Noralf Trønnes Feb. 18, 2020, 9:31 p.m. UTC | #5
Den 18.02.2020 21.57, skrev Andy Shevchenko:
> On Sun, Feb 16, 2020 at 7:30 PM Noralf Trønnes <noralf@tronnes.org> wrote:
>>
>> Hi,
>>
>> A while back I had the idea to turn a Raspberry Pi Zero into a $5
>> USB to HDMI/SDTV/DSI/DPI display adapter.
>>
>> Thinking about how to represent the display to the driver I realised
>> that hardware use registers as API. And Linux does have a generic
>> register abstraction: regmap. Furthermore this means that if I can do a
>> regmap over USB implementation, it will be easy to do other functions
>> like gpio, adc and others. After a few iterations trying to understand
>> the USB subsystem and satisfying driver requirements, I now have
>> something that looks promising.
>>
>> I'm sending out an early version hoping to get feedback especially on
>> the core parts that handles regmap and interrupts.
>>
>> Overview:
>>
>>           USB Host          :         USB Device
>>                             :
>>             --------------  :  ------------------
>> ----------  | mfd: mud   |  :  | f_mud          |  ----------
>> | Driver |  --------------  :  |                |  | Driver |
>> ----------  | regmap-usb |  :  | (mud_regmap)   |  ----------
>>             --------------  :  ------------------
>>
>>
>> I've attached 2 drivers:
>> - gpio/pinctrl: is more or less finished
>> - display: needs a lot more work
> 
> Can regmap-usb be used for drivers/mfd/dln2.c for example?
> 

No, apparently dln-2 uses custom protocol structs for each function with
a common header. regmap-usb is a register abstraction with the ability
to bulk read/write multiple registers in one transfer.

I see that dln-2 does a lot of what I'm aiming for except that it
doesn't have the display part.

Noralf.