HDMI and the BeagleBone Black Multimedia Environment

HDMI in the Linux Kernel

Inside the BeagleBone Black's Linux kernel, the Texas Instruments LCD controller (TILCDC) driver provides video framebuffer functionality. This module is responsible for controlling the data and control signals that are placed on the processor's LCD signal pins. The source code files for TILCDC are located inside the drivers/gpu/drm/tilcdc subdirectory of the kernel.

Like any Linux framebuffer module, the TILCDC driver also provides an interface file within the /dev directory (usually /dev/fb0) that userspace applications use to interface with kernel space framebuffer functionality. This interface file handles the configuration and maintenance of a linear memory buffer that represents the video data that will eventually be rendered on the display. Userspace applications open and write to the /dev/fb0 interface file to place data within this memory buffer. Every time the display is refreshed, the data from the memory buffer is examined and sent to the display via the LCD pins. This approach lets userspace applications directly manipulate the graphics shown on the display.

Both the audio CODEC driver and HDMI framer control driver are implemented within the tda998x kernel module. The two source files for this module, tda998x_drv.c and tda998x_audio_drv.c, are located in the drivers/drm/gpu/i2c subdirectory of the kernel source. The audio CODEC portion of the module implements the nxptda audio CODEC, which has an ALSA userspace friendly name of nxp-hdmi-hifi. This audio CODEC is a dummy ALSA driver that contains just enough code (less than 100 lines) to create the appropriate interface files within /dev for userspace applications to use the audio CODEC as an ALSA device.

Any userspace audio data written to this ALSA device is passed into the McASP [3] driver (sound/soc/davinci/dacinci-mcasp.c), and the McASP driver places that audio data onto the processor's McASP0 signals in the I2S protocol.

This I2S data stream is understood by the HDMI framer as is, so there is no need for a "smart" software audio CODEC to change or convert the format of the data. The HDMI framer will use an internal audio CODEC to perform any necessary conversion of the audio data format before transmitting it.

The control driver for the HDMI framer implements the I2C communications that directly control the behavior of the TDA19988 HDMI framer chip. This driver communicates the specific format of the video data (resolution, refresh rate, etc.) and audio data (sampling rate, same size, etc.) to the HDMI framer chip so that the HDMI framer knows exactly what data to expect from the McASP0 and LCD pins. This driver also fetches the EDID block from the display and tells the HDMI framer chip when to start and stop transmitting audio and video data to the display.

Configuring HDMI Audio and Video

A common problem experienced by new BeagleBone Black users is not receiving any audio output when using the on-board HDMI. The video works, but no ALSA audio device is available for userspace applications to open and use. Why?

The Consumer Electronics Association (CEA) has established a standard (CEA-861) that specifies a set of video modes that support the transfer of audio within the HDMI data stream. Each CEA mode is a pair made of a video resolution (in pixels) and a screen refresh rate (in hertz). Table 1 lists several of the most common CEA modes; a total of 64 CEA modes are listed in the kernel.

Tabelle 1

Common CEA Modes


Refresh Rate (Hz)















With the exception of the 640x480 resolution, all of the CEA modes describe wide-screen displays. Unless the framebuffer is configured to use one of these CEA modes, the audio subsystem in the HDMI framer driver will not initialize and no audio data will be sent to the display. It is counter-intuitive, but audio over HDMI won't be available if you are not using the proper video resolution!

The default behavior of the kernel's DRM subsystem is to pick the highest-resolution CEA mode possible when initializing the kernel framebuffer driver. The DRM subsystem will first check if an EDID block for the display is available. If it is not, the framebuffer will default to a resolution of 1024x768 at 16 BPP. This behavior is hard-coded in the function drm_fb_helper_single_fb_probe() in drm_fb_helper.c. Unfortunately, 1024x768 is not a valid CEA mode. This has the side effect of disabling audio if your BeagleBone Black is not connected to a display when you power the board on, or if you are using a video adapter cable that blocks the transmission of the EDID block.

If the EDID block is available, the video modes listed in the block are compared against the list of CEA modes located in the edid_cea_modes[] array in drm_edid_modes.h. If at least one CEA mode is listed in the EDID block, HDMI audio is enabled, and the listed CEA mode with the highest resolution is picked for framebuffer initialization. If no CEA modes are available, HDMI audio is disabled and the highest available non-CEA resolution from the block is used for framebuffer initialization.

You might find it necessary to request the use of a particular video mode. For example, if you are turning the BeagleBone Black into a multimedia appliance that will be attached to an HDMI television, it makes sense to request a particular video mode that supports audio. Requesting a particular mode also allows you to design graphical GUIs around a specific, fixed resolution without any worry about whether the DRM subsystem will select a different, higher resolution that happens to be reported in the EDID block.

