14 Replies Latest reply on Jul 7, 2016 5:01 AM by dcesn367

    Edison FW SFI Tables




      I'm interested on doing one project and do it right form the very beginning. For that I need new hardware I'm planning to add and so needs to be added to the SFI Tables. I have seen that the IFWI is in the edison-src tar|zip is downloaded to build the BSP, so it is not being compiled. So my question is: can I have access to the IFWI or SFI tables?, is there a way or tool to edit it?, or what are the resources intel provides for such efforts?


      Edit the FW binaries is not an option because it is breaking the system, and I don't like to keep hacking the kernel in case it gets to a final product, so please help provide what would be the best option.


      Thank you in advance




        • 1. Re: Edison FW SFI Tables

          Hi icpda,


          I will investigate on this and let you know if I find some useful information.




          • 2. Re: Edison FW SFI Tables

            I am looking for some help in this area too.  I have never worked with SFI tables before and it took me a while to discover adding entries to the the board.c file does not do any good if the device is not in the sfi table. I have been able to find  /sys/firmware/sfi/tables/ , but have not been able to figure out where they are located in the yaocto (or linux kernel?) builds.. binary or source.  Any help would be appreciated



            • 3. Re: Edison FW SFI Tables



              The new firmware needs to be added to the custom build image recipe. What kind of hardware are you trying to add? Can you give an example of the firmware that needs to be added?




              • 4. Re: Edison FW SFI Tables



                I am trying to add the ks8851 (spi to ethernet) on SPI5 FS0.  As far as I can tell to do this properly I need to

                • add the ks8851 to the SFI
                • remove ads7955 from the the SFI (uses SPI5 FS0)
                • add the KS8851 to board.c , and the appropriate platform_ files (similar to the platform_spidev.c/.h)
                • 5. Re: Edison FW SFI Tables

                  mweal, the board.c file is not enough, how it works is that after parsing SFI tables from IFWI it start finding the different type of devices in the tables, then it looks in the array of IDs in board.c and call it's platform_data functions if available. For example spidev, in the tables there is a spidev, then after parsing the table look at the ids for "spidev" string and make the calls to platform_spidev to set the platform data, but that is not the actual device, the devices is registered by "processing the SFI tables. I don't have the source right know to point you to the actual files but that was my understanding when looking at it, hope that helps.


                  As you see in the sysfs path, the sfi tables are in firmware, but just processed in kernel. So we would need either access to the FW or a method to edit such tables.




                  • 6. Re: Edison FW SFI Tables

                    Hi Sergio,


                    Instead of use a new FW is it possible to edit the SFI tables somehow or maybe parse and stitch the new SFI tables?, maybe a tool for that?


                    What I am currently doing is to add an SPI display to spi 5.1, so I have to remove current spidev from the id table in board.c in order to avoid any conflict du to the use of CS1. The device registration is done creating a new platform device file, but I would like to move that to SFI table.


                    This is only one device of many I would like to add, so in order to avoid create different platform devices I would like to have it all in the FW.


                    Also in future I am thinking to use a common kernel for platform with different components connected, so the only variant would be the FW with different SFI tables.



                    Any doubt please let me know





                    • 7. Re: Edison FW SFI Tables



                      Thanks for the feedback.  I figured out most of what you described.  The part I was missing was the SFI table being outside of the kernel. So if I understand correctly, the SFI tables are in the ./device-software/utils/flash/ifwi/edison/ binary files which are provided without source code or tools. So the only way to change the SFI tables right now is to edit the raw binary files.


                      After looking at the code, I think I'll disable the conflicting devices by deleting them  in board.c,  then register my own devices in a kernel module as i need them (I prefer to avoid changes where possible to the kernel proper).

                      • 8. Re: Edison FW SFI Tables

                        Hi icpda,


                        The only suggestion I could give you is to try and find in the BSP files any guide as to where to find or have access to the SFI tables, because unfortunately there are no official Intel tools to edit the SFI tables. Another option would be to find a third party tool you can find a way to access these tables.




                        • 9. Re: Edison FW SFI Tables

                          Hi Sergio,


                          I have check the BSP guide but it is focus on the kernel and poky filesystem, and the SFI Tables are in the firmware binaries that comes in the edison-src tar provided by intel. You can look at the binaries here: ./device-software/utils/flash/ifwi/edison

                          If you open those files with an hex editor you can see there the devices from SFI Tables that later are going to be pass to kernel to be register. It is not possible to edit the hex files because it is going to corrupt the binary, so I would expect intel to provide either the FW or a tool to add/edit the SFI Tables to avoid kernel hacking.

                          Also I've been looking for the FW source but seems it is not yet open, any idea if it is going to be provided to the public and when?

                          Thank you in advance



                          • 10. Re: Edison FW SFI Tables



                            Unfortunately, a tool to edit SFI tables is not available.




                            • 11. Re: Edison FW SFI Tables

                              To summarise, in the need of add new devices the SFI Tables is not an option because there isn't any available tool so far to edit or modify such tables and seems like IFWI source is not going to be available to user. So the best option is to do all the hacks in kernel and add the devices there and remove possible conflicting devices from board.c file.

                              • 12. Re: Edison FW SFI Tables

                                Hi All,


                                I was able to register a EN28J60 adapter to SPI5.0 by a hack.


                                However, the device is still not working, I am yet to debug whether its my HW or some issues on the device diver itself.

                                I am still waiting for my logic analyser to come to further debug. I just want to share this and maybe someone chip in.


                                My concept was to remove any SFI table related to ads7955 in the Kernel source.

                                Once ads7955 is not included during initialisation that is done in intel_mid_sfi file. Then I created a sfi_device_table_entry and devs_id for my device. Created a function to initialise it and call it after default tables are initialised.


                                I am not sure if what I'm doing is making since, I am newbie in Linux Kernel and I am HW guy. If someone has a known working HW connected to SPI5.0, maybe you can test it out.





                                Some snip of dmesg:


                                root@edison:~# dmesg | grep -i spi

                                [    0.191957] SPI bus=5, name=          spidev, irq=0x 0, max_freq=25000000, cs=1

                                [    0.192236] SPI bus=5, name=        enc28j60, irq=0x 0, max_freq=12000000, cs=0

                                [    1.988458] intel_mid_ssp_spi_unified 0000:00:07.0: found PCI SSP controller (ID: 8086h:1194h cfg: 0dh)

                                [    1.989421] intel_mid_ssp_spi_unified 0000:00:07.0: register with SPI framework (bus spi3)

                                [    1.989584] intel_mid_ssp_spi_unified 0000:00:07.0: master is unqueued, this is deprecated

                                [    1.989614] intel_mid_ssp_spi_unified 0000:00:07.0: Unbalanced pm_runtime_enable!

                                [    1.995826] intel_mid_ssp_spi_unified 0000:00:07.1: found PCI SSP controller (ID: 8086h:1194h cfg: 15h)

                                [    1.996705] intel_mid_ssp_spi_unified 0000:00:07.1: register with SPI framework (bus spi5)

                                [    1.996868] intel_mid_ssp_spi_unified 0000:00:07.1: master is unqueued, this is deprecated

                                [    1.997597] intel_mid_ssp_spi_unified 0000:00:07.1: Unbalanced pm_runtime_enable!

                                [    2.006144] intel_mid_ssp_spi_unified 0000:00:07.2: found PCI SSP controller (ID: 8086h:1194h cfg: 19h)

                                [    2.006976] intel_mid_ssp_spi_unified 0000:00:07.2: register with SPI framework (bus spi6)

                                [    2.007151] intel_mid_ssp_spi_unified 0000:00:07.2: master is unqueued, this is deprecated

                                [    2.007180] intel_mid_ssp_spi_unified 0000:00:07.2: Unbalanced pm_runtime_enable!

                                [    6.736889] enc28j60 spi5.0: enc28j60 Ethernet driver 1.01 loaded

                                [    6.817863] enc28j60 spi5.0: enc28j60 chip not found

                                [    6.817927] enc28j60: probe of spi5.0 failed with error -5





                                So here are the steps I made:

                                1. Under board.c, I commented ads7955 entry. This is to remove it from the SFI table.


                                        /* SPI devices */

                                        {"spidev", SFI_DEV_TYPE_SPI, 0, &spidev_platform_data, NULL},

                                //      {"ads7955", SFI_DEV_TYPE_SPI, 0, &ads7955_platform_data, NULL},

                                        {"bma023", SFI_DEV_TYPE_I2C, 1, &no_platform_data, NULL},

                                2. Under intel_mid_sfi.c, I did the ff:

                                a. add header to platform_enc28j60.h. This header file is a copy of the platform_ads7955.h, I replaced all "ads7955 to enc28j60"


                                #include "./device_libs/platform_enc28j60.h"

                                b. create a sfi_device_table_entry and devs_id for enc28j60. Then intialise it.


                                static struct sfi_device_table_entry sfi_enc28j60_table_entry;

                                static struct devs_id enc28j60_devs_id;




                                static void init_enc28j60_spi(void)


                                        sfi_enc28j60_table_entry.type = SFI_DEV_TYPE_SPI;

                                        sfi_enc28j60_table_entry.host_num = 5;

                                        sfi_enc28j60_table_entry.addr = 0;

                                        sfi_enc28j60_table_entry.max_freq = 12000000;

                                        sfi_enc28j60_table_entry.irq = 0xff;

                                        strcpy(sfi_enc28j60_table_entry.name, "enc28j60");


                                        strcpy(enc28j60_devs_id.name, "enc28j60");

                                        enc28j60_devs_id.type = SFI_DEV_TYPE_SPI;

                                        enc28j60_devs_id.delay = 0;

                                        enc28j60_devs_id.get_platform_data = &enc28j60_platform_data;

                                        enc28j60_devs_id.device_handler = NULL;


                                        sfi_handle_spi_dev(&sfi_enc28j60_table_entry, &enc28j60_devs_id);




                                c. call the above function under "intel_mid_platform_init" function.


                                static int __init intel_mid_platform_init(void)


                                        /* Get SFI OEMB Layout */

                                        sfi_table_parse(SFI_SIG_OEMB, NULL, NULL, sfi_parse_oemb);

                                        sfi_table_parse(SFI_SIG_GPIO, NULL, NULL, sfi_parse_gpio);

                                        sfi_table_parse(SFI_SIG_DEVS, NULL, NULL, sfi_parse_devs);




                                        return 0;


                                3. Create platform_enc28j60.c and platform_enc28j60.h in device_libs folder. I just copied the platform_ads7955.c and .h and replace ads7955 with enc28j60.

                                4. modify Make file in device_libs folder. Remove ads7955 statement and replace it with enc28j60.


                                # SPI Devices

                                obj-$(subst m,y,$(CONFIG_SERIAL_MRST_MAX3110)) += platform_max3111.o

                                obj-$(subst m,y,$(CONFIG_SPI_SPIDEV)) += platform_spidev.o

                                obj-$(subst m,y,$(CONFIG_ENC28J60)) += platform_enc28j60.o

                                5. Add, commit and generate patch in git.


                                6. Copy patch to meta-intel-edison/meta-intel-edison-bsp/recipes-kernel/linux/files/

                                7. Modify linux-yocto_3.10.bbappend to add your patch


                                SRC_URI += "file://defconfig"

                                SRC_URI += "file://upstream_to_edison.patch"

                                SRC_URI += "file://0001-enc28j60.patch"

                                8. Lastly bitbake edison-image.


                                • 13. Re: Edison FW SFI Tables

                                  Thank you jbayalas, I was able to modify your hack and get spidev5.0 working

                                  • 14. Re: Edison FW SFI Tables

                                    robbaltzer do you mind sharing your patch? You got it working in the sense that ENC28J60 was working?