Arm NN TFLite RESIZE_BILINEAR one-element size heap over-read
Status: reproduced with ASan on current Arm NN; fresh prior-art gate open
Summary
Arm NN's shared TFLite ParseResize() implementation does not verify that the
resize size tensor contains the two required values before reading height and
width. A structurally valid .tflite file can declare a one-element INT32
size tensor. Arm NN allocates a four-byte vector, copies the valid four-byte
buffer into it, then reads sizeTensorData[1] immediately beyond the
allocation during model loading.
The same vulnerable function handles RESIZE_BILINEAR and
RESIZE_NEAREST_NEIGHBOR. The supplied proof uses RESIZE_BILINEAR.
ValidateBuffer() confirms only that the backing buffer is large enough for
that declared one-element tensor. The parser then assumes two elements exist:
Both files are generated with TensorFlow's official v2.19.0 schema and are 544
bytes:
Artifact
size tensor shape
Buffer bytes
Result
control.tflite
[2]
8
Loads; exit 0
poc.tflite
[1]
4
ASan heap-buffer-overflow read; exit 134
Control:
loaded 544 bytes
PoC:
text
1ERROR: AddressSanitizer: heap-buffer-overflow
2READ of size 4
30 bytes after 4-byte region
4armnnTfLiteParser::TfLiteParserImpl::ParseResize
5armnnTfLiteParser::TfLiteParserImpl::CreateNetworkFromModel
6armnnTfLiteParser::TfLiteParserImpl::CreateNetworkFromBinary
Before allocating or indexing the size vector, require an INT32 tensor with
exactly two elements. Reject any other element count with ParseException.
Add regression tests for both resize operators using the supplied one-element
size tensor.
Novelty
The fresh automated scan and semantic web review found no public report naming
ParseResize, sizeTensorData[1], or the one-element resize-size mismatch.
Public Arm NN TFLite reports found during review cover different operators and
different sinks.