The kernel= command line option is used to request a specific resolution for the video framebuffer. Figure 3 shows the different pieces of information that are specified using this option. For the HDMI output of the BeagleBone Black, the HDMI-A-1 connector is the ultimate destination of data placed into the kernel framebuffer. The video resolution and refresh rate are those of the requested video mode. Note that this option is a request. It will not force a particular mode if that mode is not available. Even if a particular requested mode is valid for a display, the default 1024x768 resolution will always be used if no EDID block is received from the display.

Figure 3: The four sections of the "video=" kernel command line option: the option itself (video=), the type of video connector associated with the video, the video resolution (in pixels), and the screen refresh rate (in Hz).

The U-Boot bootloader for the BeagleBone Black uses the uEnv.txt text file (located in a FAT filesystem boot partition) to specify the command line options that are passed to the kernel. The contents of the uEnv.txt file will vary depending upon which distribution image is used to boot the system, but any version of the file will use the environmental variable optargs to specify any kernel command-line options. The video= option is added to the optargs variable to request a particular video mode.

As an example, consider a recent version of the Angstrom Linux distribution that is installed inside the BeagleBone Black's eMMC [4]. Boot the board without a microSD card inserted (to boot into Angstrom) and without any display plugged in to the microHDMI port. Once the system is booted, log into the board:

beaglebone login: root
Last login: Sat Jan  1 00:00:30 UTC 2000 on ttyO0

Then, look at the current framebuffer resolution using the fbset command:

root@beaglebone:~# fbset
mode 1024x768-0

This output shows the default 1024x768 resolution that is set by DRM. If you plug a display into the microHDMI port, reboot, and then rerun fbset, you will see that the resolution is now set to the best resolution that DRM could find for the display per the information obtained from the display's EDID block.

To always request the framebuffer resolution to a specific video mode in Angstrom (e.g., the CEA mode of 720x480 with a 60Hz refresh rate), you must modify the uEnv.txt file. Angstrom does not mount its boot partition by default, but you can mount it using the following command:

root@beaglebone:~# mount /dev/mmcblk0p1 /mnt/card

Once the mount completes, the boot partition is mounted at the mountpoint /mnt/card. You will find the uEnv.txt file in /mnt/card/uEnv.txt. In most Angstrom images, only a single line is in the file:

optargs=quiet drm.debug=7

Using any text editor, modify this line to add the necessary video= option:

optargs=quiet drm.debug=7 video=HDMI-A-1:720x480@60

Once you are finished, save the file and unmount the partition:

root@beaglebone:~# umount /mnt/card

Reboot the board and then once again log in and check the resolution via fbset:

root@beaglebone:~# fbset
mode 720x480-0

The best video mode to request in uEnv.txt depends on how you intend to use the BeagleBone Black. When creating a multimedia appliance that is designed to use the HDMI cape to interface with an HDMI television, request a specific CEA mode.

Keep in mind that lower wide-screen resolutions (such as 720x480) are supported by more displays than higher resolutions. This is because older displays only support the lower resolutions, and newer displays are backwards-compatible with lower resolutions to support older set-top boxes, video game consoles, and other hardware. Selecting a higher resolution provides more pixels, but it might prevent the appliance from working with older HDMI televisions.

When using the HDMI cape to target a DVI monitor without any audio, a standard computer resolution (800x600, 1024x768, etc.) is a good choice for a requested resolution. Examples of appliance systems using such a design are kiosks, ATMs, or other simple devices that use commodity displays plugged directly into the HDMI cape's microHDMI connector. When using the BeagleBone Black as a desktop computer, it is normally best to not request a particular video mode and just let the DRM subsystem select the highest available resolution (as reported via the EDID block).

Buy this article as PDF

Express-Checkout as PDF

Pages: 6

Price $2.95
(incl. VAT)

Buy Raspberry Pi Geek

Get it on Google Play

US / Canada

Get it on Google Play

UK / Australia

Related content

  • Capemgr keeps track of the BeagleBone Black's expansion boards, known as capes

    The BeagleBone Black offers many interfacing options, but how can you control which ones are used and how they are configured? We take a detailed look at the Black's Capemgr subsystem and the device tree data structure it manages.

  • New Products

    What's new in the SBC, IoT, and maker realm.

  • Snapshot

    The remarkable Raspberry Pi has spawned a myriad of supporting projects – Android apps, program libraries, specialized Linux distributions, and an assortment of hardware accessories. The rapid changes within these projects is testament to the excitement and enthusiasm that developers around the world have given to the Raspberry Pi.

  • The Pi Wire

    News on Eben Upton’s CBE, a Rasp Pi IoT contest, the BeagleBone Green Wireless, and more!

  • The Pi Wire