mbox series

[U-Boot,RFC,00/14] bmips: add bcm6348-enet support

Message ID 20180212163858.25601-1-noltari@gmail.com
Headers show
Series bmips: add bcm6348-enet support | expand

Message

Álvaro Fernández Rojas Feb. 12, 2018, 4:38 p.m. UTC
In order to add bcm6348-enet support, dma-uclass must be extended to support
dma channels and rewordked to operate like the other dm uclass (clk, reset...).

This is an RFC, so please give you feedback on the things that I should
fix or rework.

Álvaro Fernández Rojas (14):
  dma: add dma channels support and improve uclass
  dma: add bcm6348-iudma support
  bmips: bcm6338: add bcm6348-iudma support
  bmips: bcm6348: add bcm6348-iudma support
  bmips: bcm6358: add bcm6348-iudma support
  phy: add support for internal phys
  net: add support for bcm6348-enet
  bmips: bcm6338: add support for bcm6348-enet
  bmips: enable f@st1704 enet support
  bmips: bcm6348: add support for bcm6348-enet
  bmips: enable ct-5361 enet support
  bmips: bcm6358: add support for bcm6348-enet
  bmips: enable hg556a enet support
  bmips: enable nb4-ser enet support

 arch/mips/dts/brcm,bcm6338.dtsi       |  29 ++
 arch/mips/dts/brcm,bcm6348.dtsi       |  42 +++
 arch/mips/dts/brcm,bcm6358.dtsi       |  46 +++
 arch/mips/dts/comtrend,ct-5361.dts    |  12 +
 arch/mips/dts/huawei,hg556a.dts       |  12 +
 arch/mips/dts/sagem,f@st1704.dts      |  12 +
 arch/mips/dts/sfr,nb4-ser.dts         |  24 ++
 configs/comtrend_ct5361_ram_defconfig |   8 +-
 configs/huawei_hg556a_ram_defconfig   |   8 +-
 configs/sagem_f@st1704_ram_defconfig  |   9 +-
 configs/sfr_nb4-ser_ram_defconfig     |   8 +-
 drivers/dma/Kconfig                   |   8 +
 drivers/dma/Makefile                  |   1 +
 drivers/dma/bcm6348-iudma.c           | 498 ++++++++++++++++++++++++++++++++
 drivers/dma/dma-uclass.c              | 212 +++++++++++---
 drivers/mtd/spi/sf-uclass.c           |  17 ++
 drivers/mtd/spi/spi_flash.c           |  11 +-
 drivers/net/Kconfig                   |   9 +
 drivers/net/Makefile                  |   1 +
 drivers/net/bcm6348-eth.c             | 517 ++++++++++++++++++++++++++++++++++
 include/configs/bmips_common.h        |   5 +-
 include/dma-uclass.h                  | 110 ++++++++
 include/dma.h                         | 226 +++++++++++----
 include/dt-bindings/dma/bcm6338-dma.h |  15 +
 include/dt-bindings/dma/bcm6348-dma.h |  17 ++
 include/dt-bindings/dma/bcm6358-dma.h |  17 ++
 include/phy.h                         |   2 +
 include/spi_flash.h                   |   3 +
 28 files changed, 1780 insertions(+), 99 deletions(-)
 create mode 100644 drivers/dma/bcm6348-iudma.c
 create mode 100644 drivers/net/bcm6348-eth.c
 create mode 100644 include/dma-uclass.h
 create mode 100644 include/dt-bindings/dma/bcm6338-dma.h
 create mode 100644 include/dt-bindings/dma/bcm6348-dma.h
 create mode 100644 include/dt-bindings/dma/bcm6358-dma.h

Comments

Álvaro Fernández Rojas Feb. 19, 2018, 5:26 p.m. UTC | #1
No comments about DMA?

2018-02-12 17:38 GMT+01:00 Álvaro Fernández Rojas <noltari@gmail.com>:

> In order to add bcm6348-enet support, dma-uclass must be extended to
> support
> dma channels and rewordked to operate like the other dm uclass (clk,
> reset...).
>
> This is an RFC, so please give you feedback on the things that I should
> fix or rework.
>
> Álvaro Fernández Rojas (14):
>   dma: add dma channels support and improve uclass
>   dma: add bcm6348-iudma support
>   bmips: bcm6338: add bcm6348-iudma support
>   bmips: bcm6348: add bcm6348-iudma support
>   bmips: bcm6358: add bcm6348-iudma support
>   phy: add support for internal phys
>   net: add support for bcm6348-enet
>   bmips: bcm6338: add support for bcm6348-enet
>   bmips: enable f@st1704 enet support
>   bmips: bcm6348: add support for bcm6348-enet
>   bmips: enable ct-5361 enet support
>   bmips: bcm6358: add support for bcm6348-enet
>   bmips: enable hg556a enet support
>   bmips: enable nb4-ser enet support
>
>  arch/mips/dts/brcm,bcm6338.dtsi       |  29 ++
>  arch/mips/dts/brcm,bcm6348.dtsi       |  42 +++
>  arch/mips/dts/brcm,bcm6358.dtsi       |  46 +++
>  arch/mips/dts/comtrend,ct-5361.dts    |  12 +
>  arch/mips/dts/huawei,hg556a.dts       |  12 +
>  arch/mips/dts/sagem,f@st1704.dts      |  12 +
>  arch/mips/dts/sfr,nb4-ser.dts         |  24 ++
>  configs/comtrend_ct5361_ram_defconfig |   8 +-
>  configs/huawei_hg556a_ram_defconfig   |   8 +-
>  configs/sagem_f@st1704_ram_defconfig  |   9 +-
>  configs/sfr_nb4-ser_ram_defconfig     |   8 +-
>  drivers/dma/Kconfig                   |   8 +
>  drivers/dma/Makefile                  |   1 +
>  drivers/dma/bcm6348-iudma.c           | 498 ++++++++++++++++++++++++++++++
> ++
>  drivers/dma/dma-uclass.c              | 212 +++++++++++---
>  drivers/mtd/spi/sf-uclass.c           |  17 ++
>  drivers/mtd/spi/spi_flash.c           |  11 +-
>  drivers/net/Kconfig                   |   9 +
>  drivers/net/Makefile                  |   1 +
>  drivers/net/bcm6348-eth.c             | 517 ++++++++++++++++++++++++++++++
> ++++
>  include/configs/bmips_common.h        |   5 +-
>  include/dma-uclass.h                  | 110 ++++++++
>  include/dma.h                         | 226 +++++++++++----
>  include/dt-bindings/dma/bcm6338-dma.h |  15 +
>  include/dt-bindings/dma/bcm6348-dma.h |  17 ++
>  include/dt-bindings/dma/bcm6358-dma.h |  17 ++
>  include/phy.h                         |   2 +
>  include/spi_flash.h                   |   3 +
>  28 files changed, 1780 insertions(+), 99 deletions(-)
>  create mode 100644 drivers/dma/bcm6348-iudma.c
>  create mode 100644 drivers/net/bcm6348-eth.c
>  create mode 100644 include/dma-uclass.h
>  create mode 100644 include/dt-bindings/dma/bcm6338-dma.h
>  create mode 100644 include/dt-bindings/dma/bcm6348-dma.h
>  create mode 100644 include/dt-bindings/dma/bcm6358-dma.h
>
> --
> 2.11.0
>
>
Álvaro Fernández Rojas Feb. 20, 2018, 6:55 p.m. UTC | #2
Hi Simon,

