Communicate with an FPGA through the EIM (torizon)

I am trying to migrate an apalis IMX6Q board which used WinCE on torizon.

The biggest difficulty I encounter is using EIM to communicate with a fpga.

I used some code and tutorials provided by Torzdex and the community to set it up on WinCE but I don’t find the same content and documentation for torizon.

What I understood is that I must add an overlay to my device tree to make the system activate the EIM. But I don’t know which overlay uses (I think a such overlay already exist, right?). After that do I have to write a driver or something else?

Could you tell me if I try to use the best method? If not, what should I do?
Does it exist some documentation or examples on this subject?

Best regards.

Greetings @rfonck,

You are correct that you’ll need to activate the EIM subsystem in the device tree. We do not have a pre-existing overlay to do this. However it should be simple.

As seen here in the device tree: imx6qdl-apalis.dtsi « dts « boot « arm « arch - linux-toradex.git - Linux kernel for Apalis, Colibri and Verdin modules

The EIM subsystem, denoted by the weim node is disabled. We just need to set this to “okay”. So an overlay like this should do:

/dts-v1/;
/plugin/;

/ {
        compatible = "toradex,apalis_imx6q";
};

&weim {
	status = "okay";
};

As for interacting with the interface the suggested way would be to create a memory map to the EIM bus and do write/read operations from there. Such an example of an implementation can be seen in this thread here: Accessing External Memory Bus (EIM) on iMX6 via memory map - Technical Support - Toradex Community

Best Regards,
Jeremias

Thank you for your reply.

I used the following configuration (that I adapted from examples I found in different websites).

/dts-v1/;
/plugin/;

/ {
	compatible = "toradex,apalis_imx6q";
};


&ecspi1 {
	status = "disabled";
};

&can2 {
	status = "disabled";
};


&i2c3 {
	status = "disabled";
};

&uart3 {
	status = "disabled";
};

&usbh1 {
	status = "disabled";
};




&weim {
     status = "okay";
	fsl,weim-cs-gpr = <&gpr>;
	/* weim memory map: 32MB on CS0, 32MB on CS1, 32MB on CS2, 32MB on CS3 */
	ranges = <0 0 0x08000000 0x02000000
	          1 0 0x0a000000 0x02000000
	          2 0 0x0c000000 0x02000000
	          3 0 0x0e000000 0x02000000>;
	          
    /* SRAM on CS0 */
	fpga@0,0 {
		compatible = "altr,socfpga-fpga-mgr";
		reg = <0 0 0x00010000>;
		#address-cells = <1>;
		#size-cells = <1>;
		bank-width = <2>;
        fsl,weim-cs-timing = <0x00610001 0x00000000 0x0E022000
                 0x00000000 0x1c092480 0x00000000>;
	};
     

};

I think the interface has been activated but I observe incoherent signals on the fpga side of my installation.

Indeed I observe chip select signal changing when I read memory on the adress : 0x08000000. But the signal corresponding to the adress is not coherent at all. I mean that by reading on the adresses 0x08000000 and 0x08000012 the signal corresponding to the adress don’t change and I don’t see data changing when a perform a write operation on the sames adresses.

Is it possible that de “compatible” value I set is not adapted ? I found it on bindings about imx6 but I don’t really know what which impact it can have on the operation.

otherwise found an examble of what I must setup (accessing fpga through the eim) working on windows and by analysing the code I understood thaat the clock settings must be modified. How can I set it up on torizon and can it causes the actual issue I’m confronted with ?

have you an idea of what other problem can cases this malfunction ?

Best regards

I have forgotten a fairly important part of activating the EIM interface. Not only do you have to set the status to okay but you need to also reassign all the pins to the WEIM node in the device tree so it actually has the correct pinmuxings. On Colibri i.MX6 you don’t have to do this but for Apalis i.MX6 you do.

Most of the EIM pins in the device tree are default assigned to other interfaces. Meaning you’ll need to do quite a bit of modifications. Namely disable any interface that is using an EIM pin, then reassign it to the weim node.

There’s another thread here in the community where another customer did just that: Apalis IMX6 EIM access - Technical Support - Toradex Community

Fortunately they shared their device tree source with their changes. Please note that it appears these changes were done on an older kernel/device tree but not much should be different in terms of the EIM related things.

Best Regards,
Jeremias

Thank you for your reply.

My eim interface is now working with a custom driver (based on the classic imx6 weim driver) who configure directly some specific values in registers as CCM_CSCMR1 (I didn’t found any other way to change these values).

I can access values from my FPGA memory using tools like dedmem2 on /dev/mem.

I’m now trying to make the access to these values as simple as possible in order to allow an .net application reading it.

So here are my questions:
Is it possible to set un a /dev/fpga device or something similar and directly read on it from the user space ?
How can I access my fpga memory without having root priviledges from the user space ?
Does-it exist sram drivers that can perform that ?

Best regards,
rfonck

Glad you were able to get something going!

As for accessing things without root/sudo privileges, I have an idea. So your .net application will run in a container. Containers have a feature to pass cgroups to allow certain privileges and access to various interfaces.

More details here: Torizon Best Practices Guide | Toradex Developer Center

I believe there’s a cgroup for /dev/mem/. Perhaps if you create a container with the proper cgroup access then you can access this without sudo/root privileges, at least in that specific container.

Best Regards,
Jeremias