Security
Headlines
HeadlinesLatestCVEs

Headline

CVE-2023-23305: garmin-ciq-app-research/CVE-2023-23305.md at main · anvilsecure/garmin-ciq-app-research

The GarminOS TVM component in CIQ API version 1.0.0 through 4.1.7 is vulnerable to various buffer overflows when loading binary resources. A malicious application embedding specially crafted resources could hijack the execution of the device’s firmware.

CVE
#vulnerability#git#buffer_overflow

Buffer Overflows in Font Resources

It is possible to embed fonts to a PRG file by specifying them in the font.xml resource file. The fonts can later be retrieved using WatchUi.loadResource(Rez.Fonts.myFont); in the application.

The firmware supports two types of font:

  • A legacy non-unicode font format that is no longer generated when compiling a PRG application but still supported inside the firmware
  • A unicode font format

During compilation, the original font files are stored alongside a custom header that defines several properties. For instance, for non-unicode font, the following header is prefixed to the font data:

Index

Size in bytes

Name

Value

0x00

4

sentinel

0x0000f23b

0x04

4

height

0x08

4

glyph count

0x0c

4

min

0x10

2

data size

0x12

3 * glyph count

glyph table buffer

n

4

glyph sentinel

n + 4

1 * data size

extra data buffer

When computing the buffers that will hold the font data, integer overflows can occur resulting in an allocated buffer being smaller than expected. When the font data is then copied, the firmware writes out of bounds.

e_tvm_error _tvm_app_load_resource(s_tvm_ctx *ctx,int fd,uint app_type,s_tvm_object *resource,s_tvm_object *out) { // […] // Anvil: Read header from the font resource eVar1 = file_read_4bytes(fd,&font_height); psVar2 = (uint)eVar1; if (psVar2 != 0x0) goto LAB_047ac2c6; eVar1 = file_read_4bytes(fd,(uint *)&font_glyph_count); // […] if ((psVar2 != (s_tvm_ctx *)0x0) || (psVar2 = file_read_2bytes?(fd,&font_data_size), psVar2 != 0x0)) goto LAB_047ac2c6; // Anvil: Computing the size of the buffer to allocate. // Anvil: This can overflow, resulting in the size being smaller than expected size_glyph_table_buffer = (font_data_size & 0xffff) + (int)font_glyph_count * 4 + 0x34; // […] // Anvil: Allocating the buffer, which could be smaller than expected tvm_mem_alloc(ctx,size_glyph_table_buffer,0,&glyph_table); // […] // Anvil: Read `font_glyph_count` bytes from the font resource and copy them to the buffer. Since the buffer is smaller than expected, it writes out-of-bounds. for (i_glyph = (s_tvm_ctx *)psVar2; i_glyph < font_glyph_count; i_glyph = (s_tvm_ctx *)((int)&i_glyph->unknown-? + 1)) { if ((s_tvm_ctx *)psVar2 == (s_tvm_ctx *)0x0) { p_current_glyph = &p_glyph_table_data->glyphs_buffer + (int)i_glyph; while( true ) { // Anvil: Out-of-bound write psVar2 = file_read_2bytes(fd,p_current_glyph); if ((s_tvm_ctx *)psVar2 != (s_tvm_ctx *)0x0) break; iVar2 = file_read-?(fd,&sentinel,1); if (iVar2 != 1) { // […] } // Anvil: Out-of-bound write *(undefined *)((int)p_current_glyph + 3) = sentinel._0_1_; i_glyph = (s_tvm_ctx *)((int)&i_glyph->unknown-? + 1); p_current_glyph = p_current_glyph + 1; if (font_glyph_count <= i_glyph) goto LAB_047ac98a; } } } // […] }

The same vulnerable pattern can be seen for unicode fonts. Although the header is different, the firmware computes the size of the buffer to allocate based on the values specified in the header, which can overflow and result in an allocated buffer smaller than expected.

It is possible to trigger the crash by compiling a PRG application and editing its font resource to change the header values with:

  • Glyph count: 0x4000001A
  • Font data size: 0x108

The computed buffer size will be: (0x108 & 0xffff) + 0x4000001A * 4 + 0x34 = 0x1000001a4. Since the registers can only hold 32-bit values, it gets truncated to 0x1000001a4 & 0xffffffff = 0x1a4. The firmware will then attempt to copy 0x4000001A glyphs to a buffer of 0x1a4 bytes.

The following proof-of-concept triggers the vulnerability: https://github.com/anvilsecure/garmin-ciq-app-research/blob/main/poc/GRMN-06.prg

CVE: Latest News

CVE-2023-50976: Transactions API Authorization by oleiman · Pull Request #14969 · redpanda-data/redpanda
CVE-2023-6905
CVE-2023-6903
CVE-2023-6904
CVE-2023-3907