El 20/02/2018 a las 19:49, Simon Glass escribió:
> Hi Alvaro,
>
> On 20 February 2018 at 10:46, Álvaro Fernández Rojas <noltari@gmail.com> wrote:
>> Move dma_ops to a separate header file, following other uclass implementations.
>>
>> Signed-off-by: Álvaro Fernández Rojas <noltari@gmail.com>
>> ---
>>   drivers/dma/dma-uclass.c |  3 ++-
>>   include/dma-uclass.h     | 38 ++++++++++++++++++++++++++++++++++++++
>>   include/dma.h            | 22 ----------------------
>>   3 files changed, 40 insertions(+), 23 deletions(-)
>>   create mode 100644 include/dma-uclass.h
>>
>> diff --git a/drivers/dma/dma-uclass.c b/drivers/dma/dma-uclass.c
>> index 3d0ce22fbc..6fd4e1b35d 100644
>> --- a/drivers/dma/dma-uclass.c
>> +++ b/drivers/dma/dma-uclass.c
>> @@ -10,10 +10,11 @@
>>    */
>>
>>   #include <common.h>
>> -#include <dma.h>
>>   #include <dm.h>
>>   #include <dm/uclass-internal.h>
>>   #include <dm/device-internal.h>
>> +#include <dma.h>
>> +#include <dma-uclass.h>
>>   #include <errno.h>
>>
>>   DECLARE_GLOBAL_DATA_PTR;
>> diff --git a/include/dma-uclass.h b/include/dma-uclass.h
>> new file mode 100644
>> index 0000000000..e29ad103f2
>> --- /dev/null
>> +++ b/include/dma-uclass.h
>> @@ -0,0 +1,38 @@
>> +/*
>> + * Copyright (C) 2018 Álvaro Fernández Rojas <noltari@gmail.com>
>> + * Copyright (C) 2015 Texas Instruments Incorporated, <www.ti.com>
>> + * Written by Mugunthan V N <mugunthanvnm@ti.com>
>> + *
>> + * SPDX-License-Identifier:    GPL-2.0+
>> + */
>> +
>> +#ifndef _DMA_UCLASS_H
>> +#define _DMA_UCLASS_H
>> +
>> +/* See dma.h for background documentation. */
>> +
>> +#include <dma.h>
>> +
>> +/*
>> + * struct dma_ops - Driver model DMA operations
>> + *
>> + * The uclass interface is implemented by all DMA devices which use
>> + * driver model.
>> + */
>> +struct dma_ops {
>> +       /*
>> +        * Get the current timer count
> Is this the correct purpose for the transfer() method?
This is just a copy&paste, that's what you can find in upstream dma.h ;D
Anyway, I will fix that.
>> +        *
>> +        * @dev: The DMA device
>> +        * @direction: direction of data transfer should be one from
>> +                      enum dma_direction
>> +        * @dst: Destination pointer
>> +        * @src: Source pointer
>> +        * @len: Length of the data to be copied.
> Is this the number of bytes
>
> What does this function actually do? Does it queue a transfer which
> completes later? How do I check if it is done?
>
> Please add a lot more docs here.
Same as above.
>
>> +        * @return: 0 if OK, -ve on error
>> +        */
>> +       int (*transfer)(struct udevice *dev, int direction, void *dst,
>> +                       void *src, size_t len);
>> +};
>> +
>> +#endif /* _DMA_UCLASS_H */
>> diff --git a/include/dma.h b/include/dma.h
>> index 71fa77f2ea..89320f10d9 100644
>> --- a/include/dma.h
>> +++ b/include/dma.h
>> @@ -28,28 +28,6 @@ enum dma_direction {
>>   #define DMA_SUPPORTS_DEV_TO_DEV        BIT(3)
>>
>>   /*
>> - * struct dma_ops - Driver model DMA operations
>> - *
>> - * The uclass interface is implemented by all DMA devices which use
>> - * driver model.
>> - */
>> -struct dma_ops {
>> -       /*
>> -        * Get the current timer count
>> -        *
>> -        * @dev: The DMA device
>> -        * @direction: direction of data transfer should be one from
>> -                      enum dma_direction
>> -        * @dst: Destination pointer
>> -        * @src: Source pointer
>> -        * @len: Length of the data to be copied.
>> -        * @return: 0 if OK, -ve on error
>> -        */
>> -       int (*transfer)(struct udevice *dev, int direction, void *dst,
>> -                       void *src, size_t len);
>> -};
>> -
>> -/*
>>    * struct dma_dev_priv - information about a device used by the uclass
>>    *
>>    * @supported: mode of transfers that DMA can support, should be
>> --
>> 2.11.0
>>
> Regards,
> Simon
Regards,
Álvaro.
Álvaro Fernández Rojas Feb. 20, 2018, 7 p.m. UTC | #3
Hi Simon,

El 20/02/2018 a las 19:49, Simon Glass escribió:
> Hi Alvaro,
>
> On 20 February 2018 at 10:46, Álvaro Fernández Rojas <noltari@gmail.com> wrote:
>> This adds channels support for dma controllers that have multiple channels
>> which can transfer data to/from different devices (enet, usb...).
>>
>> Signed-off-by: Álvaro Fernández Rojas <noltari@gmail.com>
>> ---
>>   v2: Introduce changes reported by Vignesh:
>>    - Respect current dma implementation.
>>    - Let dma_memcpy find a compatible dma device.
>>
>>   drivers/dma/Kconfig      |   7 ++
>>   drivers/dma/dma-uclass.c | 177 +++++++++++++++++++++++++++++++++++++++++++++++
>>   include/dma-uclass.h     |  77 +++++++++++++++++++++
>>   include/dma.h            | 169 ++++++++++++++++++++++++++++++++++++++++++++
>>   4 files changed, 430 insertions(+)
>>
>> diff --git a/drivers/dma/Kconfig b/drivers/dma/Kconfig
>> index 1b92c7789d..21b2c0dcaa 100644
>> --- a/drivers/dma/Kconfig
>> +++ b/drivers/dma/Kconfig
>> @@ -12,6 +12,13 @@ config DMA
>>            buses that is used to transfer data to and from memory.
>>            The uclass interface is defined in include/dma.h.
>>
>> +config DMA_CHANNELS
>> +       bool "Enable DMA channels support"
>> +       depends on DMA
>> +       help
>> +         Enable channels support for DMA. Some DMA controllers have multiple
>> +         channels which can either transfer data to/from different devices.
>> +
>>   config TI_EDMA3
>>          bool "TI EDMA3 driver"
>>          help
>> diff --git a/drivers/dma/dma-uclass.c b/drivers/dma/dma-uclass.c
>> index 6fd4e1b35d..a16c3a786c 100644
>> --- a/drivers/dma/dma-uclass.c
>> +++ b/drivers/dma/dma-uclass.c
>> @@ -15,10 +15,187 @@
>>   #include <dm/device-internal.h>
>>   #include <dma.h>
>>   #include <dma-uclass.h>
>> +#include <dt-structs.h>
>>   #include <errno.h>
>>
>>   DECLARE_GLOBAL_DATA_PTR;
>>
>> +#ifdef CONFIG_DMA_CHANNELS
>> +static inline struct dma_ops *dma_dev_ops(struct udevice *dev)
>> +{
>> +       return (struct dma_ops *)dev->driver->ops;
>> +}
>> +
>> +# if CONFIG_IS_ENABLED(OF_CONTROL)
>> +#  if CONFIG_IS_ENABLED(OF_PLATDATA)
>> +int dma_get_by_index_platdata(struct udevice *dev, int index,
>> +                             struct phandle_2_cell *cells, struct dma *dma)
>> +{
>> +       int ret;
>> +
>> +       if (index != 0)
>> +               return -ENOSYS;
>> +       ret = uclass_get_device(UCLASS_DMA, 0, &dma->dev);
>> +       if (ret)
>> +               return ret;
>> +       dma->id = cells[0].id;
>> +
>> +       return 0;
>> +}
>> +#  else
>> +static int dma_of_xlate_default(struct dma *dma,
>> +                               struct fdtdec_phandle_args *args)
>> +{
>> +       debug("%s(dma=%p)\n", __func__, dma);
>> +
>> +       if (args->args_count > 1) {
>> +               pr_err("Invaild args_count: %d\n", args->args_count);
>> +               return -EINVAL;
>> +       }
>> +
>> +       if (args->args_count)
>> +               dma->id = args->args[0];
>> +       else
>> +               dma->id = 0;
>> +
>> +       return 0;
>> +}
>> +
>> +int dma_get_by_index(struct udevice *dev, int index, struct dma *dma)
>> +{
>> +       int ret;
>> +       struct fdtdec_phandle_args args;
>> +       struct udevice *dev_dma;
>> +       struct dma_ops *ops;
>> +
>> +       debug("%s(dev=%p, index=%d, dma=%p)\n", __func__, dev, index, dma);
>> +
>> +       assert(dma);
>> +       ret = fdtdec_parse_phandle_with_args(gd->fdt_blob, dev_of_offset(dev),
>> +                                            "dmas", "#dma-cells", 0, index,
>> +                                            &args);
> Can you please use the livetree API? E.g. see dev_read_phandle_with_args()
>
> Also please move this into an ofdata_to_platdata function rather than
> doing it each time this function is called.
Ok, I did this some time ago and I used an older version of clk-uclass 
as a starting point.
I will switch to livetree in the next patch version.
>
>> +       if (ret) {
>> +               pr_err("%s: fdtdec_parse_phandle_with_args failed: err=%d\n",
>> +                     __func__, ret);
>> +               return ret;
>> +       }
>> +
>> +       ret = uclass_get_device_by_of_offset(UCLASS_DMA, args.node, &dev_dma);
>> +       if (ret) {
>> +               pr_err("%s: uclass_get_device_by_of_offset failed: err=%d\n",
>> +                     __func__, ret);
>> +               return ret;
>> +       }
>> +
>> +       dma->dev = dev_dma;
>> +
>> +       ops = dma_dev_ops(dev_dma);
>> +
>> +       if (ops->of_xlate)
>> +               ret = ops->of_xlate(dma, &args);
>> +       else
>> +               ret = dma_of_xlate_default(dma, &args);
>> +       if (ret) {
>> +               pr_err("of_xlate() failed: %d\n", ret);
>> +               return ret;
>> +       }
>> +
>> +       return dma_request(dev_dma, dma);
>> +}
>> +#  endif /* OF_PLATDATA */
>> +
>> +int dma_get_by_name(struct udevice *dev, const char *name, struct dma *dma)
>> +{
>> +       int index;
>> +
>> +       debug("%s(dev=%p, name=%s, dma=%p)\n", __func__, dev, name, dma);
>> +
>> +       index = fdt_stringlist_search(gd->fdt_blob, dev_of_offset(dev),
>> +                                     "dma-names", name);
> dev_read...
Ok.
>
>> +       if (index < 0) {
>> +               pr_err("fdt_stringlist_search() failed: %d\n", index);
>> +               return index;
>> +       }
>> +
>> +       return dma_get_by_index(dev, index, dma);
>> +}
>> +# endif /* OF_CONTROL */
>> +
>> +int dma_request(struct udevice *dev, struct dma *dma)
>> +{
>> +       struct dma_ops *ops = dma_dev_ops(dev);
>> +
>> +       debug("%s(dev=%p, dma=%p)\n", __func__, dev, dma);
>> +
>> +       dma->dev = dev;
>> +
>> +       if (!ops->request)
>> +               return 0;
>> +
>> +       return ops->request(dma);
>> +}
>> +
>> +int dma_free(struct dma *dma)
>> +{
>> +       struct dma_ops *ops = dma_dev_ops(dma->dev);
>> +
>> +       debug("%s(dma=%p)\n", __func__, dma);
>> +
>> +       if (!ops->free)
>> +               return 0;
>> +
>> +       return ops->free(dma);
>> +}
>> +
>> +int dma_enable(struct dma *dma)
>> +{
>> +       struct dma_ops *ops = dma_dev_ops(dma->dev);
>> +
>> +       debug("%s(dma=%p)\n", __func__, dma);
>> +
>> +       if (!ops->enable)
>> +               return -ENOSYS;
>> +
>> +       return ops->enable(dma);
>> +}
>> +
>> +int dma_disable(struct dma *dma)
>> +{
>> +       struct dma_ops *ops = dma_dev_ops(dma->dev);
>> +
>> +       debug("%s(dma=%p)\n", __func__, dma);
>> +
>> +       if (!ops->disable)
>> +               return -ENOSYS;
>> +
>> +       return ops->disable(dma);
>> +}
>> +
>> +int dma_receive(struct dma *dma, void **dst)
>> +{
>> +       struct dma_ops *ops = dma_dev_ops(dma->dev);
>> +
>> +       debug("%s(dma=%p)\n", __func__, dma);
>> +
>> +       if (!ops->receive)
>> +               return -1;
>> +
>> +       return ops->receive(dma, dst);
>> +}
>> +
>> +int dma_send(struct dma *dma, void *src, size_t len)
>> +{
>> +       struct dma_ops *ops = dma_dev_ops(dma->dev);
>> +
>> +       debug("%s(dma=%p)\n", __func__, dma);
>> +
>> +       if (!ops->send)
>> +               return -1;
>> +
>> +       return ops->send(dma, src, len);
>> +}
>> +#endif /* CONFIG_DMA_CHANNELS */
>> +
>>   int dma_get_device(u32 transfer_type, struct udevice **devp)
>>   {
>>          struct udevice *dev;
>> diff --git a/include/dma-uclass.h b/include/dma-uclass.h
>> index e29ad103f2..5faec69207 100644
>> --- a/include/dma-uclass.h
>> +++ b/include/dma-uclass.h
>> @@ -12,6 +12,7 @@
>>   /* See dma.h for background documentation. */
>>
>>   #include <dma.h>
>> +#include <fdtdec.h>
>>
>>   /*
>>    * struct dma_ops - Driver model DMA operations
>> @@ -20,6 +21,82 @@
>>    * driver model.
>>    */
>>   struct dma_ops {
>> +#ifdef CONFIG_DMA_CHANNELS
>> +       /**
>> +        * of_xlate - Translate a client's device-tree (OF) DMA specifier.
>> +        *
>> +        * The DMA core calls this function as the first step in implementing
>> +        * a client's dma_get_by_*() call.
>> +        *
>> +        * If this function pointer is set to NULL, the DMA core will use a
>> +        * default implementation, which assumes #dma-cells = <1>, and that
>> +        * the DT cell contains a simple integer DMA Channel.
>> +        *
>> +        * At present, the DMA API solely supports device-tree. If this
>> +        * changes, other xxx_xlate() functions may be added to support those
>> +        * other mechanisms.
>> +        *
>> +        * @dma: The dma struct to hold the translation result.
>> +        * @args:       The dma specifier values from device tree.
>> +        * @return 0 if OK, or a negative error code.
>> +        */
>> +       int (*of_xlate)(struct dma *dma,
>> +                       struct fdtdec_phandle_args *args);
> Use new livetree struct here
Ok.
>
> Regards,
> Simon
Regards,
Álvaro.