Loading bootable software images onto the EMMC of PICO-IMX6 and PICO-IMX7 on PICO-PI

Difficulty Levels: Intermediate
Date added: June 20, 2018
Affected Products: PICO-IMX6 , PICO-PI

The easiest way to load software images onto the PICO SOM that include onboard EMMC on PICO-PI (or any other baseboard where an onboard SD card is not available or preferred) is to use this process.

The first phase is to boot the SOM into a special boot mode we call ‘serial downloader’ mode which allows you to download a boot image to the SOM over the USB OTG port. You download a boot image to the board called a USB OTG Loader. The sole purpose of this boot image is to make the onboard EMMC of the SOM available as a USB mass storage device to the host PC over USB OTG. The host PC can then write the image to the EMMC.

Download the required software

You can select a demo image from our FTP site. You can also load an image you’ve built yourself, for example with Yocto. Look for images without “installer” in the filename. As an aside, “Installer” images are another way to load software into EMMC but are only applicable to baseboards with microSD card slots such as PICO-DWARF, PICO-NYMPH, and PICO-HOBBIT.


Also, download the latest USB OTG Loader from our FTP site here and unpack it somewhere on your host PC. For the purposes of loading the EMMC, we can only support using this software on a Linux host at this time.


Step 1: Put the PICO-PI into serial download mode

PICO-PI has a block of 4 jumpers that are used to configure the boot mode of the board. For this, please reference the following article on our knowledgebase:


Plug the PICO-PI board into your hosts USB connection using the provided USB Type A to Type C cable.

Also, if you want to check out the serial console, you can attach a USB type A to microUSB cable to the debug console port and view/interact with it using a terminal emulator of your choice (PuTTY, minicom, picocom, etc.).

Step 2: Run the USB OTG Loader

The USB OTG loader is used to provide access read and write a SOM’s on-board EMMC from a host computer running Windows or Linux (caveat – see below). The way this tool works is to download a small Linux image to the SOM’s memory. The main job of this small Linux image is to export the EMMC of the SOM as a USB mass storage device (i.e. a flash drive).

Issues with Windows 7 Hosts

While you can use the USB OTG loader to download the correct image to the board, Windows 7 cannot be used to directly load the EMMC due to an incompatibility in the USB device driver. Windows 10 seems to be better behaved in this regard, but this article just discusses the use of Linux hosts for the purposes of loading the EMMC.

Using a Linux Host

On your Linux host, open a terminal and go to where you unpacked the USB OTG loader files. In my setup, I put these in my Downloads folder:

$ cd ~/Downloads/pico-imx6-imx6ul-imx7_otg-installer_{datecode}

Then run the loader as root, using the boot image appropriate for the SOM you are trying to load:


$ sudo linux/imx_usb pico-imx6q_bootbomb_{datecode}.imx

For PICO-IMX6 Dual Lite:

$ sudo linux/imx_usb pico-imx6dl_bootbomb_{datecode}.imx

For PICO-IMX6 Solo

$ sudo linux/imx_usb pico-imx6s_bootbomb_{datecode}.imx


$ sudo linux/imx_usb pico-imx7d_bootbomb_{datecode}.imx

When you run the loader, you should see message output like this from the program (note that the following is from a procedure involving PICO-IMX6Q):

$ sudo ./imx_usb ../pico-imx6q_bootbomb_20171031.imx
config file </usr/etc/imx-loader.d/imx_usb.conf>
vid=0x066f pid=0x3780 file_name=mx23_usb_work.conf
vid=0x15a2 pid=0x004f file_name=mx28_usb_work.conf
vid=0x15a2 pid=0x0052 file_name=mx50_usb_work.conf
vid=0x15a2 pid=0x0054 file_name=mx6_usb_work.conf
vid=0x15a2 pid=0x0061 file_name=mx6_usb_work.conf
vid=0x15a2 pid=0x0063 file_name=mx6_usb_work.conf
vid=0x15a2 pid=0x0071 file_name=mx6_usb_work.conf
vid=0x15a2 pid=0x007d file_name=mx6_usb_work.conf
vid=0x15a2 pid=0x0080 file_name=mx6_usb_work.conf
vid=0x1fc9 pid=0x0128 file_name=mx6_usb_work.conf
vid=0x15a2 pid=0x0076 file_name=mx7_usb_work.conf
vid=0x1fc9 pid=0x0126 file_name=mx7ulp_usb_work.conf
vid=0x15a2 pid=0x0041 file_name=mx51_usb_work.conf
vid=0x15a2 pid=0x004e file_name=mx53_usb_work.conf
vid=0x15a2 pid=0x006a file_name=vybrid_usb_work.conf
vid=0x066f pid=0x37ff file_name=linux_gadget.conf
vid=0x1b67 pid=0x4fff file_name=mx6_usb_sdp_spl.conf
vid=0x0525 pid=0xb4a4 file_name=mx6_usb_sdp_spl.conf
vid=0x1fc9 pid=0x012b file_name=mx8mq_usb_work.conf
config file </usr/etc/imx-loader.d/mx6_usb_work.conf>
parse /usr/etc/imx-loader.d/mx6_usb_work.conf
15a2:0054(mx6_qsb) bConfigurationValue =1
Interface 0 claimed
HAB security state: development mode (0x56787856)
== work item
filename ../pico-imx6q_bootbomb_20171031.imx
load_size 0 bytes
load_addr 0x00000000
dcd 1
clear_dcd 0
plug 1
jump_mode 2
jump_addr 0x00000000
== end work item
Setting boot_data_ptr to 0
main dcd length 238
sub dcd length 234
loading binary file(../pico-imx6q_bootbomb_20171031.imx) to 177ff400, skip=0, fsize=25ac00 type=aa
<<<2468864, 2468864 bytes>>>
succeeded (status 0x88888888)
jumping to 0x177ff400

