Hi Chris,
Thanks for the reply.
Yes, I have tried that solution, but somehow the driver get a cap fault
(dereferencing a null pointer) eventually later, but I have not
investigated why.
As I mentioned in my original post, that approach is definitely not the
correct one, as the priv property should well, remain private to the MUX
subsystem. I'm ok to expose it (assuming there are no other issues that I
will have to investigate) through a simple API (i.e.
get_iomux_base_vaddr()).

And thank you for the pointer to your project. I will definitely take a
look at that.

Regards,
Fabrizio Bertocci
Real-Time Innovations
Sunnyvale, CA





On Tue, Jun 26, 2018 at 6:10 AM, Chris Guikema <
[email protected]> wrote:

> Fabrizio,
>
>
>
> It looks like the mux_sys_init uses the RESOURCE macro,
>
>
>
> #define RESOURCE(op, id) ps_io_map(&(op->io_mapper),  (uintptr_t)
> id##_PADDR, id##_SIZE, 0, PS_MEM_NORMAL)
>
>
>
> So you should just have to change the IMX6_IOMUXC_SIZE in imx6/mux.c to
> 0x4000 to map the four pages the mux should need.
>
>
>
> In the setup_iomux_enet function you could add a check to see if
> io_ops->mux_sys->priv == NULL, then use the RESOURCE macro. Else, just set
> base to equal to already mapped address.
>
>
>
> -    void *base = RESOURCE(&io_ops->io_mapper, IOMUXC);
>
> +    void *base;
>
> +
>
> +    if (io_ops->mux_sys_priv != NULL) {
>
> +        base = io_ops->mux_sys_priv;
>
> +    }
>
> +    else  {
>
> +        base = RESOURCE(&io_ops->io_mapper, IOMUXC);
>
> +    }
>
>
>
> I haven’t tested that, but it’s the logic that you should apply to your
> code.
>
>
>
> I’ll let Data61 respond to why the mux stuff was added.
>
>
>
> DornerWorks helped get the imx6 Ethernet drivers functional. We have an
> http server application that we host on our Github page that runs on seL4
> 7.0. You could give that a try as a reference.
>
>
>
> https://github.com/dornerworks/dw-camkes-manifests
>
>
>
> Let me know if you need any more help.
>
>
>
> Chris Guikema
>
>
>
> *From:* Devel [mailto:[email protected]] *On Behalf Of *Fabrizio
> Bertocci
> *Sent:* Monday, June 25, 2018 9:12 PM
> *To:* [email protected]
> *Subject:* [seL4] IOMUX on iMX6 conflict with libethdrivers
>
>
>
> Hi,
>
> I need your help in trying to understand what is the best way to implement
> a permanent fix I can push on the seL4 repository regarding the
> incompatibility issues between the libethdriver and MUX interface of the
> platsupport.
>
>
>
> This apply to the iMX6 ethernet driver. I'm not sure about other platforms.
>
>
>
> In short, the problem is that platsupport takes ownership of the entire
> MUX (maps the I/O) when the io_ops are initialized:
>
> Repo: seL4/seL4_libs
>
> File: libsel4platsupport/src/io.c
>
> Function: sel4platsupport_new_io_ops
>
>   ...
>
>   mux_sys_init(io_ops, get_mux_dependencies(), &io_ops->mux_sys);
>
>   ...
>
>
>
> The above call end up calling the platform-specific mux_sys_init that maps
> only the first 4Kb of IO space from address 0x020e0000 (the base address
> of the IOMUX controller - note: the IOMUX controller uses 16Kb of address
> space for its registers, not 4Kb!!!):
>
> Repo: seL4/util_libs
>
> File: libplatsupport/src/plat/imx6/mux.c
>
> Function: mux_sys_init
>
>   ...
>
>   MAP_IF_NULL(io_ops, IMX6_IOMUXC, _mux.iomuxc);
>
>   return imx6_mux_init_common(mux);
>
>
>
> The pointer "io_ops->mux_sys->priv" should point to the base address of
> the IOMUX of the SoC (in the virtual memory space of the calling process).
>
>
>
> The Ethernet driver unfortunately attempts to map the IOMUX again:
>
> Repo: seL4/util_libs
>
> File: libethdrivers/src/plat/imx6/uboot/mx6qsabrelite.c
>
> Function: setup_iomux_enet
>
>   ...
>
>   void *base = RESOURCE(&io_ops->io_mapper, IOMUXC);
>
>   ...
>
>   // Modify the IOMUX registers, then release the mapped IO:
>
>   ...
>
>   UNRESOURCE(&io_ops->io_mapper, IOMUXC, base);
>
>
>
> but using a larger size (the full 16Kb from the same base address of the
> IOMUX controller).
>
>
>
> So, the ethernet controller attempt to map the IO fails because it is
> already mapped, and nothing works.
>
>
>
> Right now in my project I've entirely commented out the initialization of
> the MUXC from the sel4platsupport_new_io_ops function.
>
>
>
> I understand that if the io_ops attempt to map the MUX (and leave it
> mapped) there must be a reason, unfortunately I fail to see it. The
> structure describing the MUXC register (struct imx6_iomuxc_regs, defined in
> libplatsupport/src/plat/imx6/mux.c) is private and not accessible outside
> that file, and the only two interface functions available
> (mux_feature_enable/mux_feature_disable) are not enough to be usable by
> the ethernet driver.
>
>
>
> The ethernet driver could also attempt to reuse the same mapped IOMUX
> (beside that the size of the mapped area is different and won't work
> anyway), but that will require using the 'priv' field of the
> io_ops->mux_sys (beside, even trying to map the whole 16Kb of the IOMUX and
> have the driver to reuse the same mapped address, for some unknown reasons
> it doesn't work).
>
>
>
> So, what is the right approach to fix this problem?
>
> Why the MUX subsystem maps some IO, never release it and keep it private
> for most of it?
>
> The IOMUX has been introduced somewhere between version 1.0 and 9.x... and
> it seems a half-baked job... Can we just comment it out if nobody is using
> it?
>
> Or if you have some ideas/suggestions on how to expand it in such a way
> the ethernet driver could use, please let me know. I'll be happy to
> implement it.
>
>
>
> Regards,
>
> Fabrizio
>
>
>
>
>
>
>
>
>
>
>
_______________________________________________
Devel mailing list
[email protected]
https://sel4.systems/lists/listinfo/devel

Reply via email to