apache / apache/arrow

[C++][Gandiva] Out-of-bounds read in evaluate_return_char_length with malformed pad fill text

Open
#50,592 0 comments 0 reactions 1 assignee Claimed by @Arawoof06 View on GitHub
Dominant language
C++
Stars
17.1k
Forks
4.3k
Avg merge
3d 13h
Merged PRs (30d)
88

Description

### Describe the bug, including details regarding any error messages, version, and platform.

`evaluate_return_char_length` in `cpp/src/gandiva/precompiled/string_ops.cc` sizes the `lpad`/`rpad` output when the fill text is more than one byte wide. It counts the fill glyphs with `utf8_length_ignore_invalid`, which charges an invalid or truncated glyph a single byte, then walks the fill text a second time stepping by the width `utf8_char_length` declares, with no bound on `fill_index`.

The two walks disagree on malformed fill text. For the fill `{0xE0, 'a', 'a'}` the count is 3 glyphs, so the partial-fill loop runs up to twice, while its first step consumes all 3 bytes; the next `fill_text[fill_index]` read is past the end of the fill buffer.

Reachable from `lpad(text, n, fill)` / `rpad(text, n, fill)` where `fill` comes from untrusted string data. With a verbatim copy of the helper under AddressSanitizer and the fill above in an exactly-sized heap buffer, `lpad('ab', 7, fill)` gives:

```
ERROR: AddressSanitizer: heap-buffer-overflow
READ of size 1 ...
0 bytes after 3-byte region
```

Built from `main` (154962c).

### Component(s)

C++ - Gandiva

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.