Once this is done, you should see several USB drives connect to your host. If you are viewing the serial console messages using a terminal emulator, you should some Linux boot messages appear.

Step 3) Write the image to EMMC

Now it is time to write the images to EMMC of the board. For this, we have to know the block device in Linux that represents the attached EMMC. For this we use the lsblk command.

$ lsblk
sda 8:0 0 465.8G 0 disk
├─sda1 8:1 0 190M 0 part /boot/efi
├─sda2 8:2 0 244M 0 part /boot
└─sda3 8:3 0 465.3G 0 part
├─leo-root 252:0 0 459.4G 0 lvm /
└─leo-swap_1 252:1 0 6G 0 lvm [SWAP]
sdb 8:16 1 3.5G 0 disk
├─sdb1 8:17 1 16M 0 part
├─sdb2 8:18 1 16M 0 part
├─sdb3 8:19 1 1K 0 part
├─sdb4 8:20 1 1.6G 0 part
├─sdb5 8:21 1 1024M 0 part
├─sdb6 8:22 1 512M 0 part
├─sdb7 8:23 1 8M 0 part
├─sdb8 8:24 1 6M 0 part
└─sdb9 8:25 1 2M 0 part
sr0 11:0 1 1024M 0 rom

Look for a block device which corresponds to the removable devices (data in ‘RM’ column is 1). You can also correlate this to messages from the dmesg log:

$ dmesg
[16660625.186236] usb 3-3: Product: HobbitBoard
[16660625.186251] usb 3-3: Manufacturer: TechNexion
[16660625.193126] usb-storage 3-3:1.0: USB Mass Storage device detected
[16660625.193405] scsi host12: usb-storage 3-3:1.0
[16660626.192470] scsi 12:0:0:0: Direct-Access Linux File-Stor Gadget 0401 PQ: 0 ANSI: 2
[16660626.193163] sd 12:0:0:0: Attached scsi generic sg2 type 0
[16660626.193466] sd 12:0:0:0: [sdb] 7405568 512-byte logical blocks: (3.79 GB/3.53 GiB)
[16660626.193691] sd 12:0:0:0: [sdb] Write Protect is off
[16660626.193711] sd 12:0:0:0: [sdb] Mode Sense: 0f 00 00 00
[16660626.193941] sd 12:0:0:0: [sdb] Write cache: enabled, read cache: enabled, doesn't support DPO or FUA
[16660626.211516] sdb: sdb1 sdb2 sdb3 < sdb5 sdb6 sdb7 sdb8 sdb9 > sdb4
[16660626.344976] sd 12:0:0:0: [sdb] Attached SCSI removable disk

From the above, in this example, you can be sure that /dev/sdb corresponds to the correct drive. You do not want to make a mistake here and accidentally overwrite your host’s main drive data. That would be bad.

If your host automatically mounts any of the attached drives, you will need to unmount them. You can easily tell if any are mounted using the ‘mount’ command.

Now you are ready to write the image to EMMC. For this we will use the ‘dd’ command. On your host, use the command:

$ sudo dd if={path to image file} of={path to block device of exported EMMC} bs=1M

In this example, we are going to write an Android image to a block device as above (/dev/sdb):

$ sudo dd if=pico-imx6_pico-pi_android-7.1.1_lcd-800x480_20171229 of=/dev/sdb bs=1M

The amount of time that this command takes to run depends on the size of the image you are writing. When completed, it should provide you with some messages that tell you how many blocks were written:

$ sudo dd if=pico-imx6_pico-pi_android-7.1.1_lcd-800x480_20171229 of=/dev/sdb bs=1M
3501+0 records in
3501+0 records out
3671064576 bytes (3.7 GB, 3.4 GiB) copied, 240.962 s, 15.2 MB/s

You can now power off the unit by unplugging the USB Type C cable, and then change the boot configuration jumpers to boot from the onboard EMMC.

If you’ve done everything right, when you power on the board, and the image you loaded should now run.

Stay up to date with all the latest TechNexion news...

Sign-up for our Newsletter